GitOps
This page helps you keep Goiabada’s Kubernetes files in a Git repository that Argo CD or Flux applies.
Set up the repository
Section titled “Set up the repository”-
Generate each environment’s files in a directory of its own, running the setup wizard once per environment. Each one answers its own URLs, namespace and database, so each gets a manifest of its own rather than patches over another’s:
goiabada-deploy/├── components/│ └── common/│ └── kustomization.yaml├── production/│ ├── goiabada-setup.yaml│ ├── goiabada-k8s.yaml│ ├── goiabada-secrets.sealed.yaml│ ├── goiabada-encryption-key.sealed.yaml│ └── kustomization.yaml└── staging/└── ...Commit
goiabada-setup.yaml, the answers file, andgoiabada-k8s.yaml. Never commitgoiabada-secrets.yaml: add it to.gitignore. -
Put the Secrets in the repository sealed, or leave them out, as Secrets describes: a sealed file per Secret with SealedSecrets, an
ExternalSecretper Secret with the External Secrets Operator, or Secrets created from your terminal, which the repository then leaves out. Sealed files andExternalSecrets let the GitOps tool rebuild an environment from the repository alone. -
Write the patches every environment shares in a Kustomize component. This one raises the auth server’s CPU limit, as Resource limits suggests for a higher sign-in peak. Save this as
components/common/kustomization.yaml:apiVersion: kustomize.config.k8s.io/v1alpha1kind: Componentpatches:- target:kind: Deploymentname: goiabada-authserverpatch: |-apiVersion: apps/v1kind: Deploymentmetadata:name: goiabada-authserverspec:template:spec:containers:- name: authserverresources:limits:cpu: "1"The
targetselects the Deployment by kind and name alone, so the patch fits every environment’s namespace. A patch without one matches only a Deployment in the namespace its ownmetadatanames, and Kustomize refuses it when it names none. -
Write each environment’s kustomization. This one also caps the auth server’s database pool at 10 connections, for a smaller database. Save this as
production/kustomization.yaml:apiVersion: kustomize.config.k8s.io/v1beta1kind: Kustomizationresources:- goiabada-k8s.yaml- goiabada-secrets.sealed.yaml- goiabada-encryption-key.sealed.yamlcomponents:- ../components/commonpatches:- target:kind: Deploymentname: goiabada-authserverpatch: |-apiVersion: apps/v1kind: Deploymentmetadata:name: goiabada-authserverspec:template:spec:containers:- name: authserverenv:- name: GOIABADA_DB_MAX_OPEN_CONNSvalue: "10"Leave the sealed files out of
resourcesif you create the Secrets another way. Check what it builds before you commit it:Terminal window kubectl kustomize production -
Point your GitOps tool at each environment’s directory, with Argo CD or Flux below. These steps are tested with Argo CD v3.5.6 and Flux v2.10.0.
Regenerate or patch
Section titled “Regenerate or patch”A setting the wizard asks, other than a password, belongs in the answers file, and everything else in a patch:
| Change | How |
|---|---|
| URLs, namespace, the database’s host, port, name, user and TLS, routing, the HTTPS certificates, NetworkPolicies, mesh ports, the auth server’s replicas, metrics, images, labels and annotations, the rate limiter | Regenerate with the new answer |
| Resources, node selectors, tolerations, affinity, the admin console’s replicas, a server setting the wizard doesn’t ask | A patch in the environment’s kustomization, or in the component when every environment shares it |
| A new Goiabada release | Regenerate every environment with the new release’s wizard |
| A password or key | Change it in the Secrets, as Rotate secrets describes, and in their source when something else owns them |
To regenerate, run the wizard over the environment’s answers file, from its directory, with the answer that changes. It leaves the Secrets as they are:
cd production./goiabada-setup-linux-amd64 --answers=goiabada-setup.yaml --keep-secrets --authserver-replicas=3git diffReview the diff, commit and push, and the GitOps tool applies it. The answers file records the new answer, so the next regeneration keeps it. Run it again on a deployment has the rest.
Set a server setting the wizard doesn’t ask, such as GOIABADA_DB_MAX_OPEN_CONNS, as an env entry of the container, as the kustomization above does, rather than by patching the ConfigMap. It overrides the ConfigMap’s value of the same name, and applying it rolls the pods. A patched ConfigMap doesn’t roll them: the pods keep the old value until something restarts them.
A change made in the cluster by hand, such as a kubectl scale, doesn’t last: Argo CD’s self-heal reverts it at once, and Flux at its next reconciliation. Make the change in the repository.
Argo CD
Section titled “Argo CD”One Application per environment, in the namespace Argo CD runs in, here production’s. Register the repository’s credentials as Argo CD’s documentation describes:
apiVersion: argoproj.io/v1alpha1kind: Applicationmetadata: name: goiabada-production namespace: argocdspec: project: default source: repoURL: https://git.example.com/platform/goiabada-deploy.git targetRevision: main path: production destination: server: https://kubernetes.default.svc namespace: goiabada syncPolicy: automated: prune: true selfHeal: trueArgo CD builds the kustomization itself. prune deletes what leaves the manifest, such as the NetworkPolicies when you regenerate with them turned off, and selfHeal reverts changes made by hand. An Application pointed at a deployment you applied with kubectl takes its objects over, and rolls the pods once if its patches change them.
A GitRepository for the repository, and one Kustomization per environment, in the namespace Flux runs in. The secretRef names a Secret holding the repository’s credentials, as Flux’s documentation describes:
apiVersion: source.toolkit.fluxcd.io/v1kind: GitRepositorymetadata: name: goiabada-deploy namespace: flux-systemspec: interval: 1m url: https://git.example.com/platform/goiabada-deploy.git ref: branch: main secretRef: name: goiabada-deploy-auth---apiVersion: kustomize.toolkit.fluxcd.io/v1kind: Kustomizationmetadata: name: goiabada-production namespace: flux-systemspec: interval: 10m sourceRef: kind: GitRepository name: goiabada-deploy path: ./production prune: true wait: true timeout: 5mprune deletes what leaves the manifest, and wait holds the Kustomization not ready until every object it applied is, the pods included. To apply a commit without waiting for the intervals:
flux reconcile kustomization goiabada-production --with-sourceDeleting an environment
Section titled “Deleting an environment”When you answered yes to creating the namespace, the manifest declares it, and the GitOps tool owns it with everything else. Deleting a Flux Kustomization that prunes, or an Argo CD Application with cascading deletion, then deletes the namespace and everything in it, Secrets you created by hand included.
Sealed files and ExternalSecrets come back with the rest when the environment is applied again. Secrets created from your terminal don’t: create them again, with the same values, as Secrets explains. For a namespace that must outlive the GitOps tool’s objects, answer no to creating it, and create it outside the repository. To switch an environment that already runs, never just regenerate: follow Switching a running deployment first, or pruning deletes the namespace.
The Internal TLS guide in a repository
Section titled “The Internal TLS guide in a repository”The Internal TLS guide’s files go in the environment’s directory, beside its kustomization, and its patches in that kustomization’s patches. They name the namespace goiabada, so they belong to the environment deployed there rather than to the component.