github.com/argoproj/argo-cd/v2@v2.10.5/docs/proposals/application-name-identifier.md (about)

     1  ---
     2  title: Change the way application resources are identified
     3  authors:
     4    - "@jannfis"
     5  sponsors:
     6    - TBD
     7  reviewers:
     8    - TBD
     9  approvers:
    10    - TBD
    11  
    12  creation-date: 2021-06-07
    13  last-updated: 2021-06-07
    14  ---
    15  
    16  # Change the way application resources are identified
    17  
    18  This is a proposal to introduce the tracking method settings that allows using
    19  an annotation as the application identifier instead of the application instance label.
    20  This will allow application names longer than 63 characters and solve issues caused by
    21  copying `app.kubernetes.io/instance` label. As an additional goal, we propose to introduce an
    22  installation ID that will allow multiple Argo CD instances to manage resources
    23  on the same cluster.
    24  
    25  
    26  ## Summary
    27  
    28  Argo CD identifies resources it manages by setting the _application instance
    29  label_ to the name of the managing `Application` on all resources that are
    30  managed (i.e. reconciled from Git). The default label used is the well-known
    31  label `app.kubernetes.io/instance`.
    32  
    33  This proposal suggests to introduce the `trackingMethod` setting that allows
    34  controlling how applicaton resources are identified and allows switching to
    35  using the annotation instead of `app.kubernetes.io/instance` label.
    36  
    37  ## Motivation
    38  
    39  The main motivation behind this change is to solve the following known issues:
    40  
    41  * The Kubernetes label value cannot be longer than 63 characters. In large scale
    42    installations, in order to build up an easy to understand and
    43    well-formed naming schemes for applications managed by Argo CD, people often
    44    hit the 63 character limit and need to define the naming scheme around this
    45    unnecessary limit.
    46  
    47  * Popular off-the-shelf Helm charts often add the `app.kubernetes.io/instance` label
    48    to the generated resource manifests. This label confuses Argo CD and makes it think the
    49    resource is managed by the application.
    50  
    51  * Kubernetes operators often create additional resources without creating owner reference
    52    and copy the `app.kubernetes.io/instance` label from the application resource. This is
    53    also confusing Argo CD and makes it think the resource is managed by the application.
    54  
    55  An additional motivation - while we're at touching at application instance
    56  label - is to improve the way how multiple Argo CD instances could manage
    57  applications on the same cluster, without requiring the user to actually
    58  perform instance specific configuration.
    59  
    60  ### Goals
    61  
    62  * Allow application names of more than 63 characters
    63  
    64  * Prevent confusion caused by copied/generated `app.kubernetes.io/instance` label
    65  
    66  * Keep having a human-readable way to identify resources that belong to a
    67    given Argo CD application
    68  
    69  * As a stretch-goal, allow multiple Argo CD instances to manage resources on
    70    the same cluster without the need for configuring application instance label
    71    key (usually `app.kubernetes.io/instance`)
    72  
    73  ### Non-Goals
    74  
    75  * Change the default name of the application instance label
    76  
    77  ## Proposal
    78  
    79  We propose introducing a new setting `trackingMethod` that allows to control
    80  how application resources are identified. The `trackingMethod` setting takes
    81  one of the following values:
    82  
    83  * `label` (default) - Argo CD keep using the `app.kubernetes.io/instance` label.
    84  * `annotation+label` - Argo CD keep adding `app.kubernetes.io/instance` but only
    85    for informational purposes: label is not used for tracking, value is truncated if
    86    longer than 63 characters. The `app.kubernetes.io/instance` annotation is used
    87    to track application resources.
    88  * `annotation` - Argo CD uses the `app.kubernetes.io/instance` annotation to track
    89    application resources.
    90  
    91  The `app.kubernetes.io/instance` attribute values includes the application name,
    92  resources identifier it is applied to, and optionally the Argo CD installation ID:
    93  
    94  The application name allows to identify the application that manages the resource. The
    95  resource identifier prevents confusion if an operation copies the
    96  `app.kubernetes.io/instance` annotation to another resource. Finally optional
    97  installation ID allows separate two Argo CD instances that manages resources in the same cluster.
    98  
    99  The `trackingMethod` setting should be available at the system level and the application level to
   100  allow the smooth transition from the old `app.kubernetes.io/instance` label to the new tracking method.
   101  Using the app leverl settings users will be able to first switch applications one by one to the new tracking method
   102  and prepare for the migration. Next system level setting can be changed to `annotation` or `annotation+label`
   103  and not-migrated applications can be configured to use `labels` using application level setting.
   104  
   105  
   106  ### Use cases
   107  
   108  Add a list of detailed use cases this enhancement intends to take care of.
   109  
   110  #### Use case 1: Allow for more than 63 characters in application name
   111  
   112  As a user, I would like to be able to give my applications names with arbitrary
   113  length, because I want to include identifiers like target regions and possibly
   114  availability zones, the environment and possibly other identifiers (e.g. a team
   115  name) in the application names. The current restriction of 63 characters is not
   116  sufficient for my naming requirements.
   117  
   118  #### Use case 2: Allow for retrieving all resources using Kubernetes
   119  
   120  As an administrator, I want to enable my users to use more than 63 characters
   121  in their application names, but I still want to be able to retrieve all of the
   122  resources managed by that particular application using Kubernetes mechanisms,
   123  e.g. a label selector as in the following example:
   124  
   125  ```
   126  kubectl get deployments -l app.kubernetes.io/instance=<application> --all-namespaces
   127  ```
   128  
   129  #### Use case 3: Multiple Argo CD instances managing apps on same cluster
   130  
   131  I also want to be able to see which application and Argo CD instance is the
   132  one in charge of a given resource.
   133  
   134  ### Implementation Details/Notes/Constraints [optional]
   135  
   136  #### Include resource identifies in the `app.kubernetes.io/instance` annotation
   137  
   138  The `app.kubernetes.io/instance` annotation might be accidently added or copied
   139  same as label. To prevent Argo CD confusion the annotation value should include
   140  the identifier of the resource annotation was applied to. The resource identifier
   141  includes the group, kind, namespace and name of the resource. It is proposed to use `;`
   142  to separate identifier from the application name.
   143  
   144  ```yaml
   145  annotations:
   146      app.kubernetes.io/instance: <application-name>;<group>/<kind>/<namespace>/<name>
   147  ```
   148  
   149  Example:
   150  
   151  ```yaml
   152  apiVersion: apps/v1
   153  kind: Deployment
   154  metadata:
   155    name: my-deployment
   156    namespace: default
   157    annotations:
   158      app.kubernetes.io/instance: my-application;apps/Deployment/default/my-deployment
   159  ```
   160  
   161  #### Allow multiple Argo CD instances manage applications on same cluster
   162  
   163  As of today, to allow two or more Argo CD instances with a similar set of
   164  permissions (e.g. cluster-wide read access to resources) manage applications
   165  on the same cluster, users would have to configure the _application instance
   166  label key_ in the Argo CD configuration to a unique value. Otherwise, if an
   167  application with the same name exists in two different Argo CD installations,
   168  both would claim ownership of the resources of that application.
   169  
   170  We do see the need for preventing such scenarios out-of-the-box in Argo CD.
   171  For this, we do suggest the introduction of an _installation ID_ in the
   172  form of a standard _GUID_.
   173  
   174  This GUID would be generated once by Argo CD upon startup, and is persisted in
   175  the Argo CD configuration, e.g. by storing it as `installationID` in the
   176  `argocd-cm` ConfigMap. The GUID of the installation would need to be encoded
   177  in some way in the resources managed by that Argo CD instance.
   178  
   179  We suggest using a dedicated annotation to store the GUID and modify Argo CD so that it matches _both_, the app
   180  instance key and the GUID to determine whether a resource is managed by
   181  this Argo CD instance. Given above mentioned GUID, this may look like the
   182  following on a resource:
   183  
   184    ```yaml
   185    apiVersion: v1
   186    Kind: Secret
   187    metadata:
   188      name: some-secret
   189      namespace: some-namespace
   190      annotations:
   191        app.kubernetes.io/instance: my-application;/Secret/some-namespace/some-secret
   192        argo-cd.argoproj.io/installation-id: 61199294-412c-4e78-a237-3ebba6784fcd
   193    ```
   194  
   195  The user should be able to opt-out of this feature by setting the `installationID` to an empty string.
   196  
   197  ### Security Considerations
   198  
   199  We think this change will not have a direct impact on the security of Argo CD
   200  or the applications it manages. 
   201  
   202  ### Risks and Mitigations
   203  
   204  The proposal assumes that user can keep adding `app.kubernetes.io/instance` label
   205  to be able to retrieve resources using `kubectl get -l app.kubernetes.io/instance=<application>` command.
   206  However, Argo CD is going to truncate the value of the label if it is longer than 63 characters. There is
   207  a small possibility that there are several applications with the same first 63 characters in the name. This
   208  should be clearly stated in documentation.
   209  
   210  ### Upgrade / Downgrade Strategy
   211  
   212  Upgrading to a version that implements this proposal should be seamless, as
   213  previously injected labels will not be removed and additional annotations will
   214  be applied to the resource. E.g. consider following resource in Git, that will
   215  be synced as part of an application named `some-application`. In Git, the
   216  resource looks like follows:
   217  
   218  ```yaml
   219  apiVersion: v1
   220  Kind: Secret
   221  metadata:
   222    name: some-secret
   223    namespace: some-namespace
   224  ```
   225  
   226  When synced with the current incarnation of Argo CD, Argo CD would inject the
   227  application instance label and once the resource is applied in the cluster, it
   228  would look like follows:
   229  
   230  ```yaml
   231  apiVersion: v1
   232  Kind: Secret
   233  metadata:
   234    name: some-secret
   235    namespace: some-namespace
   236    labels:
   237      app.kubernetes.io/instance: some-application
   238  ```
   239  
   240  Once Argo CD is updated to a version implementing this proposal, the resource
   241  would be rewritten to look like the following:
   242  
   243  ```yaml
   244  apiVersion: v1
   245  Kind: Secret
   246  metadata:
   247    name: some-secret
   248    namespace: some-namespace
   249    labels:
   250      app.kubernetes.io/instance: some-application
   251    annotations:
   252      app.kubernetes.io/instance: my-application;/Secret/some-namespace/some-secret
   253      argo-cd.argoproj.io/installation-id: 61199294-412c-4e78-a237-3ebba6784fcd
   254  ```
   255  
   256  On a rollback to a previous Argo CD version, this change would be reverted
   257  and the resource would look like the first shown example above.
   258  
   259  ## Drawbacks
   260  
   261  We do see some drawbacks to this implementation:
   262  
   263  * This change would trigger a re-sync of each and every managed resource, which
   264    may result in unexpected heavy load on Argo CD and the cluster at upgrade
   265    time. The workaround is an ability to opt-out of this as a default and enable it
   266    on application basis.
   267  
   268  ## Alternatives
   269  
   270  * Enabling application names longer than 63 characters could also be done
   271    by using the hashed value of the application name and additional metadata as a label.
   272    The disadvantage of this approach is that hash value is not human friendly. In particular,
   273    it is difficult to retrieve application manifests using `kubectl get -l app.kubernetes.io/instance=<application>`.