Expert Chapitre 37-38 / 19

GitOps : Git comme état désiré (ArgoCD) & Flux : la réconciliation continue

Comprendre le paradigme GitOps où un dépôt Git devient la source unique de l'état désiré, et découvrir comment ArgoCD et Flux réconcilient en continu le cluster avec cet état — avec du YAML et kubectl.

GitOps : Git comme état désiré (ArgoCD)

L’idée en une phrase

Le GitOps élève un dépôt Git au rang de source unique de l’état désiré d’un cluster : un contrôleur embarqué compare en permanence les manifestes versionnés dans Git avec les ressources réelles du cluster, puis réconcilie tout écart — la même boucle observe → diff → agit que celle d’un controller Kubernetes, appliquée cette fois à l’ensemble de l’infrastructure déclarative.

Analogie : Considérons un architecte qui dépose les plans définitifs d’un bâtiment dans un coffre-fort notarié. Chaque matin, un maître d’œuvre compare l’avancement réel du chantier avec les plans du coffre. Si une cloison manque ou a été déplacée, il la reconstruit conformément au plan — sans attendre d’instruction supplémentaire. Le coffre-fort est le dépôt Git (immuable, auditable), le chantier est le cluster, et le maître d’œuvre est le contrôleur GitOps.

Points clés

  • Le principe fondateur du GitOps repose sur quatre piliers formulés par l’OpenGitOps working group : l’infrastructure est déclarative, l’état désiré est versionné et immuable dans Git, les changements sont appliqués automatiquement par un agent, et l’agent réconcilie en continu l’état réel avec l’état désiré. Aucune modification manuelle via kubectl apply n’est censée contourner ce flux.
  • ArgoCD implémente ce paradigme sous forme d’un contrôleur déployé dans le cluster. Il surveille un ou plusieurs dépôts Git (via polling ou webhook) et compare le contenu du dépôt (l’état désiré) avec les ressources effectivement présentes dans le cluster (l’état réel). L’écart est affiché dans une interface web et peut être réconcilié automatiquement ou après approbation manuelle.
  • ArgoCD modélise chaque déploiement sous la forme d’une CR Application. Cette CR déclare le dépôt Git source, le chemin des manifestes, le cluster cible et la politique de synchronisation. Le contrôleur d’ArgoCD réconcilie cette CR exactement comme n’importe quel Operator réconcilie sa CR — la boucle est la même, le domaine change.
  • Le statut d’une Application ArgoCD reflète l’écart entre Git et le cluster : Synced (état réel = état désiré), OutOfSync (écart détecté), Degraded (ressources en échec). Ce status est la manifestation directe du diff calculé par la boucle de réconciliation.
  • La politique auto-sync avec self-heal active la réconciliation automatique : toute dérive du cluster (suppression manuelle d’un pod, modification d’un ConfigMap via kubectl edit) est corrigée sans intervention humaine. Sans self-heal, ArgoCD se contente de signaler l’écart.

Exemple concret

Une équipe gère un microservice payment-api déployé dans un namespace production. Le Deployment, le Service et le ConfigMap sont versionnés dans un dépôt Git infra-k8s, dans le répertoire apps/payment-api/. ArgoCD surveille ce répertoire. À t₀, un opérateur modifie le ConfigMap directement dans le cluster via kubectl edit pour changer un flag de feature. ArgoCD détecte l’écart lors de son prochain cycle de réconciliation (toutes les 3 minutes par défaut). Avec self-heal activé, ArgoCD réapplique le ConfigMap tel qu’il existe dans Git — la modification manuelle est annulée. L’opérateur constate la correction et comprend que toute modification durable doit passer par un commit dans le dépôt Git. Le dépôt Git reste la source de vérité.

Comparaison — déploiement CI/CD classique vs GitOps

CritèreCI/CD push (pipeline applique)GitOps pull (agent réconcilie)
Qui applique les manifestesLe pipeline CI/CD (externe au cluster)Un contrôleur dans le cluster
Source de véritéLe pipeline au moment de l’exécutionLe dépôt Git en permanence
Détection de dériveAucune — l’état peut diverger entre deux pipelinesContinue — l’agent compare à chaque cycle
Accès cluster requisLe pipeline a besoin de credentials clusterSeul l’agent interne a accès — surface d’attaque réduite
RollbackRelancer un ancien pipeline ou écrire un scriptgit revert — l’agent réconcilie automatiquement

Code YAML — déclaration d’une Application ArgoCD

# application.yaml — l'Application est une CR qui décrit l'état désiré d'un déploiement
apiVersion: argoproj.io/v1alpha1
kind: Application
metadata:
  name: payment-api
  namespace: argocd                  # ArgoCD surveille ses CR dans ce namespace
