The next gitops task for my home cluster was to make ArgoCD automatically install new applications when I add them to the configuration git repository.
In this post, I’m going to show how to set up an Argo CD git generator ApplicationSet and point it at a specific directory in a configuration repository.
- Part 1 - Setting up Talos with a Cilium CNI on proxmox
- Part 2 Add SSL to Kubernetes using Cilium, cert-manager and LetsEncrypt with domains hosted on Amazon Route 53
- Part 3 - Set up Secret Management with SOPS
- Part 4 - Back up your Talos etcd cluster to a SMB share
- Part 5 - Install ArgoCD
- Part 6 - Install MQTT into a k8s cluster
- Part 7 - Add an ArgoCD
gitgeneratorApplicationSet
Software Versions
Here are the versions of the software I used while writing this post.
| Software | Version |
|---|---|
argocd |
3.2.6 |
kubernetes |
1.34.1 |
talos |
1.12.4 |
Pre-requisites
To follow along with this post, you will need:
- A kubernetes cluster. I’m using the talos cluster from Part 1 - Setting up Talos with a Cilium CNI on proxmox, but this will work with any kubernetes cluster.
- A configuration git repository
- ArgoCD installed in your cluster. See Part 5 - Install ArgoCD for installation instructions
- If you’ve been following along with this series, you already have
helmandkubectl. Otherwise you canbrew installthem or follow the install instructions at helm.sh and kubectl.
Background
ArgoCD is great for managing things deployed into your cluster, but I don’t want to have to explicitly add a new app every time I add something to my cluster. Insetad, I want to be able to just merge a PR and have Argo detect the new App and install it, or update existing Apps.
To do this we’re going to create an Argo Git Generator ApplicationSet that watches a directory in our configuration repository.
Creating the Git Generator
Make a directory in your configuration repository - I used argocd/apps. For each new app, you’re going to create a subdirectory to contain your manifest files and a config.yaml that tells Argo what namespace to use and what cluster to deploy it to.
Here’s the ApplicationSet:
apiVersion: argoproj.io/v1alpha1
kind: ApplicationSet
metadata:
name: apps-git-generator
namespace: argocd
spec:
goTemplate: true
generators:
- git:
repoURL: 'https://github.com/USERNAME/CONFIGURATION_REPOSITORY.git'
revision: HEAD
requeueAfterSeconds: 60
files:
- path: "argocd/apps/**/config.yaml"
- path: "argocd/disabled/**/config.yaml"
exclude: true
template:
metadata:
# Accessing the 'app' block from config.yaml via dot notation
name: '{{ .app.name }}'
labels:
target-cluster: '{{ .app.clusterName }}'
spec:
# Logic: use app.project, fallback to "default" string
project: '{{ if .app.project }}{{ .app.project }}{{ else }}default{{ end }}'
source:
repoURL: 'https://github.com/USERNAME/CONFIGURATION_REPOSITORY.git'
targetRevision: HEAD
path: '{{ .path.path }}'
destination:
# Fallback logic for cluster URL
server: '{{ if .app.clusterUrl }}{{ .app.clusterUrl }}{{ else }}https://kubernetes.default.svc{{ end }}'
namespace: '{{ if .app.namespace }}{{ .app.namespace }}{{ else }}default{{ end }}'
syncPolicy:
automated:
prune: true
selfHeal: true
syncOptions:
- CreateNamespace=true
- PrunePropagationPolicy=foreground
- PruneLast=true
Add the ApplicationSet to your git configuration repository and then apply it to your cluster.
# Assumeing you're at the root of your configuration repository
git add argocd/infrastructure/argocd/git-generator-ApplicationSet.yaml && \
git commit argocd/infrastructure/argocd/git-generator-ApplicationSet.yaml -m 'Add git generator Argo ApplicationSet' && \
git push && \
kubectl apply -f argocd/infrastructure/argocd/git-generator-ApplicationSet.yaml
A couple of notes - this will only load manifests from directories that have a valid config.yaml file. The manifests will be installed into the namespace specified in config.yaml. This makes it easy to uninstall an app - git mv appdir/config.yaml appdir/disabled.config.yaml && git commit -m 'Disable appdir' appdir && git push
Here’s the format the ApplicationSet expects in config.yaml files:
app:
name: "name-of-app" # This will appear in as the app's name in Argo CD.
namespace: "namespace-you-want" # This will be created if necessary
# Use a label-friendly name
clusterName: sisyphus
# Use the full URL for the destination
clusterUrl: https://kubernetes.default.svc # I'm having argo manage the cluster it's installed in
Your configuration repository layout should look similar to this
repo-root -- argocd
\____ apps
\___ appdir
|___ config.yaml
|
|___ something.yaml
|
|___ something-else.yaml
Now that the ApplicationSet is installed, whenever you merge changes to your default branch, ArgoCD will detect them and apply them.
This ApplicationSet is configured to wait two minutes between between checks of your git repository. You can force an immediate check either with the Refresh Apps button on the ArgoCD applications page or by running argocd app get APPNAME --refresh.
Note - if you have multiple apps in the same git repository, refreshing any of them will cause Argo to deploy any changes to all of the other apps in that repository too.
No more manual app creation, just merge and apps automatically start up.
Summary
You have:
- Installed an Argo CD
gitgeneratorApplicationSetin your cluster so that you can add/update/remove applications from your cluster by making changes to your configuration repository withgit.