-
Notifications
You must be signed in to change notification settings - Fork 115
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Remove the ComponentStatus resource type #1234
Conversation
The core/v1:ComponentStatus resource only supports the GET operation, and is deprecated/unsupported [1]. Remove it from our SDKs since it's not useful in this form. [1] kubernetes/kubernetes#93570
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM overall.
Is it worth announcing this removal more broadly, in case there are users of it?
I tried using it, and couldn't get it to do anything since it doesn't support POST. I'd be surprised if anyone is using it. |
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> The custom script called from custom Make had temporary modifications to setup.py and pyproject.toml. These are now upstreamed to pulumi/pkg and with version 3.81.0 this happens automatically as part of code generation. This PR removes temporary script code. Fixes #2553 Part of the rollout plain in pulumi/home#2883 ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR improves the handling of the read-only metadata fields of Kubernetes objects, such as `creationTimestamp` and `resourceVersion`. The provider now ignores these fields when they appear as resource inputs, to address a few quirks: 1. Unparseable values do not cause an API Server error during preview. 2. A subsequent refresh does not show a difference to the `__inputs` property. 3. The behavior is now uniform for standard resource types and for custom resource types. An integration test is provided to show that such fields are ignored as inputs, and are still available as outputs. Manual tests confirmed identical behavior for custom resource objects. ### Related issues (optional) Closes #2351 Related: - #2511 - #2445 <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes Closes #2485. This PR implements cancelation for `Create` and `Update` operations on the Helm Release resource. When the user presses ctrl-c, the Helm operation is cancelled and the stack state is updated accordingly. This is an improvement over the current behavior where the Helm release may be orphaned by Pulumi. A future enhancement would be to implement cancelation for the `Delete` operation, once it becomes possible in the Helm v3 library (see [PR](helm/helm#12109) and the `RunWithContext` variants). _Note: no new tests are provided because I don't see a way to simulate cancelation using the integration test framework._ ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Related to pulumi/pulumi#14057. It is safe to merge this PR beforehand.
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This PR exposes the helm template `--kube-version` argument so it can be manually specified in situations when there is no access to the Kubernetes API server (e.g running a diff in CSA mode with no connection to the cluster). Prior to this merge: * If there were zero k8s contexts --> this field was unset meaning helm would default to some old version (1.20.0 at the time of writing) if it couldn't connect to the k8s context * 1+ k8s contexts --> would always try to contact the API server to get the version leading to an error if the API server was unreachable. This variable will override the behavior in either case, but is mostly useful in the first case or when the context in the second case is malformed / unreachable. ### Related issues (optional) <!--Refer to related PRs or issues: pulumi#1234, or 'Fixes pulumi#1234' or 'Closes pulumi#1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes pulumi#2563
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes Closes #2486 This PR exposes the provider input properties as outputs, and normalizes those inputs to provide the effective values. This opens up some new scenarios: 1. Use the provider's namespace as an input property, in a uniform way. 2. A better experience when the ambient kubeconfig is changed; Pulumi reports a diff to `namespace`, `context` or `cluster` as appropriate, which helps to explain why downstream changes may be occurring. ### Detailed Changes The following provider inputs are normalized such that they contain the effective values in stack state: 1. `namespace` - normalized to contain the ambient namespace or `default`. 2. `context`- normalized to contain the ambient context name. 3. `cluster` normalized to contain the ambient cluster name. The `kubeconfig` property is not normalized, which means that the application would need to manually load the ambient config. It seems like a bad idea to normalize the `kubeconfig` for a few reasons: 1. it bloats the stack state to include the entire kubeconfig contents. 2. the kubeconfig may contain a secret in rare situations but isn't modeled as a secret input. 6. the application can workaround it, since the raw output is now available. The Helm provider was simplified to always take the merged kubeconfig (`apiConfig`) from the kube provider, as opposed to reloading it in some cases. This should have no effect on the behavior. Some minor improvements to kubeconfig loading logic: 1. Use a non-interactive loader for the kubeconfig, since the provider is a non-interactive server (see [original PR](e85e033#diff-5e83e1a18ae8dd9641b49e491350ae5b8afaf7fdb60dfcf4d4447a17e334e473R26)). The rationale is to be consistent with the (newer) Helm code. 2. When the `kubeconfig` property is path-like, don't try to parse it as content. This improves the error message. 3. Fallback to using the `default` namespace (as opposed to undefined) for diff purposes when the config could not be loaded. The special-case logic around 'replacement' was simplified to consider only the normalized server name. That is, the provider recommends replacement when the `name` field of the active server has changed. The earlier code had major limitations - it didn't consider the ambient kubeconfig, and didn't support kubeconfig paths. ### Testing New tests were added and/or updated: 1. `TestProvider` - updated to verify that the provider's `namespace` output property is useable as an input to other resources. 2. `TestProviderOutputs` - added to verify provider outputs and the normalization logic. 3. `Test_loadKubeconfig` - added to verify kubeconfig loading/parsing logic. New utility code was developed for easily asserting that certain engine events occurred during `ExtraRuntimeValidation`; see `util.go#AssertEvents`. ### Example Here's an example showing the use of the provider's new `namespace` output property, and showing the improved change detection related to the ambient namespace. The program relies on the ambient kubeconfig, uses the ambient namespace to create a `Deployment`, and binds the provider's `namespace` output property to the stack outputs: ```yaml name: issue-2486-yaml runtime: yaml description: A minimal Kubernetes Pulumi YAML program outputs: namespace: ${k8s.namespace} deployment: ${deployment.metadata.namespace}/${deployment.metadata.name} resources: k8s: type: pulumi:providers:kubernetes deployment: type: kubernetes:apps/v1:Deployment options: provider: ${k8s} properties: spec: replicas: 1 selector: matchLabels: app: nginx template: metadata: labels: app: nginx spec: containers: - image: nginx name: nginx ``` The procedure deploys the stack, changes the ambient namespace, and then previews the changes: ```plain ❯ pulumi up -f Updating (dev) View in Browser (Ctrl+O): https://app.pulumi.com/eron-pulumi-corp/issue-2486-yaml/dev/updates/8 Type Name Status Info + pulumi:pulumi:Stack issue-2486-yaml-dev created (3s) 4 warnings + ├─ pulumi:providers:kubernetes k8s created (0.12s) + └─ kubernetes:apps/v1:Deployment deployment created (2s) Outputs: deployment: "default/deployment-bf4abb76" namespace : "default" Resources: + 3 created Duration: 4s ❯ kubectl config set-context --current --namespace eron Context "docker-desktop" modified. ❯ pulumi preview Previewing update (dev) View in Browser (Ctrl+O): https://app.pulumi.com/eron-pulumi-corp/issue-2486-yaml/dev/previews/2cf2c42a-0a95-42b3-b193-ffca7f401fc7 Type Name Plan Info pulumi:pulumi:Stack issue-2486-yaml-dev 4 warnings ~ ├─ pulumi:providers:kubernetes k8s update [diff: ~namespace] +- └─ kubernetes:apps/v1:Deployment deployment replace [diff: ~metadata] Resources: ~ 1 to update +-1 to replace 2 changes. 1 unchanged ``` The resultant stack state: ```json { "urn": "urn:pulumi:dev::issue-2486-yaml::pulumi:providers:kubernetes::k8s", "custom": true, "id": "78fe6e28-5f2e-4823-af95-df9021ce46f9", "type": "pulumi:providers:kubernetes", "inputs": { "cluster": "docker-desktop", "context": "docker-desktop", "namespace": "default" }, "outputs": { "cluster": "docker-desktop", "context": "docker-desktop", "namespace": "default" }, "parent": "urn:pulumi:dev::issue-2486-yaml::pulumi:pulumi:Stack::issue-2486-yaml-dev", "created": "2023-10-06T00:06:46.065029Z", "modified": "2023-10-06T00:06:46.065029Z" }, ``` ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This is a series of commits to fix a p1 and to improve the import of Helm Releases. The regression occurred because `Read` attempted to use the provider-generated inputs to compute a checksum, and returned an error if it couldn't, and this caused the `pulumi import` tool to fail in cases where the inputs aren't guessable. The fix is to eat the problem during `Read`. While implementing the fix, it became apparent that the templating code for the `Release` resource should be decoupled from the `Chart` resource, mainly to improve the consistency of how chart names are handled. Specific changes: - suppress error in computing inputs during `Read`. - decouple the templating code. - simplify the chart linting code. - use a timeout that is consistent with the Delete op. - new tests for the import variants. <!--Give us a brief description of what you've done and what it solves. --> Closes #2596 ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> --------- Co-authored-by: Ramon Quitales <ramon@pulumi.com>
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This PR enhances the `Release` resource to search harder for a matching chart when importing a release. When Helm installs a chart, it doesn't record any information about the chart location, simply its name. Pulumi attempts to locate a chart: 1. (existing) by looking for an expanded chart directory (e.g. `nginx/`) in the program directory. 2. (new) by looking for a chart archive in the program directory, with or without the version info (e.g. `nginx-15.3.4.tgz`). 3. (new) by looking in the local Helm repositories for a chart, matching the name and version. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
…2653) <!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This PR passes kubeVersion and apiVersions info from the server to Helm to fix a regression that occurred in #2568. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Fixes: #2631
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Closes #2644 This PR fixes support for OCI charts on Windows, by making the code be more consistent with Helm (see [code](https://github.com/helm/helm/blob/main/pkg/action/install.go#L724)). I believe the error comes from the call to `os.Stat` (see Golang implementation which is based on CreateFile, [here](https://go.dev/src/os/stat_windows.go)). ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR stabilizes Helm upgrades **by abandoning the use of checksums** (which was added in v4.5.0, see [PR](#2568)), while allowing for local chart change detection via the chart's version number. That is, the user would be expected to touch the chart's version to compel Pulumi to roll out the change. Implementation-wise, this is accomplished by resolving the `version` property during `Check`. The checked input reflects the goal version, and if the goal has changed, then `Diff` detects this in the natural way and effects an upgrade. `Check` no longer uses `helm template` to render the chart, it simply resolves the chart version. The diff logic is improved here to use a three-way merge, to be able to detect drift in the actual Helm release. The refresh logic is improved to not mutate inputs (as was done in the past to help with drift detection). ### Related issues (optional) Closes #2649 <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
… resource" (#2677) <!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR fixes an intermittent problem that resembles: ``` kubernetes:helm.sh/v3:Release (mongodb): error: 1 error occurred: * Helm release "mongodb/mongodb-456643ba" failed to initialize completely. Use Helm CLI to investigate.: failed to become available within allocated timeout. Error: Helm Release mongodb/mongodb-456643ba: release mongodb-456643ba failed, and has been rolled back due to atomic being set: failed to create resource: the server could not find the requested resource ``` The problem was that a Go struct (containing a client-go rest config) was being shared and mutated by numerous independent routines. The solution was to copy the struct. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2481
…2771) <!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR refactors the kubeconfig loading code to be more consistent between `DiffConfig` and `Configure`. Previously the `DiffConfig` method did not support file-based kubeconfigs, and would throw a spurious parser error. `DiffConfig` loads the kubeconfig to be able to detect cluster replacement, by comparing the active cluster info. Unlike `Configure`, it doesn't have support for ambient kubeconfigs. When an ambient config is in use, or the config is invalid (e.g. the `context` or `cluster` properties refer to a non-existent entry), then the replacement logic is skipped. This PR also fixes a panic in `DiffConfig` that would occur if `cluster` or `context` is a computed value; the provider will conservatively suggest replacement as it does when `kubeconfig` is a computed value. ### Testing New test cases were added for cluster change detection. New tests were added for the parsing code that was consolidated into `utils.go`. The tests now cover file-, string-, and object-based resource property values for `kubeconfig`. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes: #2663 Related: #1032
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR implements unit tests for the await logic, i.e. the flow of hitting the API server (with retry), then invoking the registered awaiter to poll for success, then refreshing the live object. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2791
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This PR clears the resource status after the awaiter completes, to ensure that the status pertaining to a replacement resource (which would have the same URN) isn't stale. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2761
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR changes the provider's await logic to get the object name from the output properties rather than the input properties, since the inputs may or may not contain an object name, to prepare to support `generateName` field (see #2539). Note that auto-naming populates the inputs, whereas generateName doesn't. The awaiters continue to look to the inputs (not the live object) for the `skipAwait` and `timeout` annotations. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Related: #2539
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Skips the normalization step in the presence of computed inputs. Note: previously when `clients.Normalize` was called with a `Secret`, it would panic. If called with a non-secret, an internal error would be masked and the original object would be used. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2845
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> A follow-up to #2863 to upgrade to pu/pu v3.109.0 across the board. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR teaches `ConfigGroup` to detect whether a given file path is a glob pattern, to make the handling of non-existent files be consistent w.r.t `ConfigFile`. In other words, `*.yaml` MAY match a file whereas `manifest.yaml` MUST match a file. The detection code looks for special characters '*', '?', and '[' and respects the escape syntax. Intended to be consistent with: [https://pkg.go.dev/path/filepath#Match](https://pkg.go.dev/path/filepath#Match) An alternative to doing pattern detection would be: 1. to expose a `glob` property to toggle globbing, or 2. a `patterns` property alongside the `files` property for patterns and non-patterns respectively ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2871
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> <!--Give us a brief description of what you've done and what it solves. --> A follow-up to #2863 to upgrade to pu/pu v3.109.0 across the board. <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes Or link to full URLs to issues or pull requests in other GitHub repositories. --> (cherry picked from commit 7246ed3)
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR fixes a couple of related problems with "ambiguous kinds": 1. For kinds with clashing names (e.g. `Role`), be sure to check the apiversion before using built-in information or dynamic discovery. 2. For kinds with casing problems, don't mask the problem; show the API server error. Note that kubectl has the following behavior w.r.t (2): ```yaml apiVersion: awx.ansible.com/v1beta1 kind: awx metadata: name: my-awx namespace: awx ``` ``` ❯ kubectl apply -f manifest.yaml --server-side=false The awx "my-awx" is invalid: kind: Invalid value: "awx": must be AWX ❯ kubectl apply -f manifest.yaml --server-side=true Error from server (BadRequest): invalid object type: awx.ansible.com/v1beta1, Kind=awx ``` An explanation of the technical approach: the `kinds.Kind` type is used in the codebase to represent a well-known kind, i.e. known at code generation time. To prepare this PR, I audited the locations where `Kind` is used, and ensured that it wasn't being used for arbitrary kinds. Where necessary, the use of `Kind` was conditioned on the `apiVersion` being one of the well-known values. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2865 Closes #2143
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This PR doesn't make any substantive changes to the provider, it breaks apart the parsing-and-registration code into two independent functions, in anticipation of applying component-specific sorting strategies. Specifics: - split the logic into `Parse` and `Register` - split the test code accordingly - enriches the registration data that is collected by the mock resource monitor ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR adds support for resource ordering within a `ConfigGroup` or `ConfigFile`. Two approaches are supported (and work in combination): 1. implicit dependencies: the provider uses heuristics to install CRDs and namespaces first. 2. explicit dependencies: the provider understands the `config.kubernetes.io/depends-on` annotation to explicitly declare a dependency on a given resource. The implementation is based on [kubernetes-sigs/cli-utils](https://github.com/kubernetes-sigs/cli-utils) and its support for resource ordering ([documentation](https://github.com/kubernetes-sigs/cli-utils?tab=readme-ov-file#resource-ordering)). To be clear, ordering _across_ `ConfigGroup` resources is supported already, simply using the `dependsOn` option. This PR adds a more granular ordering _within_ the group. ### Testing New test cases were added to verify the new behavior. Many tests rely on a common manifest file, and it is updated to include a CRD and a namespace. Manual testing was performed with the following well-known manifests: 1. knative-serving-core ([ref](https://github.com/knative/serving/releases/download/knative-v1.13.1/serving-core.yaml)) 2. cert-manager ([ref](https://github.com/cert-manager/cert-manager/releases/download/v1.14.4/cert-manager.yaml)) ### Example Here's an example that installs cert-manager then provisions a certificate issuer and a TLS certificate. An explicit dependency is drawn between the `Certificate` and `Issuer`. ```yaml name: issue-2881-cert-manager runtime: yaml description: Installs cert-manager. See https://cert-manager.io/docs/installation/kubectl/ for details. variables: {} resources: install: type: kubernetes:yaml/v2:ConfigGroup properties: files: - https://github.com/cert-manager/cert-manager/releases/download/v1.14.4/cert-manager.yaml test: type: kubernetes:yaml/v2:ConfigGroup options: dependsOn: - ${install} properties: yaml: | apiVersion: v1 kind: Namespace metadata: name: cert-manager-test --- apiVersion: cert-manager.io/v1 kind: Issuer metadata: name: test-selfsigned namespace: cert-manager-test spec: selfSigned: {} --- apiVersion: cert-manager.io/v1 kind: Certificate metadata: name: selfsigned-cert namespace: cert-manager-test annotations: config.kubernetes.io/depends-on: cert-manager.io/namespaces/cert-manager-test/Issuer/test-selfsigned spec: dnsNames: - example.com secretName: selfsigned-cert-tls issuerRef: name: test-selfsigned ``` Within the stack state, one sees dependencies, e.g. on the `Certificate` resource. ```json { "urn": "urn:pulumi:dev::issue-2881-cert-manager::kubernetes:yaml/v2:ConfigGroup$kubernetes:cert-manager.io/v1:Certificate::test-cert-manager-test/selfsigned-cert", "id": "cert-manager-test/selfsigned-cert", "type": "kubernetes:cert-manager.io/v1:Certificate", "dependencies": [ "urn:pulumi:dev::issue-2881-cert-manager::kubernetes:yaml/v2:ConfigGroup$kubernetes:cert-manager.io/v1:Issuer::test-cert-manager-test/test-selfsigned", "urn:pulumi:dev::issue-2881-cert-manager::kubernetes:yaml/v2:ConfigGroup$kubernetes:core/v1:Namespace::test-cert-manager-test" ] } ``` ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2881
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This PR strengthens the normalization of the parsed Kubernetes objects to better interoperate with #2881. Specifically: 1. Applies the default namespace as necessary on each object, so that they may be reliably targeted by the `depends-on` resource. 2. Stabilizes the resource id (e.g. `default/my-map` versus `my-map`). 3. Validates that the objects are well-formed more eagerly than during `Register`. For example, given the below manifest and assuming that the default namespace is `default`, we would expect a `DependsOn` option from `Certificate` to `Issuer`. Observe that `namespace` isn't explicitly set on the issuer. ```yaml name: issue-2870-cert-manager runtime: yaml resources: example: type: kubernetes:yaml/v2:ConfigGroup properties: yaml: | apiVersion: cert-manager.io/v1 kind: Issuer metadata: name: test-selfsigned spec: selfSigned: {} --- apiVersion: cert-manager.io/v1 kind: Certificate metadata: name: selfsigned-cert annotations: config.kubernetes.io/depends-on: cert-manager.io/namespaces/default/Issuer/test-selfsigned spec: dnsNames: - example.com secretName: selfsigned-cert-tls issuerRef: name: test-selfsigned ``` To apply the default namespace correctly, one must know whether a given kind is namespace-scoped. The provider naturally uses the discovery client, and also looks for a matching CRD amongst the parsed objects (since they're not yet installed). ### Testing New test cases were added for `Normalize`, and some test cases were moved from `Register` because the validation is performed more eagerly. New sub-tests were added for `IsNamespacedKind` to cover the local CRD enhancement. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2870
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR changes the prefix character that is used, as per this discussion: https://pulumi.slack.com/archives/C8R654Y6S/p1711035557620359 Tested with a few well-known manifests and seems to be a good improvement on readability. ```plain pulumi:pulumi:Stack issue-2881-cert-manager-dev 4 warn ├─ kubernetes:yaml/v2:ConfigGroup install + │ ├─ kubernetes:core/v1:Namespace install:cert-manager create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-cluster-view create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-controller-certificates create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-edit create + │ ├─ kubernetes:core/v1:ServiceAccount install:cert-manager/cert-manager-webhook create + │ ├─ kubernetes:core/v1:ServiceAccount install:cert-manager/cert-manager create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-view create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-controller-issuers create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-controller-clusterissuers create + │ ├─ kubernetes:core/v1:ServiceAccount install:cert-manager/cert-manager-cainjector create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-controller-ingress-shim create + │ ├─ kubernetes:apiextensions.k8s.io/v1:CustomResourceDefinition install:certificaterequests.cert-manager.io create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRoleBinding install:cert-manager-controller-certificates create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-cainjector create + │ ├─ kubernetes:core/v1:Service install:cert-manager/cert-manager create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:Role install:kube-system/cert-manager-cainjector:leaderelection create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:RoleBinding install:cert-manager/cert-manager-webhook:dynamic-serving create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:Role install:cert-manager/cert-manager-webhook:dynamic-serving create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-controller-certificatesigningrequests create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRoleBinding install:cert-manager-controller-certificatesigningrequests create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:Role install:kube-system/cert-manager:leaderelection create + │ ├─ kubernetes:rbac.authorization.k8s.io/v1:ClusterRole install:cert-manager-controller-approve:cert-manager-io create ``` ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> The yaml/v2 package eagerly resolves kinds to apply a default namespace. This PR addresses a problem with the use case where a kind is installed by one `ConfigGroup` and then used by another. In preview mode, the kind cannot be found by the latter group because the expected side-effect (i.e. installation of a CRD) doesn't occur. The solution to the issue is to maintain a cache in the provider of new CRDs. When the provider executes `Check` on a `CustomResourceDefinition` resource, it adds the CRD to the cache. Later, when a component resource must resolve a given kind, it checks the cache. In this way, the cache compensates for the lack of side-effects (i.e. API server calls) that would normally allow the kind to be resolved. Overall ordering is established using `DependsOn`. It is reasonable to populate the cache during `Check` because a)`Check` produces the "planned" state that is needed later without actuating it, and b) `Update` is called conditionally and thus isn't a reliable alternative. ### Implementation Details The provider has three overlapping modes of operation - preview-mode, `clusterUnreachable` and `yamlRenderMode` - that affect the initialization and use of `clientSet`. Previously when `clusterUnreachable` is true then the `clientSet` is left null. Now, we new-up the `clientSet` itself but leave its various fields null. This change makes it possible to use the CRD cache in all modes, as was necessary to support `yamlRenderMode`. ### Testing A new integration test is added called `yamlv2` that exercises this scenario. Manual testing of "cluster unreachable mode" was done by misconfiguring my local environment (to have an invalid kube context). Tested in combination with "yaml rendering mode" and found that the latter works as expected even when the cluster is unreachable. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Updated the codedocs for new ConfigGroup and ConfigFile (v2) resources. A working example is also provided for YAML and Java. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2868
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
…2957) <!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This PR fixes the "panic" that occurs when an uninitialized provider is used with the yaml/kustomize resources. In that situation, the invoke calls aren't performed and the engine simply returns an uninitialized result. This causes a problem in the callers because the methods on `ImmutableArray` mustn't be used when the value is uninitialized (`IsDefault` is true). ### Example The example given in #2741 easily repros the issue. With this fix, the behavior improves: ``` Diagnostics: kubernetes:yaml:ConfigFile (guestbook): warning: Required input properties have unknown values. Preview is incomplete. Outputs: FrontendIp: output<string> ``` ### Testing Includes integration tests involving an uninitialized provider with a `ConfigFile` or `Directory`. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2741
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR implements an MLC-based `Chart` resource as per [design doc](https://docs.google.com/document/d/1_DZlsAyG4-3BxrAkJBj8R6wIVuzhAkxRDyq8k_Zcst4/edit?usp=sharing). Notable improvements over v3:Chart: - Input schema more closely resembles v3:Release. - Performs templating in an online mode. - More control over resource ordering via annotation: `config.kubernetes.io/depends-on` - Uses [Pulumi Assets](https://www.pulumi.com/docs/concepts/assets-archives/) for supplemental files (keyring, repository opts). - Use assets as values files (`--values`) and as individual values (`--set-file`). - Use multiple values files. - Support for post-rendering w/ arguments. - OCI registry support. Detailed changes: - [pkg/helm] introduce a reusable Helm tool wrapper - [pkg/gen] define `helm.sh/v4:Chart` resource plus `v4:PostRenderer,v4:RepositoryOpts` - [provider] initialize the Helm EnvSettings based on provider configuration - [provider/helmv4] implement Chart resource provider - [provider/yamlv2] add `PreRegisterF` hook to be able to mutate child resource options, specifically `RetainOnDelete` - [provider/yamlv2] new gomega matcher: `HaveSkipAwaitAnnotation()` - [tests/testdata] new 'reference' chart for testing purposes - [misc] bugfix for kube client settings Tests: - New suite for Chart provider w/ coverage of all in-scope features - Extended tests for provider Construct RPC to cover namespacing, kube client settings, helm release settings ### Examples See the examples in the API docs: https://github.com/pulumi/pulumi-kubernetes/blob/47a6ae4fceb8339c49d4f13b5f765af798c0308b/provider/pkg/gen/examples/overlays/chartV4.md#example-usage Local Chart: ```yaml type: kubernetes:helm.sh/v4:Chart properties: namespace: cert-manager chart: ./cert-manager ``` Repository Chart: ```yaml # helm repo add bitnami https://charts.bitnami.com/bitnami type: kubernetes:helm.sh/v4:Chart properties: namespace: cert-manager chart: bitnami/cert-manager version: "1.1.0" ``` Remote Chart: ```yaml type: kubernetes:helm.sh/v4:Chart properties: namespace: cert-manager chart: cert-manager version: "1.1.0" repositoryOpts: repo: https://charts.bitnami.com/bitnami ``` OCI Chart: ```yaml type: kubernetes:helm.sh/v4:Chart properties: namespace: cert-manager chart: oci://registry-1.docker.io/bitnamicharts/cert-manager version: "1.1.0" ``` Custom Values: ```yaml type: kubernetes:helm.sh/v4:Chart properties: namespace: cert-manager chart: oci://registry-1.docker.io/bitnamicharts/cert-manager version: "1.1.0" values: installCRDs: false notes: fn::fileAsset: notes.txt valueYamlFiles: - fn::fileAsset: values.yaml ``` Chart Verification w/ Keyring: ```yaml type: kubernetes:helm.sh/v4:Chart properties: namespace: cert-manager chart: oci://registry-1.docker.io/eronwrightpulumi/cert-manager version: "1.1.0" verify: true keyring: fn::fileAsset: "public.pgp" ``` Post-Rendering: ```yaml type: kubernetes:helm.sh/v4:Chart properties: namespace: cert-manager chart: oci://registry-1.docker.io/bitnamicharts/cert-manager version: "1.1.0" postRenderer: command: ./kustomize args: [] ``` ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Fixes #2847
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Introduces a new Pulumi annotation to set the [deletion propagation policy](https://kubernetes.io/docs/tasks/administer-cluster/use-cascading-deletion/), e.g. to support non-cascading delete on `StatefulSet` to preserve pods during replacement (see [walkthrough](https://kubernetes.io/docs/tutorials/stateful-application/basic-stateful-set/#non-cascading-delete)). Note that the policy annotation must be set on the old resource before deleting or replacing it; setting it on the replacement or on the live object is ineffective. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #1831 ### Example This example serves to show how the 'orphan' propagation policy allows for non-disruptive replacement of a StatefulSet, e.g. by touching the `volumeClaimTemplates`. ```yaml name: issue-1831 runtime: yaml description: A StatefulSet to demonstrate the `pulumi.com/deletionPropagationPolicy` annotation. config: # disable SSA for this demonstration kubernetes:enableServerSideApply: false resources: nginx: type: kubernetes:apps/v1:StatefulSet properties: metadata: name: nginx annotations: pulumi.com/deletionPropagationPolicy: "orphan" spec: replicas: 1 selector: matchLabels: app: nginx serviceName: nginx template: metadata: labels: app: nginx spec: containers: - image: nginx:1.19.9 name: nginx ports: - containerPort: 80 name: web volumeClaimTemplates: - metadata: name: nginx spec: accessModes: - ReadWriteOnce resources: requests: storage: 1Gi ``` Following the initial deployment, we have these objects: ``` ❯ kubectl get statefulset,pod,pvc -ocustom-columns='KIND:.kind,NAME:.metadata.name,UID:.metadata.uid' KIND NAME UID StatefulSet nginx b1aa144d-3f16-448e-8e15-02d2c2d4b61a Pod nginx-0 c00d97cc-39d7-4a95-b839-0910f911dbca PersistentVolumeClaim nginx-nginx-0 2c624ff9-e856-4d2d-bfaf-527c6b770bc7 ``` To provoke a replacement, we change the PVC template: ``` requests: - storage: 1Gi + storage: 2Gi ``` Let's also increase the replicas: ``` spec: - replicas: 1 + replicas: 2 ``` And deploy: ``` ❯ pulumi up -f Updating (dev) Type Name Status Info pulumi:pulumi:Stack issue-1831-dev 4 warnings; 2 messages +- └─ kubernetes:apps/v1:StatefulSet nginx replaced (2s) [diff: ~spec] Resources: +-1 replaced 1 unchanged ``` Looking again at the objects: ``` ❯ kubectl get statefulset,pod,pvc -ocustom-columns='KIND:.kind,NAME:.metadata.name,UID:.metadata.uid' KIND NAME UID StatefulSet nginx 135d9142-460c-4f64-82a6-8ce23427f52b Pod nginx-0 c00d97cc-39d7-4a95-b839-0910f911dbca Pod nginx-1 8c80932f-7051-4fc7-baeb-00dae4b07b64 PersistentVolumeClaim nginx-nginx-0 2c624ff9-e856-4d2d-bfaf-527c6b770bc7 PersistentVolumeClaim nginx-nginx-1 e4b4fd18-28b2-454b-8c6b-9fa06435d3d6 ``` We see the expected result: the StatefulSet was replaced, the existing pod was adopted, and a new pod was added w/ a PVC. In more detail, the StatefulSet controller uses the selector to identify existing pods, then chooses to delete or adopt based on suitability. Note the updated owner reference on `nginx-0`: ```yaml apiVersion: v1 kind: Pod metadata: name: nginx-0 uid: c00d97cc-39d7-4a95-b839-0910f911dbca ownerReferences: - apiVersion: apps/v1 blockOwnerDeletion: true controller: true kind: StatefulSet name: nginx uid: 135d9142-460c-4f64-82a6-8ce23427f52b ``` To demonstrate how the StatefulSet controller might choose to delete the existing pod rather than adopting it, let's change the image rather than the replicas: ``` containers: - - image: nginx:1.19.9 + - image: nginx:1.19.10 requests: - storage: 2Gi + storage: 3Gi ``` We deploy again and see that all pods were replaced. ``` KIND NAME UID StatefulSet nginx ead53943-abc9-47c8-9393-326f845c7f42 Pod nginx-0 74752b8c-3979-478b-9be4-ff3ca1b0aa6f Pod nginx-1 b6c2f0f6-f5ff-4e04-a1da-66966b8d697c PersistentVolumeClaim nginx-nginx-0 2c624ff9-e856-4d2d-bfaf-527c6b770bc7 PersistentVolumeClaim nginx-nginx-1 e4b4fd18-28b2-454b-8c6b-9fa06435d3d6 ``` Note that PVC `nginx-nginx-0` was not replaced and still has `storage: 1Gi`.
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2800
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes This PR updates the pulumi-java dependency from v0.8.0 to v0.12.0. Notable changes: - pulumi/pulumi-java#1356 - pulumi/pulumi-java#1361 - pulumi/pulumi-java#1228 ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Implements `CustomResource` for Java SDK as an overlay, for parity with other SDKs. An overlay is necessary for [this reason](#2787 (comment)). #### Features Supports two usage modes. Note that each SDK is slightly different in which mode(s) it supports. - **untyped**, where you use `CustomResource` directly and set arbitrary fields on the object. - **typed**, where you subclass `CustomResource` to create a strongly-typed wrapper representing a CRD. A "Patch" variant is also provided. Provides a "getter" method in both untyped and typed mode. Note that the patch variant doesn't have a getter in most SDKs. #### Summary of Changes - new example: `examples/java/customresource` - new resource: `apiextensions.CustomResource` - new resource: `apiextensions.CustomResourcePatch` - new dependency: `net.bytebuddy:byte-buddy:1.14.15` - new dependency:`com.google.guava:guava:32.1.2-jre` (used by core already) TODOs: - [x] Prerequisite: Pulumi Java 0.12 (pulumi/pulumi-java#1361) - [x] `Get` method (untyped and typed) - [x] Patch variant - [x] Integration test or in-tree example ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2787 ### API - `CustomResource` - to be used directly or subclassed to expose typed output properties - `CustomResourceArgs` - the final class to be used directly in the untyped use-case - `CustomResourceArgsBase` - the abstract base class for custom resource args, to expose typed input properties - `CustomResourceArgsBase.Builder<T,B>` - the base class for your custom args builder - `CustomResourcePatch` - to be used directly or subclassed to expose typed output properties - `CustomResourcePatchArgs` - the final class to be used directly in the untyped use-case - `CustomResourcePatchArgsBase` - the abstract base class for custom resource args, to expose typed input properties - `CustomResourcePatchArgsBase.Builder<T,B>` - the base class for your custom args builder ### Implementation Details #### Working with Untyped Inputs The core Pulumi Java SDK has no support for dynamic inputs; it relies exclusively on reflection of the supplied `InputArgs` subclass (see: [`InputArgs::toMapAsync`](https://github.com/pulumi/pulumi-java/blob/f887fbc869974ae7d9049cb4a5b62f51b1151dcb/sdk/java/pulumi/src/main/java/com/pulumi/resources/InputArgs.java#L63)). To support the "untyped" mode, this implementation codegens a class at runtime using bytebuddy. #### Builder Inheritance The Java SDK leans on the fluent builder pattern, and there are special challenges in designing a builder that is amenable to inheritance. This implementation uses generics as seen [here](https://egalluzzo.blogspot.com/2010/06/using-inheritance-with-fluent.html). ## Example Here's an example program to deploy two [cert-manager issuers](https://cert-manager.io/docs/concepts/issuer/). - `issuer1` is untyped, and calls `otherFields(...)` on the builder to set the `spec`. - `issuer2` is typed, calls `spec(...)` on a subclassed builder to set the `spec`, and uses the typed `spec` output. Note that the `apiVersion` and `kind` are set automatically. The code seen in `Inputs` and `Outputs` section would, in practice, be generated by pulumi-java-gen based on a schema file. The untyped and typed getter variants are also demonstrated. ```java package myproject; import java.util.Map; import java.util.Objects; import java.util.Optional; import javax.annotation.Nullable; import com.pulumi.Pulumi; import com.pulumi.core.Output; import com.pulumi.core.annotations.CustomType; import com.pulumi.core.annotations.Export; import com.pulumi.core.annotations.Import; import com.pulumi.kubernetes.apiextensions.CustomResource; import com.pulumi.kubernetes.apiextensions.CustomResourceArgs; import com.pulumi.kubernetes.apiextensions.CustomResourceArgsBase; import com.pulumi.kubernetes.meta.v1.inputs.ObjectMetaArgs; public class App { public static void main(String[] args) { Pulumi.run(ctx -> { var issuer1 = new CustomResource("issuer1", CustomResourceArgs.builder() .apiVersion("cert-manager.io/v1") .kind("Issuer") .metadata(ObjectMetaArgs.builder().build()) .otherFields(Map.of("spec", Map.of( "selfSigned", Map.of()))) .build()); ctx.export("issuer1_name", issuer1.metadata().applyValue(s -> s.name())); var get1 = CustomResource.get("get1", "cert-manager.io/v1", "Issuer", issuer1.id(), null); var issuer2 = new Issuer("issuer2", IssuerArgs.builder() .metadata(ObjectMetaArgs.builder().build()) .spec(Inputs.IssuerSpecArgs.builder() .selfSigned(Inputs.SelfSignedArgs.builder().build()) .build()) .build()); ctx.export("issuer2_name", issuer2.metadata().applyValue(s -> s.name())); ctx.export("issuer2_selfsigned", issuer2.spec().applyValue(s -> s.selfSigned().isPresent())); var get2 = Issuer.get("get2", issuer2.id(), null); ctx.export("get2_selfsigned", get2.spec().applyValue(s -> s.selfSigned().isPresent())); }); } } class Issuer extends CustomResource { /** * The spec of the Issuer. */ @export(name = "spec", refs = { Outputs.IssuerSpec.class }, tree = "[0]") private Output<Outputs.IssuerSpec> spec; public Output<Outputs.IssuerSpec> spec() { return this.spec; } public Issuer(String name, @nullable IssuerArgs args) { super(name, makeArgs(args)); } public Issuer(String name, @nullable IssuerArgs args, @nullable com.pulumi.resources.CustomResourceOptions options) { super(name, makeArgs(args), options); } protected Issuer(String name, Output<String> id, @nullable com.pulumi.resources.CustomResourceOptions options) { super(name, "cert-manager.io/v1", "Issuer", id, options); } private static IssuerArgs makeArgs(@nullable IssuerArgs args) { var builder = args == null ? IssuerArgs.builder() : IssuerArgs.builder(args); return builder .apiVersion("cert-manager.io/v1") .kind("Issuer") .build(); } public static Issuer get(String name, Output<String> id, @nullable com.pulumi.resources.CustomResourceOptions options) { return new Issuer(name, id, options); } } class IssuerArgs extends CustomResourceArgsBase { /** * The spec of the Issuer. */ @import(name = "spec", required = true) @nullable private Output<Inputs.IssuerSpecArgs> spec; public static Builder builder() { return new Builder(); } public static Builder builder(IssuerArgs defaults) { return new Builder(defaults); } static class Builder extends CustomResourceArgsBase.Builder<IssuerArgs, Builder> { public Builder() { super(new IssuerArgs()); } public Builder(IssuerArgs defaults) { super(new IssuerArgs(), defaults); } public Builder spec(@nullable Output<Inputs.IssuerSpecArgs> spec) { $.spec = spec; return this; } public Builder spec(Inputs.IssuerSpecArgs spec) { return spec(Output.of(spec)); } @OverRide protected void copy(IssuerArgs args) { super.copy(args); $.spec = args.spec; } } } class Inputs { public static final class IssuerSpecArgs extends com.pulumi.resources.ResourceArgs { public static final IssuerSpecArgs Empty = new IssuerSpecArgs(); @import(name = "selfSigned", required = true) private @nullable Output<SelfSignedArgs> selfSigned; public Optional<Output<SelfSignedArgs>> selfSigned() { return Optional.ofNullable(this.selfSigned); } private IssuerSpecArgs() { } private IssuerSpecArgs(IssuerSpecArgs $) { this.selfSigned = $.selfSigned; } public static Builder builder() { return new Builder(); } public static Builder builder(IssuerSpecArgs defaults) { return new Builder(defaults); } public static final class Builder { private IssuerSpecArgs $; public Builder() { $ = new IssuerSpecArgs(); } public Builder(IssuerSpecArgs defaults) { $ = new IssuerSpecArgs(Objects.requireNonNull(defaults)); } public Builder selfSigned(@nullable Output<SelfSignedArgs> selfSigned) { $.selfSigned = selfSigned; return this; } public Builder selfSigned(SelfSignedArgs selfSigned) { return selfSigned(Output.of(selfSigned)); } public IssuerSpecArgs build() { return $; } } } public static final class SelfSignedArgs extends com.pulumi.resources.ResourceArgs { public static final SelfSignedArgs Empty = new SelfSignedArgs(); private SelfSignedArgs() { } private SelfSignedArgs(SelfSignedArgs $) { } public static Builder builder() { return new Builder(); } public static Builder builder(SelfSignedArgs defaults) { return new Builder(defaults); } public static final class Builder { private SelfSignedArgs $; public Builder() { $ = new SelfSignedArgs(); } public Builder(SelfSignedArgs defaults) { $ = new SelfSignedArgs(Objects.requireNonNull(defaults)); } public SelfSignedArgs build() { return $; } } } } class Outputs { @CustomType static final class IssuerSpec { private @nullable SelfSigned selfSigned; private IssuerSpec() { } public Optional<SelfSigned> selfSigned() { return Optional.ofNullable(this.selfSigned); } public static Builder builder() { return new Builder(); } public static Builder builder(IssuerSpec defaults) { return new Builder(defaults); } @CustomType.Builder public static final class Builder { private @nullable SelfSigned selfSigned; public Builder() { } public Builder(IssuerSpec defaults) { Objects.requireNonNull(defaults); this.selfSigned = defaults.selfSigned; } @CustomType.Setter public Builder selfSigned(@nullable SelfSigned selfSigned) { this.selfSigned = selfSigned; return this; } public IssuerSpec build() { final var _resultValue = new IssuerSpec(); _resultValue.selfSigned = selfSigned; return _resultValue; } } } @CustomType static final class SelfSigned { private SelfSigned() { } public static Builder builder() { return new Builder(); } public static Builder builder(SelfSigned defaults) { return new Builder(defaults); } @CustomType.Builder public static final class Builder { public Builder() { } public Builder(SelfSigned defaults) { Objects.requireNonNull(defaults); } public SelfSigned build() { final var _resultValue = new SelfSigned(); return _resultValue; } } } } ``` Gives the expected output: ``` ❯ pulumi preview --diff Previewing update (dev) + pulumi:pulumi:Stack: (create) [urn=urn:pulumi:dev::issue-2787-javaa::pulumi:pulumi:Stack::issue-2787-javaa-dev] + kubernetes:cert-manager.io/v1:Issuer: (create) [urn=urn:pulumi:dev::issue-2787-javaa::kubernetes:cert-manager.io/v1:Issuer::issuer1] [provider=urn:pulumi:dev::issue-2787-javaa::pulumi:providers:kubernetes::default_0_0_16_SNAPSHOT::04da6b54-80e4-46f7-96ec-b56ff0331ba9] apiVersion: "cert-manager.io/v1" kind : "Issuer" metadata : { annotations: { pulumi.com/autonamed: "true" } name : "issuer1-dcda28b8" namespace : "default" } spec : { selfSigned: {} } + kubernetes:cert-manager.io/v1:Issuer: (create) [urn=urn:pulumi:dev::issue-2787-javaa::kubernetes:cert-manager.io/v1:Issuer::issuer2] [provider=urn:pulumi:dev::issue-2787-javaa::pulumi:providers:kubernetes::default_0_0_16_SNAPSHOT::04da6b54-80e4-46f7-96ec-b56ff0331ba9] apiVersion: "cert-manager.io/v1" kind : "Issuer" metadata : { annotations: { pulumi.com/autonamed: "true" } name : "issuer2-a0d8c527" namespace : "default" } spec : { selfSigned: {} } --outputs:-- issuer1_name : "issuer1-dcda28b8" issuer2_name : "issuer2-a0d8c527" issuer2_selfsigned: true ```
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ## Proposed changes This PR implements the Kustomize `Directory` resource (v2) as a multi-language component resource. The `Directory` resource creates child resources based on a kustomization directory. The input is a path to a directory containing 'kustomization.yaml', or a git repository URL with a path suffix and other qualifiers. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #2786 ### API |property|description| |-|-| | `directory` | The directory or git URL containing the kustomization to apply. | | `namespace` | Overrides the default namespace. | | `skipAwait` | Applies the skipAwait annotation. | | `resourcePrefix` | Prefix for child resources, defaults to the component name. | ### Feature: Remote Targets This implementation supports remote kustomization targets as described [here](https://github.com/kubernetes-sigs/kustomize/blob/master/examples/remoteBuild.md). Note: the v1 implementation also supports git references, but resolves them using the Pulumi SDK ([`RetrieveGitFolder`](https://github.com/pulumi/pulumi/blob/v3.117.0/sdk/go/common/workspace/templates.go#L392)) rather than using Kustomize's own implementation. ### Feature: Enable Alpha Plugins This implementation always enables Kustomize's plugin support, akin to `kustomize build --enable-alpha-plugins`. Plugins are drawn from `KUSTOMIZE_PLUGIN_HOME` (default: `~/.config/kustomize/plugin/`). Note: the kustomize library doesn't allow for easy customization of the plugin home. ### Feature: Unrestricted Loading Kustomize has a strict and a relaxed mode with respect to path references outside the kustomization base directory (`--load-restrictor`, default is `strict`). The feature seems intended to encourage portability, similarly to paths in Dockerfiles. This implementation simply enables the relaxed mode. ### Feature: Enable Helm Charts This implementation enables [Helm chart support in Kustomize](https://kubectl.docs.kubernetes.io/references/kustomize/kustomization/helmcharts/), which is an experimental feature of Directory v1 (see: #2470). Note that chart support in Kustomize is limited and evolving; see kubernetes-sigs/kustomize#4401 for the long-term support plan. The `helm` binary is assumed to be on the path. ### Feature: Namespace Override New to v2 is support for overriding the default namespace (default is from provider configuration), as a convenience. Kustomize itself has a similar facility (see: [namespace](https://kubectl.docs.kubernetes.io/references/kustomize/kustomization/namespace/)) but it makes sense to support it natively. ### Feature: Resource Ordering The Directory resource uses Pulumi's engine to install the resources produced by kustomize. It automatically detects dependencies between some resources. For example, it knows to install namespaces and Custom Resource Definitions (CRDs) first. Use the `config.kubernetes.io/depends-on` annotation to declare an explicit resource dependency. See [blog post](https://www.pulumi.com/blog/kubernetes-yaml-v2/#resource-ordering) for more info. ### Limitation: Kubernetes-Style Transformations The older v1 implementation provides the ability to transform the Kubernetes objects produced by kustomize before being sent to the server. That feature isn't available in Directory v2 at this time. You may still use Pulumi's [transform option](https://www.pulumi.com/docs/concepts/options/transformations/) to modify the child resources. ### Tests The PR includes unit tests covering the provider implementation code. ### Example Here's an example of deploying a couple of kustomizations. The `local` kustomization (see: [helloWorld](https://github.com/kubernetes-sigs/kustomize/tree/master/examples/helloWorld) for details) shows how to use a variable to select a kustomization overlay. ```yaml name: issue-2786-yaml runtime: yaml description: | Demonstrates the Directory resource. Reference: https://github.com/kubernetes-sigs/kustomize/tree/master/examples/helloWorld config: variant: type: string default: staging outputs: name: ${local.resources} resources: ns: type: kubernetes:core/v1:Namespace local: type: kubernetes:kustomize/v2:Directory properties: namespace: ${ns.metadata.name} directory: ./config/${variant} skipAwait: true remote: type: kubernetes:kustomize/v2:Directory properties: namespace: ${ns.metadata.name} directory: https://github.com/kubernetes-sigs/kustomize//examples/helloWorld/?ref=v3.3.1 skipAwait: true ```
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR fixes a problem with how Chart v4 uses the Helm library. The design goal is to allow for connectivity during template rendering, to support the lookup function (see helm/helm#9426) and to provide an accurate [Capabilities object](https://helm.sh/docs/chart_template_guide/builtin_objects/). Unfortunately we were slightly too aggressive and caused some of Helm's "non-template" code to execute. This fix works by turning off the `helm template --validation` flag, so that the internal `ClientOnly` flag is true thus avoiding [this block of code](https://github.com/helm/helm/blob/6f32a8f9d338bacc3c6a1c0c3610012b01edb3d1/pkg/action/install.go#L345-L350) that causes the unexpected error. A side-effect of `ClientOnly` being true is that the capabilities aren't automatically set, and so we set them using the provider's kube client (akin to using `--kube-version`). Detailed changes: - (chart.go) use ClientOnly mode, set KubeVersion and APIVersions - (tool.go) remove redundant KubeVersion and ExtraAPIs - (testdata/reference) add a version check - (chart_test.go) unit tests for `.Capabilities` - integration test to install cert-manager ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #3045
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR fixes the `ValueOpts` in `pkg/provider/pkg/helm` to properly handle arrays of values when expanding the assets. New unit test cases were added. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #3060
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Some minor updates to the API docs for the overlay components: - link to the newer version of the respective component, since the newer versions have fixes for some of the long-standing issues with these overlays. - clarify the supported languages I had considered adding a "known issues" section, e.g. to mention the `dependsOn` limitation, but I felt it would be overkill, and that simply linking to the newer version would suffice. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #1773 Closes #2181
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This PR seeks to make the `apiVersion` and `kind` properties be [plain](https://www.pulumi.com/docs/using-pulumi/pulumi-packages/schema/#type) (prompt) values when configuring a `CustomResource`. A plain value is required to eagerly compute the resource type token, e.g. `kubernetes:stable.example.com/v1:CronTab` or `kubernetes:stable.example.com/v1:CronTabPatch`. Since the SDKs already accept an input, this PR strives to continue to support it, rather than making a breaking change, if possible. That's accomplished by synchronously waiting on the output data. Three APIs are considered here: 1. creating or importing a CustomResource using resource args 2. getting an existing custom resource using the `get` helpers 3. patching a CustomResource using the "Patch" variant A summary of changes: - Pulumi Schema - mark the `apiVersion` and `kind` properties to be `plain: true`. - Go SDK - Use `internals.UnsafeAwaitOutput` to synchronously resolve the value. - NodeJS SDK - Change to CustomResourceArgs to use plain property type (BREAKING CHANGE) - Java SDK - add some null checks ### Breaking Changes #### NodeJS SDK The args are retyped to `string` with expectation that most programs will be unaffected. Closes #1115 ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
This issue has been addressed in PR #3079 and shipped in release v4.15.0. |
This issue has been addressed in PR #3061 and shipped in release v4.14.0. |
This issue has been addressed in PR #3036 and shipped in release v4.13.1. |
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> _Blocked on: https://github.com/pulumi/pulumi-java/pull/1394_ Updated Java SDK with better support for resource hydration, per pulumi/pulumi-java#1393. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #3057
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Re: pulumi/ci-mgmt#1091 Since the original dependency required higher SDK versions than 3.x.x., the remediation also upgrades SDK generators to latest. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Adds a doc note to Chart/v4 regarding the Release v3/v4 resource. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> Closes #3263
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> This updates the code does the following: - Updates to pulumi-java v1.0.0 - Updates the .pulumi.version to use v3.146.0 so that it matches the provider/go.mod - Updates the CHANGELOG so that markdownlint doesn't complain. ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. -->
<!--Thanks for your contribution. See [CONTRIBUTING](CONTRIBUTING.md) for Pulumi's contribution guidelines. Help us merge your changes more quickly by adding more details such as labels, milestones, and reviewers.--> ### Proposed changes <!--Give us a brief description of what you've done and what it solves. --> Changelog Only for Release ### Related issues (optional) <!--Refer to related PRs or issues: #1234, or 'Fixes #1234' or 'Closes #1234'. Or link to full URLs to issues or pull requests in other GitHub repositories. --> --------- Co-authored-by: Ramon Quitales <ramon@pulumi.com>
Proposed changes
The core/v1:ComponentStatus resource only supports the GET
operation, and is deprecated/unsupported [1]. Remove it from
our SDKs since it's not useful in this form.
[1] kubernetes/kubernetes#93570
Related issues (optional)
Fix #1233