github.com/argoproj/argo-cd/v3@v3.2.1/docs/operator-manual/upgrading/2.14-3.0.md (about) 1 # v2.14 to 3.0 2 3 Argo CD 3.0 is meant to be a low-risk upgrade containing only minor breaking changes. For each change, the next 4 section will describe how to quickly determine if you are impacted, how to remediate the breaking change, and (if 5 applicable) restore Argo CD 2.x default behavior. 6 7 Once 3.0 is released, no more 2.x minor versions will be released. We will continue to cut patch releases for the two 8 most recent minor versions (so 2.14 until 3.2 is released and 2.13 until 3.1 is released). 9 10 ## Images missing release notes on GitHub 11 12 !!! important 13 Images 3.0.7 - 3.0.10 are missing release notes on GitHub. There was an issue with GoReleaser and building the darwin 14 CLI that prevented the release notes from being published. More information can be found 15 on [PR #23507](https://github.com/argoproj/argo-cd/pull/23507) 16 17 ## Breaking Changes 18 19 ### Fine-Grained RBAC for application `update` and `delete` sub-resources 20 21 The default behavior of fine-grained policies have changed so they no longer apply to sub-resources. 22 Prior to v3, policies granting `update` or `delete` to an application also applied to any of its sub-resources. 23 24 Starting with v3, the `update` or `delete` actions only apply to the application itself. New policies must be defined 25 to allow the `update/*` or `delete/*` actions on an Application's managed resources. 26 27 The v2 behavior can be preserved by setting the config value `server.rbac.disableApplicationFineGrainedRBACInheritance` 28 to `false` in the Argo CD ConfigMap `argocd-cm`. 29 30 Read the [RBAC documentation](../rbac.md#fine-grained-permissions-for-updatedelete-action) for more detailed 31 information. 32 33 ### Logs RBAC enforcement as a first-class RBAC citizen 34 35 2.4 introduced `logs` as a new RBAC resource. In 2.3 and lower, users with `applications, get` access automatically got logs access. In 2.4, it became possible to enable logs RBAC enforcement with a flag in `argocd-cm` ConfigMap: 36 37 ```yaml 38 server.rbac.log.enforce.enable: 'true' 39 ``` 40 41 Starting from 3.0, this flag is removed and the logs RBAC is enforced by default, meaning the `logs` tab on `pod` view will not be visible without granting explicit `logs, get` permissions to the users/groups/roles requiring it. 42 43 #### Detection 44 45 Users who have `server.rbac.log.enforce.enable: "true"` in their `argocd-cm` ConfigMap, are unaffected by this change. 46 47 Users who have `policy.default: role:readonly` or `policy.default: role:admin` in their `argocd-rbac-cm` ConfigMap, are unaffected. 48 49 Users who don't have a `policy.default` in their `argocd-rbac-cm` ConfigMap, and either have `server.rbac.log.enforce.enable` set to `false` or don't have this setting at all in their `argocd-cm` ConfigMap are affected and should perform the below remediation steps. 50 51 After the upgrade, it is recommended to remove the setting `server.rbac.log.enforce.enable` from `argocd-cm` ConfigMap, if it was there before the upgrade. 52 53 #### Remediation 54 55 ##### Quick remediation (global change) 56 57 For users with an existing default policy with a custom role, add this policy to `policy.csv` for your custom role: `p, role:<YOUR_DEFAULT_ROLE>, logs, get, */*, allow`. 58 For users without a default policy, add this policy to `policy.csv`: `p, role:global-log-viewer, logs, get, */*, allow` and add the default policy for this role: `policy.default: role:global-log-viewer` 59 60 ##### Recommended remediation (per-policy change) 61 62 Explicitly add a `logs, get` policy to every role that has a policy for `applications, get` or for `applications, *`. 63 This is the recommended way to maintain the principle of least privilege. 64 Similar to the way access to Applications are currently managed, access to logs can be either granted on a Project scope level (Project resource) or on the `argocd-rbac-cm` ConfigMap level. 65 See this [example](../upgrading/2.3-2.4.md#example-1) for more details. 66 67 ### Default `resource.exclusions` configurations 68 69 Argo CD manifest now contains a default configuration for `resource.exclusions` in the `argocd-cm` to exclude resources that 70 are known to be created by controllers and not usually managed in Git. The exclusions contain high volume and high churn objects 71 which we exclude for performance reasons, reducing connections and load to the K8s API servers of managed clusters. 72 73 The excluded Kinds are: 74 75 - **Kubernetes Resources**: `Endpoints`, `EndpointSlice`, `Lease`, `SelfSubjectReview`, `TokenReview`, `LocalSubjectAccessReview`, `SelfSubjectAccessReview`, `SelfSubjectRulesReview`, `SubjectAccessReview`, `CertificateSigningRequest`, `PolicyReport` and `ClusterPolicyReport`. 76 - **Cert Manager**: `CertificateRequest`. 77 - **Kyverno**: `EphemeralReport`, `ClusterEphemeralReport`, `AdmissionReport`, `ClusterAdmissionReport`, `BackgroundScanReport`, `ClusterBackgroundScanReport` and `UpdateRequest`. 78 - **Cilium**: `CiliumIdentity`, `CiliumEndpoint` and `CiliumEndpointSlice`. 79 80 The default `resource.exclusions` can be overridden or removed in the configMap to preserve the v2 behavior. 81 82 Read the [Declarative Setup](../declarative-setup.md) for more detailed information to configure `resource.exclusions`. 83 84 ### Removal of `argocd_app_sync_status`, `argocd_app_health_status` and `argocd_app_created_time` Metrics 85 86 The `argocd_app_sync_status`, `argocd_app_health_status` and `argocd_app_created_time`, deprecated and disabled by 87 default since 1.5.0, have been removed. The information previously provided by these metrics is now available as labels 88 on the `argocd_app_info` metric. 89 90 #### Detection 91 92 Starting with 1.5.0, these metrics are only available if `ARGOCD_LEGACY_CONTROLLER_METRICS` is explicitly set to `true`. 93 If it is not set to true, you can safely upgrade with no changes. 94 95 #### Migration 96 97 If you are using these metrics, you will need to update your monitoring dashboards and alerts to use the new metric and 98 labels before upgrading. 99 100 ### Changes to RBAC with Dex SSO Authentication 101 102 When using Dex, the `sub` claim returned in the authentication was used as the subject for RBAC. That value depends on 103 the Dex internal implementation and should not be considered an immutable value that represents the subject. 104 105 The new behavior will request the 106 `federated:id` [scope](https://dexidp.io/docs/configuration/custom-scopes-claims-clients/) from Dex, and the new value 107 used as the RBAC subject will be based 108 on the `federated_claims.user_id` claim instead of the `sub` claim. 109 110 If you were using the Dex sub claim in RBAC policies, you will need to update them to maintain the same access. 111 112 You can know the correct `user_id` to use by decoding the current `sub` claims defined in your policies. You can also 113 configure which 114 value is used as `user_id` for some [connectors](https://dexidp.io/docs/connectors/). 115 116 ```sh 117 $> echo "ChdleGFtcGxlQGFyZ29wcm9qLmlvEgJkZXhfY29ubl9pZA" | base64 -d 118 119 example@argoproj.iodex_conn_i% 120 ``` 121 122 ```yaml 123 # Policies based on the Dex sub claim (wrong) 124 - g, ChdleGFtcGxlQGFyZ29wcm9qLmlvEgJkZXhfY29ubl9pZA, role:example 125 - p, ChdleGFtcGxlQGFyZ29wcm9qLmlvEgJkZXhfY29ubl9pZA, applications, *, *, allow 126 127 # Policies now based on federated_claims.user_id claim (correct) 128 - g, example@argoproj.io, role:example 129 - p, example@argoproj.io, applications, *, *, allow 130 ``` 131 132 If authenticating with the CLI, make sure to use the new version as well to obtain an authentication token with the 133 appropriate claims. 134 135 ### Removed support for legacy repo config in argocd-cm 136 137 Before repositories were managed as Secrets, they were configured in the argocd-cm ConfigMap. The argocd-cm option has 138 been deprecated for some time and is no longer available in Argo CD 3.0. 139 140 #### Detection 141 142 To check whether you have any repositories configured in argocd-cm, run the following command: 143 144 ```shell 145 kubectl get cm argocd-cm -n argocd -o=jsonpath="[{.data.repositories}, {.data['repository\.credentials']}, {.data['helm\.repositories']}]" 146 ``` 147 148 If you have no repositories configured in argocd-cm, the output will be `[, , ]`, and you are not impacted by this 149 change. 150 151 #### Migration 152 153 To convert your repositories to Secrets, follow the documentation for 154 [declarative management of repositories](../declarative-setup.md#repositories). 155 156 ### Ignoring ApplicationSet `applyNestedSelectors` field 157 158 Setting the `spec.applyNestedSelectors` field in an ApplicationSet resolves counter-intuitive behavior where filters in 159 nested selectors were not applied. Starting in Argo CD 3.0, the field is ignored, and behavior is always the same as if 160 `applyNestedSelectors` was set to `true`. In other words, nested selectors are always applied. 161 162 #### Detection 163 164 To detect if you are impacted, search your ApplicationSet controller logs for this string: `ignoring nested selector`. 165 If there are no logs with this string, you are not impacted. 166 167 Another way to detect if you are impacted is to run the following command: 168 169 ```shell 170 kubectl get appsets -o=json | jq -r '.items[] | select( 171 .spec.applyNestedSelectors != true and 172 .spec.generators[][].generators[][].generators[].selector != null 173 ) | .metadata.name' 174 ``` 175 176 The command will print the name of any ApplicationSet that has `applyNestedSelectors` unset or set to `false` and has 177 one or more nested selectors. 178 179 #### Remediation 180 181 Since `applyNestedSelectors` is false by default, you can safely remove the nested selectors on ApplicationSets where 182 `applyNestedSelectors` has not been explicitly set to `true`. After the selectors are removed, you can safely upgrade. 183 184 For example, you should remove the selector in this ApplicationSet before upgrading to Argo CD 3.0. 185 186 ```diff 187 apiVersion: argoproj.io/v1alpha1 188 kind: ApplicationSet 189 metadata: 190 name: guestbook 191 spec: 192 goTemplate: true 193 goTemplateOptions: ["missingkey=error"] 194 generators: 195 - matrix: 196 mergeKeys: ['test-key'] 197 generators: 198 - list: 199 elements: 200 - test-key: 'test-value' 201 cluster: staging 202 - test-key: 'test-value' 203 cluster: production 204 - merge: 205 generators: 206 - list: 207 elements: 208 - another-key: 'another-value' 209 - cluster: {} 210 - selector: 211 - matchLabels: 212 - app: guestbook 213 214 template: 215 metadata: 216 name: '{{.cluster}}-guestbook' 217 spec: 218 project: my-project 219 source: 220 repoURL: https://github.com/infra-team/cluster-deployments.git 221 targetRevision: HEAD 222 path: guestbook/{{.cluster}} 223 destination: 224 server: '{{.url}}' 225 namespace: guestbook 226 ``` 227 228 ### Upgraded Helm version with breaking changes 229 230 Helm was upgraded to 3.17.1. 231 This may require changing your `values.yaml` files for subcharts, if the `values.yaml` contain a section with a `null` object. 232 See related issue in [Helm GitHub repository](https://github.com/helm/helm/issues/12469) 233 See Helm 3.17.1 [release notes](https://github.com/helm/helm/releases/tag/v3.17.1) 234 Example of such a [problem and resolution](https://github.com/argoproj/argo-cd/pull/22035/files) 235 Explanation: 236 237 - Prior to Helm 3.17.1, `null` object in `values.yaml` resulted in a warning: `cannot overwrite table with non table` upon performing `helm template`, and the resulting K8s object was not overridden with the invalid `null` value. 238 - In Helm 3.17.1, this behavior changed and `null` object in `values.yaml` still results in this warning upon performing `helm template`, but the resulting K8s object will be overridden with the invalid `null` value. 239 - To resolve the issue, identify `values.yaml` with `null` object values, and remove those `null` values. 240 241 ### Use Annotation-Based Tracking by Default 242 243 The default behavior for [tracking resources](../../user-guide/resource_tracking.md) has changed to use annotation-based 244 tracking instead of label-based tracking. Annotation-based tracking is more reliable and less prone to errors caused by 245 external code copying tracking labels from one resource to another. 246 247 #### Detection 248 249 To detect if you are impacted, check the `argocd-cm` ConfigMap for the `application.resourceTrackingMethod` field. If it is 250 unset or is set to `label`, you are using label-based tracking. If it is set to `annotation`, you are already using 251 annotation-based tracking and are not impacted by this change. 252 253 ```sh 254 kubectl get cm argocd-cm -n argocd -o jsonpath='{.data.application\.resourceTrackingMethod}' 255 ``` 256 If you are using label-based tracking, it is also important to detect whether you have Applications that use `ApplyOutOfSyncOnly=true` syncOptions, as such Applications are likely to have orphan resources after switching to `annotation` tracking method and need to be synced explicitly right after the upgrade. 257 258 To detect whether you have such Applications, run: 259 ```sh 260 kubectl get applications.argoproj.io -A -o json | jq -r '.items[] | select(.spec.syncPolicy.syncOptions[]? == "ApplyOutOfSyncOnly=true") | .metadata.name' 261 ``` 262 263 #### Remediation 264 265 ##### Users with ApplyOutOfSyncOnly=true syncOptions and label-based tracking 266 267 For users with label-based tracking and Applications that have `ApplyOutOfSyncOnly=true` syncOptions, an explicit sync has to be run for those Applications after you upgrade. 268 Here is an example command, that syncs such an Application, it can be run after you [obtain a token](../../developer-guide/api-docs.md#authorization) to Argo CD API: 269 ```sh 270 curl -X POST -H "Authorization: Bearer $ARGOCD_TOKEN" -H "Content-Type: application/json" -d '{ 271 "name": "$YOUR_APP_NAME" 272 }' "http://$YOUR_ARGOCD_URL/api/v1/applications/$YOUR_APP_NAME/sync" 273 ``` 274 275 It is also possible to sync such an Applicaton using the UI, with `ApplyOutOfSyncOnly` option unchecked. However, currently, performing a sync without `ApplyOutOfSyncOnly` option is not possible using the CLI. 276 277 ##### Other users 278 279 For most users, it is safe to upgrade to Argo CD 3.0 and use annotation-based tracking. Labels will be replaced with 280 annotations on the next sync. Applications will not be marked as out-of-sync if labels are not present on the 281 resources. 282 283 !!! warning "Potential for orphaned resources" 284 285 There is a known edge case when switching from label-based tracking to annotation-based tracking that may cause 286 resources to be orphaned. If the first sync operation after switching to annotation-based tracking includes a 287 resource being deleted, Argo CD will fail to recognize that the resource is managed by the Application and will not 288 delete it. To avoid this edge case, it is recommended to perform a sync operation on your Applications, even if 289 they are not out of sync, so that orphan resource detection will work as expected on the next sync. 290 291 After upgrading to version 3.0, the Argo CD tracking annotation will only appear on an Application’s resources when 292 either a new Git commit is made or the Application is explicitly synced. 293 294 ##### Users who rely on label-based for resources that are not managed by Argo CD 295 Some users rely on label-based tracking to track resources that are not managed by Argo CD. They may set annotations 296 to have Argo CD ignore the resource as extraneous or to disable pruning. If you are using label-based tracking to track 297 resources that are not managed by Argo CD, you will need to construct tracking annotations instead of tracking labels 298 and apply them to the relevant resources. The format of the tracking annotation is: 299 300 ```yaml 301 argocd.argoproj.io/tracking-id: <app name>:<resource group>/<resource kind>:<resource namespace>/<resource name> 302 ``` 303 304 For cluster-scoped resources, the namespace is set to the value in the Application's `spec.destination.namespace` field. 305 306 !!! warning 307 308 Manually constructing and applying tracking labels and annotations is not an officially supported feature, and Argo 309 CD's behavior may change in the future. It is recommended to manage resources with Argo CD via GitOps. 310 311 #### Opting Out 312 313 If you are not ready to use annotation-based tracking, you can opt out of this change by setting the 314 `application.resourceTrackingMethod` field in the `argocd-cm` ConfigMap to `label`. There are no current plans to remove 315 label-based tracking. 316 317 ## Other changes 318 319 ### Using `cluster.inClusterEnabled: "false"` 320 321 When `cluster.inClusterEnabled: "false"` is explicitly configured, Applications currently configured to 322 sync on the in-cluster cluster will now be in an Unknown state, without the possibility to sync resources. 323 324 It will not be possible to create new Applications using the in-cluster cluster. When deleting existing 325 Application, it will not delete the previously managed resources. 326 327 It is recommended to perform any cleanup or migration to existing in-cluster Application before upgrading 328 when in-cluster is disabled. To perform cleanup post-migration, the in-cluster will need to be enabled temporarily. 329 330 ### Ignoring all status updates and high churn mutations 331 332 Argo CD manifest now contains a default configuration for `resource.customizations.ignoreResourceUpdates` in the `argocd-cm` 333 to exclude common resources that are often mutated in Kubernetes. These mutations are known to cause an unnecessary 334 load on Argo CD. When a watched resource is modified, Argo CD will always ignore the `.status` changes. 335 336 The default `resource.customizations.ignoreResourceUpdates` configurations can be overridden or removed in the configMap to preserve the v2 behavior. 337 338 ### Health status in the Application CR 339 340 The health status of each object used to be persisted under `/status` in the Application CR by default. 341 Any health churn in the resources deployed by the Application put load on the application controller. 342 Now, the health status is stored externally. 343 344 You can revert this behavior by setting the `controller.resource.health.persist` to `true` in the Argo CD 345 `argocd-cmd-params-cm.yaml` Config Map. 346 347 Example of a status field in the Application CR persisting health: 348 349 ```yaml 350 status: 351 health: 352 status: Healthy 353 lastTransitionTime: '2025-01-01T00:00:00Z' 354 resources: 355 - group: apps 356 health: 357 status: Healthy 358 kind: Deployment 359 name: my-app 360 namespace: foo 361 status: OutOfSync 362 version: v1 363 sync: 364 status: OutOfSync 365 ``` 366 367 Example of a status field in the Application CR _not_ persisting health: 368 369 ```yaml 370 status: 371 health: 372 status: Healthy 373 lastTransitionTime: '2025-01-01T00:00:00Z' 374 resourceHealthSource: appTree 375 resources: 376 - group: apps 377 kind: Deployment 378 name: my-app 379 namespace: foo 380 status: OutOfSync 381 version: v1 382 sync: 383 status: OutOfSync 384 ``` 385 386 #### Detection 387 388 1. Check the `argocd-cmd-params-cm.yaml` ConfigMap for `controller.resource.health.persist`. 389 390 If the value is empty or true, the health status is persisted in the Application CR. 391 392 ```sh 393 kubectl get cm argocd-cmd-params-cm -n argocd -o jsonpath='{.data.controller\.resource\.health\.persist}' 394 ``` 395 396 2. Check any Application CR for the `resourceHealthSource` field. 397 If you see a blank value, the health status is persisted in the Application CR. 398 399 ```sh 400 kubectl get applications.argoproj.io <my app> -n argocd -o jsonpath='{.status.resourceHealthSource}' 401 ``` 402 403 #### Migration 404 405 Any tools or CLI commands parsing the `.status.resources[].health` need to be updated to use the argocd cli/API to get the health status. 406 407 !!! note 408 The application list API (argocd app list) no longer returns the individual health status of resources. 409 410 ```sh 411 argocd app get <my app> -o json 412 ``` 413 414 ### Empty Environment Variables in Plugins 415 416 In Argo CD 3.0, empty environment variables are now passed to config management plugins. 417 418 ```yaml 419 apiVersion: argoproj.io/v1alpha1 420 kind: Application 421 spec: 422 source: 423 plugin: 424 name: example-plugin 425 env: 426 - name: VERSION 427 value: '1.2.3' 428 - name: DATA # Even though this is empty, it will be passed to the plugin as ARGOCD_ENV_DATA="". 429 value: '' 430 ``` 431 432 ### Ignoring resource updates configured in `ignoreDifferences` by default 433 434 By default, the existing system-level `ignoreDifferences` customizations will be added to ignore resource updates as well. 435 436 Logically, if differences to a field are configured to be ignored, there is no reason to generate the diff for the application 437 when that field changes. 438 439 To disable this behavior and preserve the v2 default, the `ignoreDifferencesOnResourceUpdates` can be set to false: 440 441 ```yaml 442 apiVersion: v1 443 kind: ConfigMap 444 metadata: 445 name: argocd-cm 446 data: 447 resource.compareoptions: | 448 ignoreDifferencesOnResourceUpdates: false 449 ``` 450 451 More details for ignored resource updates in the [Reconcile Optimization](../reconcile.md) documentation. 452 453 ### Ignoring status field from differences by default 454 455 By default, the compare options to ignore the status field has been changed from `crd` to `all` resources. 456 457 This means that differences won't be detected anymore for fields that are part of the status. 458 459 If you rely on the status field being part of your desired state, the `ignoreResourceStatusField` setting can be used to preserve the v2 default. 460 461 ```yaml 462 apiVersion: v1 463 kind: ConfigMap 464 metadata: 465 name: argocd-cm 466 data: 467 resource.compareoptions: | 468 ignoreResourceStatusField: crd 469 ``` 470 471 ### Removing default ignores of `preserveUnknownFields` for CRD 472 473 The `spec.preserveUnknownFields` has been deprecated in favor of `x-kubernetes-preserve-unknown-fields: true` in the CRD v1. 474 475 This means that CRD deployed with Argo CD containing `spec.preserveUnknownFields: false` will be out of sync. To address this problem, 476 the `preserveUnknownFields` field can be removed from the CRD spec. 477 478 Until this is completed, if you want your Application not to be out of sync, you can add the following configuration to the Application manifest. 479 480 ```yaml 481 spec: 482 ignoreDifferences: 483 - group: apiextensions.k8s.io 484 kind: CustomResourceDefinition 485 jsonPointers: 486 - /spec/preserveUnknownFields 487 ``` 488 489 You can also configure it globally in the `argocd-cm` ConfigMap. 490 491 ```yaml 492 resource.customizations.ignoreDifferences.apiextensions.k8s.io_CustomResourceDefinition: | 493 jsonPointers: 494 - /spec/preserveUnknownFields 495 ``` 496 497 More details for ignored resource updates in the [Diffing customization](../../user-guide/diffing.md) documentation. 498 499 ### Sanitized project API response 500 501 Due to security reasons ([GHSA-786q-9hcg-v9ff](https://github.com/argoproj/argo-cd/security/advisories/GHSA-786q-9hcg-v9ff)), 502 the project API response was sanitized to remove sensitive information. This includes 503 credentials of project-scoped repositories and clusters.