Contexte
En mettant en place FluxCD sur un cluster, je me suis retrouvé avec deux façons de déclarer ce que je veux déployer : Kustomization et HelmRelease. Les deux apparaissent dans quasiment tous les repos GitOps Flux, mais elles ne font pas la même chose.
Ce que j’ai appris
Kustomization (la CR Flux, pas l’objet Kustomize natif) applique des manifests YAML bruts depuis un GitRepository, en passant éventuellement par des overlays Kustomize. HelmRelease déploie un chart Helm depuis une HelmRepository/OCIRepository, avec ses values et son cycle de vie (install/upgrade/rollback) géré par le Helm controller. Une bonne partie des repos Flux utilisent en réalité les deux : une Kustomization qui, elle-même, applique des fichiers HelmRelease.yaml.
Détails
Deux ressources Flux distinctes, avec des controllers différents (kustomize-controller vs helm-controller) :
# Kustomization : applique des manifests bruts (ou un overlay Kustomize)
apiVersion: kustomize.toolkit.fluxcd.io/v1
kind: Kustomization
metadata:
name: apps-infra
namespace: flux-system
spec:
interval: 10m
path: ./clusters/prod/infra
prune: true
sourceRef:
kind: GitRepository
name: flux-system
---
# HelmRelease : déploie un chart Helm avec ses values
apiVersion: helm.toolkit.fluxcd.io/v2
kind: HelmRelease
metadata:
name: ingress-nginx
namespace: ingress-nginx
spec:
interval: 10m
chart:
spec:
chart: ingress-nginx
version: "4.11.x"
sourceRef:
kind: HelmRepository
name: ingress-nginx
values:
controller:
replicaCount: 2
Organisation qui fonctionne bien en pratique :
clusters/<env>/: une ou deuxKustomizationracines par cluster, qui pointent versapps/etinfra/.infra/<outil>/: un dossier par outil tiers packagé en chart (ingress-nginx, cert-manager, prometheus…) contenant saHelmRelease.yaml+ uneHelmRepository/OCIRepositoryassociée.apps/<app>/base+apps/<app>/overlays/<env>: manifests maison, gérés en Kustomize natif, appliqués via uneKustomizationFlux par environnement.
Règle simple : si ça vient d’un chart Helm publié par un tiers, HelmRelease ; si c’est du YAML qu’on écrit et qu’on veut décliner par environnement, Kustomization + overlays.
Que réconcilier après une modification ?
J’ai mis à jour la chart (nouvelle version dans HelmRelease.spec.chart.spec, ou nouvelle version poussée dans le repo Helm/OCI) → Flux ne voit la nouvelle version qu’au prochain polling de la HelmRepository/OCIRepository. Il faut réconcilier la source, puis le HelmChart généré, puis la HelmRelease — le flag --with-source fait les trois d’un coup :
flux reconcile helmrelease ingress-nginx -n ingress-nginx --with-source
J’ai mis à jour les values de la HelmRelease → ces values vivent dans le manifest Git de la HelmRelease, appliqué par une Kustomization Flux. Pas de nouvelle version de chart à récupérer, juste le commit à relire : réconcilier la Kustomization suffit, le helm-controller détecte le changement de génération sur la HelmRelease et relance l’upgrade tout seul :
flux reconcile kustomization apps-infra --with-source
Inutile d’appeler flux reconcile helmrelease dans ce second cas : dès que le nouveau commit est appliqué, le bump de génération suffit à déclencher le reconcile.
Une Kustomization par app ou par environnement ?
Plutôt une Kustomization par app (ou par composant infra) qu’une seule grosse par environnement. Avec une Kustomization par unité, chaque app a son propre health check, son propre prune et peut être reconciliée ou rollback indépendamment ; avec une seule Kustomization pour tout un env, un healthcheck qui échoue ou un prune: true mal maîtrisé impacte tout le lot d’un coup, et Flux ne peut pas ordonner finement les dépendances entre apps.
En pratique : une Kustomization par composant infra (cert-manager, ingress-nginx…) et une par app métier, reliées par dependsOn quand l’ordre compte (les apps dépendent souvent de l’infra) :
apiVersion: kustomize.toolkit.fluxcd.io/v1
kind: Kustomization
metadata:
name: apps-checkout
namespace: flux-system
spec:
interval: 10m
path: ./apps/checkout/overlays/prod
prune: true
dependsOn:
- name: infra-ingress-nginx
sourceRef:
kind: GitRepository
name: flux-system
Ne grouper que ce qui est vraiment couplé et doit vivre/mourir ensemble, pas juste “tout ce qui tourne dans cet environnement”.
Pourquoi c’est utile
Ça évite deux pièges : réécrire en YAML brut des charts tiers complexes (perdre les hooks, les valeurs par défaut du chart, les mises à jour de version), et à l’inverse forcer des manifests maison dans un chart Helm juste pour “faire comme Flux”. Séparer clairement infra/ (HelmRelease) et apps/ (Kustomization + overlays) rend le repo GitOps beaucoup plus lisible.
