Personally I find ArgoCD works perfectly fine for kustomize and helm charts. Each tool is used in the following manner:
argoCD
for configuring kubernetes deployments, keeping Applications in sync with the state of the git repo (GitOps)helm
charts we use it to install typical third party charts such asargoCD
,external-secrets
,cert-manager
,istiod
,kyverno
, etc.kustomize
is great a customizing the different values in k8s config files between different environments.
Here is the Github repo with example that you can use to structure your project or at least as a reference.
From now own we will consider {env}
as dev
or prod
. you can call your environments whatever you want but those two are typical bare minimum environments in multiple companies.
Here is a top level of how I currently organize my projects:
```
├─ infra # Infrastructure as Code
└─ kubernetes # Code for configuring GKE and custom k8s resources
├─ kustomize
| ├─ ApplicationSet.{env}.yaml # The base AppSet per environment
| ├─ base # base k8s resources for all environments
| └─ overlays # kustomize overlays for customizing different environments
|
└─ helm
├─ charts # Helm charts downloaded by using `helm pull {REPO}/{NAME} --untar`
└─ values # values for customizing helm charts per environment
```
helm
subdirectory
Lets start with the helm/
subdirectory at available here. This subdir just contains dummy files. The important thing to notice here is that helm/charts/
is where you download and untar
the charts from third parties such as the argocd
helm chart, or the cert-manager
helm chart. From this chart you will copy and paste the values.yaml
file into helm/values/{chart}/{env}.values.yaml
, where env
will equal to a short prefix of your environment.
Including the helm charts in your repo has the following advantages:
- Allows you to easily compare your custom
helm/values/{chart}/{env}.values.yaml
file with the original untouchedvalues.yaml
file athelm/charts/{chart}
. This is extremely useful when you want to see what was changed for your environment. - Allows you to install directly from your own repo, which gives you more consistent builds, since you can't warranty third party repos to be available, to remain in same domain or to respect semantic versioning.
- Allows developers to check easily and fast what resources will be installed by the helm chart at path
helm/charts/{chart}
The main disadvantage is:
- Every time you add a new chart it increases the Pull Request size making it harder to code review.
In my opinion the advantages here clearly outweighs the disadvantages.
kustomize
subdirectory
Now lets proceed with subdir kustomize
available here.
At the top level you will notice we have our ArgoCD ApplicationSet
one per environment at path: kustomize/ApplicationSet.{env}.yaml
Each of these ApplicationSet
will configure two ArgoCD "App of Apps":
- helm-apps: App of Apps for all helm charts
- custom-apps: App of Apps for all non helm charts, basically everything that is your custom code.
# kustomize/ApplicationSet.dev.yaml
apiVersion: argoproj.io/v1alpha1
kind: ApplicationSet
metadata:
name: appset-dev
namespace: argocd
spec:
goTemplate: true # activate Go templating
generators:
- list:
elements:
# App of apps for all helm charts
- appName: helm-apps
appType: "helm"
path: kubernetes/kustomize/overlays/dev/helm-apps
syncWave: 0
# App of apps for all non helm charts
- appName: custom-apps
appType: "custom"
path: kubernetes/kustomize/overlays/dev/custom-apps
syncWave: 1
template:
# Application Metadata
metadata:
name: "{{.appName}}"
namespace: argocd
finalizers:
# needed so k8s resources are deleted when app is deleted as well
- resources-finalizer.argocd.argoproj.io
labels:
appType: "{{.appType}}"
annotations:
# order of deployment based on syncWave
argocd.argoproj.io/sync-wave: "{{.syncWave}}"
spec:
# spec same as it (spec field) would be in a
# typical ArgoCD Application.yaml, just replace
# generator values defined above.
project: default
source:
repoURL: git@github.com:my-org/my-example-repo.git
targetRevision: dev
path: "{{.path}}" # path must point to kustomize overlays
destination:
server: 'https://kubernetes.default.svc'
syncPolicy:
automated:
prune: true
selfHeal: true
allowEmpty: true
syncOptions:
- PruneLast=true
- CreateNamespace=true
- PrunePropagationPolicy=foreground
retry:
limit: 2
Lets continue diving into kustomize
sub directory it has two sub directories:
└─ kustomize
├─ base # base k8s resources for all environments
└─ overlays # kustomize overlays for customizing different
Both kustomize/base
and kustomize/overlays
have helm-apps
sub directory and a custom-apps
sub directory.
helm-apps
contains the argoCDApplication
configuration pointing tohelm/charts/{chart}
and thehelm/values/{env}.values.yaml
. Check base kustomization file for ArgoCDkustomize/base/helm-apps/argocd-app.yaml
and overlay fordev
environment atkustomize/overlays/dev/helm-apps/argocd-app.yaml
for reference of how this works.custom-apps
contains a simplebusybox
http server I have added for your reference make sure to check respectivebase
andoverlay
directories to understand how to structure custom resources.
Once you have everything in place you can scale this dir structure which works well for multiple of applications in same cluster. You might want to refactor and break down custom-apps
into smaller chunks once you reach a significant number of apps.