spec:
  project: default
  source:
    repoURL: https://github.com/acme/infra-k8s.git
    targetRevision: main             # la branche Git = la version de l'état désiré
    path: apps/payment-api           # répertoire contenant les manifestes YAML
  destination:
    server: https://kubernetes.default.svc
    namespace: production
  syncPolicy:
    automated:
      prune: true                    # supprimer les ressources absentes de Git
      selfHeal: true                 # corriger toute dérive détectée dans le cluster
    syncOptions:
      - CreateNamespace=true

Code bash — observer la réconciliation ArgoCD

# Vérifier le statut de synchronisation de l'Application
kubectl get application payment-api -n argocd \
  -o jsonpath='{.status.sync.status}'
# Synced

# Provoquer une dérive : modifier un ConfigMap manuellement
kubectl edit configmap payment-config -n production
# (modifier une clé et sauvegarder)

# Après le prochain cycle de réconciliation (~3 min) :
kubectl get application payment-api -n argocd \
  -o jsonpath='{.status.sync.status}'
# Synced   ← ArgoCD a réconcilié : la modification manuelle est annulée

# Consulter l'historique de synchronisation
kubectl get application payment-api -n argocd \
  -o jsonpath='{.status.history[*].revision}'
# abc1234 def5678   ← chaque sync est liée à un commit Git

Piège courant : « GitOps remplace la CI/CD » est un raccourci trompeur. GitOps remplace la partie livraison (CD) — le déploiement des manifestes dans le cluster. La partie intégration (CI) — build de l’image, exécution des tests, publication dans un registre — reste nécessaire et pilotée par un pipeline classique. Le pipeline CI pousse une nouvelle image taguée dans le registre, met à jour la référence d’image dans le dépôt Git, et le contrôleur GitOps réconcilie le cluster avec ce nouvel état désiré.


Flux : la réconciliation continue

L’idée en une phrase

Flux implémente le GitOps comme un ensemble de contrôleurs spécialisés déployés dans le cluster — chacun réconciliant un aspect précis (sources Git, dépôts Helm, manifestes Kustomize) — incarnant le principe Kubernetes de composition de boucles de réconciliation indépendantes plutôt qu’un contrôleur monolithique.

Analogie : Considérons une chaîne logistique où chaque entrepôt régional dispose de son propre gestionnaire de stock. Le gestionnaire de Bordeaux surveille les niveaux de son entrepôt et passe des commandes au fournisseur pour maintenir le stock cible. Celui de Lyon fait de même, indépendamment. Un coordinateur central publie le catalogue et les niveaux cibles, mais chaque gestionnaire réconcilie localement. Flux fonctionne ainsi : chaque contrôleur (source, kustomize, helm) réconcilie sa partie de l’état désiré de manière autonome, sans coordination centralisée.

Points clés

  • Flux se décompose en contrôleurs indépendants, chacun pilotant ses propres CRDs. Le source-controller réconcilie les sources (dépôts Git, buckets, OCI) : il clone le dépôt à l’intervalle configuré et expose une archive des manifestes. Le kustomize-controller réconcilie les objets Kustomization : il applique les manifestes issus du source-controller au cluster. Le helm-controller réconcilie les HelmRelease en installant ou mettant à jour les charts Helm.
  • Ce découpage en contrôleurs autonomes reflète l’architecture même de Kubernetes : plutôt qu’un seul processus responsable de tout, chaque contrôleur possède sa propre boucle observe → diff → agit, son propre intervalle de réconciliation et ses propres conditions de statut. Une panne du helm-controller n’affecte pas la réconciliation des manifestes Kustomize.
  • La CR GitRepository définit la source : URL du dépôt, branche, intervalle de polling et éventuellement un Secret contenant les credentials. Le source-controller détecte les nouveaux commits et met à jour un artifact (archive tar) que les autres contrôleurs consomment.
  • La CR Kustomization (à ne pas confondre avec le fichier kustomization.yaml de Kustomize) pointe vers un GitRepository et un chemin. Le kustomize-controller réconcilie les manifestes de ce chemin dans le cluster, avec health checks intégrés : il attend que les ressources appliquées soient prêtes avant de marquer la réconciliation comme réussie.
  • Flux supporte les notifications bidirectionnelles : un webhook GitHub déclenche une réconciliation immédiate (au lieu d’attendre le prochain intervalle), et un Alert Flux envoie les résultats de réconciliation vers Slack, Teams ou un endpoint HTTP. L’observabilité de la boucle est ainsi intégrée dès la conception.

Exemple concret

