Skip to content

Commit 5db786c

Browse files
author
Martin Jackson
committed
Update blog post for clarity and rebase
1 parent 79adb50 commit 5db786c

File tree

1 file changed

+144
-0
lines changed

1 file changed

+144
-0
lines changed
Lines changed: 144 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,144 @@
1+
---
2+
date: 2023-11-17
3+
title: ArgoCD Config Management Plugins in Validated Patterns
4+
summary: Validated Patterns now support sidecar configmanagement plugins in ArgoCD
5+
author: Martin Jackson
6+
blog_tags:
7+
- openshift-platform-plus
8+
- devsecops
9+
- devops
10+
- patterns
11+
- pipelines
12+
- gitops
13+
aliases: /2023/11/17/argocd-cmps/
14+
---
15+
16+
# ArgoCD Configuration Management Plugins and the Validated Patterns Framework
17+
18+
## Problem
19+
20+
ArgoCD has a number of mechanisms for facilitating Kubernetes application deployments besides applying raw manifests.
21+
The most prominent mechanisms it uses are Kustomize (which is built into kubectl now) and Helm (which is an external tool still). If the user has additional needs for manifest generation that cannot be met by either of these tools, ArgoCD
22+
provides a mechanism called Configuration Management Plugins that allow for editing the manifest stream either in
23+
addition to or in lieu of Helm or Kustomize. This mechanism allows, for example, using both Helm and Kustomize on the
24+
same template files and/or bases at the same time. If the user needs a custom tool, such as [PolicyGen](https://cloud.redhat.com/blog/generating-governance-policies-using-kustomize-and-gitops) to be involved in generating Kubernetes
25+
manifests, this feature enables its use. Similarly, another use for this feature is to enable the
26+
[ArgoCD Vault Plugin](https://github.com/argoproj-labs/argocd-vault-plugin), which works by substituting specific tags
27+
in manifests. This allows users to avoid storing secrets directly in git repositories, which is one of the key needs
28+
of an operational GitOps strategy.
29+
30+
## Implementation
31+
32+
The implementation in the Validated Patterns framework is meant to conform to the mechanism described [here](https://argo-cd.readthedocs.io/en/stable/operator-manual/config-management-plugins/) upstream. Note that the plugin configuration
33+
actually must live inside the container - either "baked in" to the sidecar image, or injected via configmap. The
34+
framework supports both options.
35+
36+
Previously, the Validated Patterns `clusterGroup` chart would create three plugins using the CMP 1.0 framework. Only one
37+
of these was ever used (to the best of our knowledge), `helm-with-kustomize` in the [Industrial Edge](https://github.com/validatedpatterns/industrial-edge) pattern. As of this publication, the kustomize integration is no longer necessary -
38+
the code was refactored to operate directly on helm value files instead of creating dynamic kustomize patches.
39+
40+
In the `clusterGroup` chart (which is the heart of the Validated Patterns framework), there is a new key, `argoCD`,
41+
that can optionally be used to implement an arbitrary number of CMP 2.0-style plugins.
42+
43+
For example:
44+
45+
```yaml
46+
argoCD:
47+
initContainers: []
48+
configManagementPlugins:
49+
- name: helm-with-kustomize
50+
image: quay.io/hybridcloudpatterns/utility-container:latest
51+
imagePullPolicy: Always
52+
pluginArgs:
53+
- '--loglevel=debug'
54+
pluginConfig: |
55+
apiVersion: argoproj.io/v1alpha1
56+
kind: ConfigManagementPlugin
57+
metadata:
58+
name: helm-with-kustomize
59+
spec:
60+
preserveFileMode: true
61+
init:
62+
command: ["/bin/sh", "-c"]
63+
args: ["helm dependency build"]
64+
generate:
65+
command: ["/bin/bash", "-c"]
66+
args: ["helm template . --name-template ${ARGOCD_APP_NAME:0:52}
67+
-f $(git rev-parse --show-toplevel)/values-global.yaml
68+
-f $(git rev-parse --show-toplevel)/values-{{ .Values.clusterGroup.name }}.yaml
69+
--set global.repoURL=$ARGOCD_APP_SOURCE_REPO_URL
70+
--set global.targetRevision=$ARGOCD_APP_SOURCE_TARGET_REVISION
71+
--set global.namespace=$ARGOCD_APP_NAMESPACE
72+
--set global.pattern={{ .Values.global.pattern }}
73+
--set global.clusterDomain={{ .Values.global.clusterDomain }}
74+
--set global.hubClusterDomain={{ .Values.global.hubClusterDomain }}
75+
--set global.localClusterDomain={{ coalesce .Values.global.localClusterDomain .Values.global.hubClusterDomain }}
76+
--set clusterGroup.name={{ .Values.clusterGroup.name }}
77+
--post-renderer ./kustomize"]
78+
```
79+
80+
`initContainers` is an array of initContainers that will be added to the repo-server pod. In most cases you do not need
81+
to do this. (By default, an init container in the repo-server pod will copy the argocd binary into /var to run as the
82+
cmp server for the container. This behavior will happen even if you specify nothing here, which is the default. Since
83+
the argocd kind supports this, so do we.)
84+
85+
`configManagementPlugins` is an array. Each element will add one sidecar plugin to the GitOps repo-server pod the
86+
clusterGroup chart controls. In the `argoCD` instance it primarily adds elements to the `sidecarContainers` property.
87+
88+
The `name` element is the name of the plugin - this is how applications can specifically request that ArgoCD/GitOps
89+
process the manifests. This name is also used to compose a configmap name if the user specifies the pluginConfig string.
90+
91+
The `image` element is the image the sidecar will use. The repo-server default initContainer will copy the argocd server
92+
into the image; the user must supply any external binaries though.
93+
94+
The `imagePullPolicy` element is optional. It defaults to `Always` if not specified.
95+
96+
The `pluginArgs` element is optional, and is an array. If omitted, it does not have a default. It can be used to turn
97+
up the debug level of the cmp-server process inside the container.
98+
99+
The `pluginConfig` element is a string, and is optional. If specified, it will be passed through the Helm `tpl`
100+
function, so any recognized Helm variables or functions will be rendered. The chart will arrange for this string to
101+
be injected into the sidecar as `plugin.yaml` via configmap. While it is possible to bake this into the sidecar, changes
102+
to the plugin.yaml would require the sidecar image to be rebuilt and redeployed, and the repo-server pod restarted. It
103+
is a documented method in the upstream documentation, so the framework allows it.
104+
105+
Please note that the `preserveFileMode` setting in the example plugin config is not yet supported in ArgoCD 2.6/GitOps
106+
Operator 1.8, but is in ArgoCD 2.8/GitOps Operator 1.10. The main use for this property is to call executables inside
107+
the repository as post-renderers (as this example does). Please be aware that there are security concerns associated
108+
with doing this. The suggested practice is to ship any executable programs (including shell scripts, Python scripts
109+
etc.) as part of the sidecar image.
110+
111+
## History
112+
113+
### How CMPs came into the Validated Patterns Framework
114+
115+
In the beginning, the Validated Patterns framework had not yet developed its preference (though not, as occasionally
116+
reported, an insistence) for Helm, and most of the existing gitops repositories were based on kustomize. The first
117+
pattern implemented with the framework was [industrial-edge](https://github.com/validatedpatterns/industrial-edge).
118+
This was based on the [MANUela](https://github.com/sa-mw-dach/manuela) demo, which was completely based on kustomize.
119+
120+
We developed the Validated Patterns framework, to some degree, around what the industrial-edge pattern needed. One of
121+
the things we wanted to do was to find ways to allow the framework to be used to instantiate a demo without requiring
122+
the user to configure things that could be automatically discovered from the environment. So - the user has to
123+
configure their own credentials for connecting to git forges and container registries; but the domain the OpenShift
124+
cluster that will be running the demo can be discovered, so rather than requiring that to be configured, we provided a
125+
mechanism that extracted that information and stored it as a Helm variable. Meanwhile, the components of industrial-edge
126+
that used this information had very opinionated kustomize-based deployment mechanisms and workflows to update them.
127+
We did not want to change this mechanism at the time, so it was better for us to work out how to apply Helm templating
128+
on top of a set of of manifests that kustmomize had already rendered. The CMP 1.0 framework was suitable for this, and
129+
fairly straightforward to use, so we did. However, we did not, at that time, put any thought into parameterizing the
130+
use of config management plugins; making too radical a change to how the repo server worked would have difficult, and
131+
would have required injecting a new (and unsupported) image into a product; not something to be undertaken lightly.
132+
Finally, it was unclear that there would be significant demand for such a feature in the framework.
133+
134+
### Questions that arose around CMPs in the Validated Patterns Framework
135+
136+
Of course, there is some common wisdom about making assumptions in situations like this. Two major factors caused us to
137+
revisit the question of config management plugins in the framework. First, one of our prospective users clearly had an
138+
architectural need of the framework that was best met using config management plugins; and upstream, ArgoCD had come up
139+
with an entirely new mechanism for implementing CMPs using sidecars. This took the question of rebuilding or
140+
substituting the repo-server image off the table; but required some changes in the framework to accomodate the new
141+
mechanism. Secondly, we learned that the existing plugin framework had been deprecated and was at risk of being removed. It was actually removed upstream in ArgoCD 2.9.
142+
143+
Now that the framework supports user-specified sidecar plugins, we would love to hear your feedback. Does our adoption
144+
of CMP 2.0 meet your needs? Please engage with us in our [upstream issue tracker](https://github.com/validatedpatterns/common/issues).

0 commit comments

Comments
 (0)