Un cluster de staging utilise Flux pour gérer trois microservices. Le dépôt Git platform-config contient un répertoire par service. Un GitRepository est configuré avec un intervalle de 1 minute. À t₀, un développeur pousse un commit qui modifie le nombre de replicas du service cart-api de 2 à 4. Le source-controller détecte le nouveau commit dans les 60 secondes, clone le dépôt et produit un nouvel artifact. Le kustomize-controller observe que l’artifact a changé, applique les manifestes mis à jour et lance un health check. Le Deployment cart-api passe de 2 à 4 replicas. Le kustomize-controller marque la Kustomization comme Ready: True. Un Alert Flux envoie une notification Slack : « Kustomization cart-api réconciliée avec succès — commit abc1234 ».

Comparaison — ArgoCD vs Flux

CritèreArgoCDFlux
ArchitectureContrôleur monolithique + serveur API + UI webEnsemble de micro-contrôleurs (source, kustomize, helm)
InterfaceUI web riche + CLI argocdCLI flux + portail Weave GitOps (optionnel)
Modèle de réconciliationUne CR Application = un déploiement completComposition de CRs (GitRepository + Kustomization \| HelmRelease)
Multi-tenancyProjects + RBAC applicatifNamespaces natifs + ServiceAccounts Kubernetes
DéclenchementPolling + webhooksPolling + Receiver (webhook natif)

Code YAML — configuration Flux (GitRepository + Kustomization)

# git-repository.yaml — le source-controller surveille ce dépôt
apiVersion: source.toolkit.fluxcd.io/v1
kind: GitRepository
metadata:
  name: platform-config
  namespace: flux-system
spec:
  interval: 1m                       # fréquence de réconciliation de la source
  url: https://github.com/acme/platform-config.git
  ref:
    branch: main
  secretRef:
    name: git-credentials            # Secret contenant le token d'accès
---
# kustomization.yaml — le kustomize-controller applique ces manifestes
apiVersion: kustomize.toolkit.fluxcd.io/v1
kind: Kustomization
metadata:
  name: cart-api
  namespace: flux-system
spec:
  interval: 5m                       # fréquence de réconciliation des manifestes
  sourceRef:
    kind: GitRepository
    name: platform-config
  path: ./apps/cart-api              # chemin des manifestes dans le dépôt
  prune: true                        # supprimer les ressources absentes de Git
  targetNamespace: staging
  healthChecks:
    - apiVersion: apps/v1
      kind: Deployment
      name: cart-api
      namespace: staging
  timeout: 3m                        # durée maximale du health check

Code bash — observer la réconciliation Flux

# Installer Flux dans le cluster (bootstrap)
flux bootstrap github \
  --owner=acme \
  --repository=platform-config \
  --branch=main \
  --path=clusters/staging \
  --personal
# ✔ all components are healthy

# Vérifier l'état du GitRepository
flux get sources git
# NAME               REVISION     SUSPENDED  READY  MESSAGE
# platform-config    main@abc1234 False      True   stored artifact for revision 'main@abc1234'

# Vérifier l'état de la Kustomization
flux get kustomizations
# NAME       REVISION     SUSPENDED  READY  MESSAGE
# cart-api   main@abc1234 False      True   Applied revision: main@abc1234

# Forcer une réconciliation immédiate (sans attendre l'intervalle)
flux reconcile kustomization cart-api --with-source
# ✔ source reconciliation completed
# ✔ kustomization reconciliation completed

# Observer les événements de réconciliation
flux events --for Kustomization/cart-api
# Kustomization/cart-api  info   Reconciliation finished, next run in 5m

Piège courant : « Flux et ArgoCD sont interchangeables — le choix est purement esthétique » est une simplification. L’architecture diffère fondamentalement : ArgoCD centralise la logique dans un seul contrôleur avec un serveur API dédié et une interface web intégrée, tandis que Flux distribue la réconciliation entre plusieurs micro-contrôleurs indépendants pilotés uniquement par des CRDs Kubernetes. Ce choix a des conséquences sur le multi-tenancy (Flux repose sur les namespaces natifs), la résilience (une panne d’un contrôleur Flux n’affecte pas les autres) et l’opérabilité (ArgoCD offre une visibilité immédiate via son UI, Flux exige un outil complémentaire). Le bon choix dépend de l’équipe et de l’environnement.


Quiz — validation des acquis
Expert 7 questions Objectif : 5/7 minimum
0/7
bonnes reponses
Objectif non atteint (minimum 5/7 requis).
Relire la fiche memo ci-dessus en pretant attention aux points manques, puis cliquer sur « Recommencer » pour retenter.