Cloud
Azure ACR et AKS : contenir un digest d'image vulnérable avant de redéployer
Un runbook de production pour relier un signal de vulnérabilité ACR aux pods AKS, geler la promotion, revenir à un digest connu, valider le rollout puis conserver ou supprimer l'image suspecte.
Une analyse de vulnérabilité signale un digest dans Azure Container Registry. Le même dépôt contient plusieurs tags, des pods AKS tournent déjà et le pipeline peut encore promouvoir l’image. Supprimer immédiatement le manifest paraît prudent. Cette action ne remplace pourtant pas les conteneurs en cours et peut rendre leur prochain redémarrage impossible avant qu’un digest sain soit prêt.
Le cas d’usage est un service déployé dans plusieurs namespaces AKS depuis une image ACR. L’équipe doit déterminer où le digest suspect s’exécute, stopper sa propagation, revenir vers un artefact connu et prouver que le cluster ne le relance plus. La sortie du runbook est une décision explicite : conserver temporairement le manifest pour l’investigation, le supprimer du registre ou isoler le workload faute de version sûre.
Fixer l’incident au digest
Un tag décrit une intention de publication ; un digest identifie le manifest réellement exécuté. Un même digest peut porter plusieurs tags, et un tag mutable peut désormais pointer vers une autre image. Le dossier d’incident doit commencer par le digest complet, le dépôt, le registre et la preuve qui a déclenché l’alerte.
incident: inc-container-2026-08-08-01
registry: acrprodweu
repository: payments/api
suspect_digest: sha256:<digest-suspect>
finding:
source: approved-vulnerability-assessment
severity: <severity>
affected_component: <package-or-layer>
exploitable_context: under-review
scope:
clusters: [aks-prod-weu, aks-prod-neu]
environments: [production]
containment_owner: platform-oncall
application_owner: payments-team
known_good_digest: sha256:<digest-known-good>
deletion_authorized: false Ne transformez pas automatiquement une sévérité élevée en suppression immédiate. Confirmez que le finding concerne ce digest, que le composant vulnérable est présent dans le chemin d’exécution et que l’image n’est pas seulement un parent utilisé pendant le build. Cette qualification ajuste l’urgence ; elle ne doit pas retarder le gel de promotion.
Relier le manifest ACR aux workloads AKS
Commencez par inventorier les métadonnées du manifest et les tags attachés. Cette lecture est non destructive.
ACR="acrprodweu"
REPOSITORY="payments/api"
SUSPECT_DIGEST="sha256:<digest-suspect>"
az acr manifest list-metadata --registry "$ACR" --name "$REPOSITORY" --query "[?digest=='$SUSPECT_DIGEST']" --output json Interrogez ensuite les pods pour lire l’image demandée et l’identifiant résolu par le runtime. Le champ image peut encore montrer un tag alors que imageID expose le digest effectivement tiré.
kubectl get pods --all-namespaces -o json | jq -r '
.items[] as $pod
| ($pod.status.containerStatuses // [])[]
| select(.imageID | contains("sha256:<digest-suspect>"))
| [
$pod.metadata.namespace,
$pod.metadata.name,
.name,
.image,
.imageID,
(.ready | tostring),
(.restartCount | tostring)
]
| @tsv' Répétez l’inventaire sur chaque cluster du périmètre. Associez chaque pod à son contrôleur, puis au dépôt GitOps ou à la release qui porte l’état désiré. Modifier un pod isolé ne tient pas : Deployment, StatefulSet, DaemonSet ou opérateur le recréera depuis sa propre référence.
Conservez aussi les workloads à zéro replica et les CronJobs. Ils ne produisent aucun pod au moment du diagnostic, mais peuvent relancer le digest lors du prochain scale-out ou de la prochaine planification.
Geler la propagation sans effacer la preuve
Le premier changement doit empêcher une nouvelle promotion, pas détruire l’artefact étudié. Suspendez le job qui déplace les tags de release, bloquez le digest dans la politique de déploiement et interdisez les relances automatiques non nécessaires. Gardez les lectures ACR et la collecte de logs disponibles.
blocked:
- promote suspect digest to an environment tag
- create a new workload revision with suspect digest
- restart or scale out affected workloads without approval
- rebuild from an unpinned base image
still_allowed:
- read registry metadata and vulnerability evidence
- export manifests, SBOM and deployment history
- build and scan a remediation candidate
- deploy the approved known-good digest to a canary
exit_conditions:
- every desired-state reference is known
- a deployable safe digest is selected
- rollback and isolation paths are assigned
- validation commands are ready before rollout Un tag déplacé n’assainit pas les pods existants. Une suppression ACR ne les arrête pas non plus. Le confinement est complet seulement quand le pipeline refuse le digest et que l’état désiré des contrôleurs ne peut plus le recréer.
Choisir un retour sûr, pas seulement une image plus ancienne
Le candidat de retour doit être identifié par digest et requalifié avec les données disponibles au moment de l’incident. « Revenir à la version précédente » ne suffit pas si cette version partage la même couche vulnérable ou n’est plus compatible avec une migration de schéma déjà appliquée.
Vérifiez au minimum la provenance du build, le résultat de scan, la compatibilité de configuration, les dépendances externes, les migrations irréversibles et la capacité de l’image à démarrer avec l’état courant. Si aucun digest précédent n’est défendable, construisez une image corrigée depuis une base épinglée ou isolez le service. Ne remettez pas le digest suspect en production uniquement parce que le nouveau rollout échoue.
Retour vers un digest connu
digest rescanné et provenance vérifiée
compatible avec le schéma et la configuration actuels
probe de démarrage disponible
autre version sûre prête en cas de régression
Construire un digest corrigé
aucune version précédente compatible
patch de dépendance ou base image nécessaire
pipeline reproductible et attestations disponibles
Isoler le workload
exploitation active ou impact élevé confirmé
aucun digest sûr immédiatement déployable
exposition réseau ou action métier peut être suspendue
restauration soumise à une nouvelle validation Redéployer par digest et commencer par un canary
Modifiez la source de vérité, pas seulement le cluster. La référence par digest garantit que tous les nouveaux pods demandent le même manifest, même si un tag est déplacé ensuite.
spec:
template:
metadata:
annotations:
naxaya.com/image-incident: inc-container-2026-08-08-01
spec:
containers:
- name: api
image: acrprodweu.azurecr.io/payments/api@sha256:<digest-known-good>
imagePullPolicy: IfNotPresent Appliquez d’abord ce changement à une replica ou à un segment de trafic borné. Vérifiez le démarrage, la readiness, les erreurs applicatives, les dépendances et un parcours métier réversible. Étendez ensuite par palier. L’objectif n’est pas uniquement d’obtenir un Deployment Available, mais de prouver que le digest attendu traite correctement le trafic réel.
NAMESPACE="payments"
DEPLOYMENT="payments-api"
kubectl rollout status --namespace "$NAMESPACE" deployment/"$DEPLOYMENT" --timeout=10m
kubectl get pods --namespace "$NAMESPACE" -l app=payments-api -o custom-columns='POD:.metadata.name,IMAGE:.spec.containers[*].image,IMAGE_ID:.status.containerStatuses[*].imageID,READY:.status.containerStatuses[*].ready' Une fois le rollout terminé, relancez l’inventaire global du digest suspect. Le résultat attendu est vide pour les pods en cours, les nouveaux pods et les jobs déclenchés pendant la fenêtre. Contrôlez également que les manifests GitOps, CronJobs et workloads suspendus ne le référencent plus.
Décider quoi faire du manifest suspect
Supprimer par digest dans ACR retire le manifest et tous les tags qui le référencent. L’opération est destructive. Elle empêche de nouveaux pulls depuis ce registre, mais n’arrête pas les conteneurs lancés et peut faire échouer un redémarrage encore configuré sur ce digest.
Avant suppression, exigez trois preuves : aucun état désiré approuvé ne référence le digest, aucune dépendance de restauration ne l’utilise et les éléments d’investigation nécessaires ont été conservés selon la politique de l’organisation. Affichez d’abord la cible exacte, puis faites autoriser l’action.
ACR="acrprodweu"
REPOSITORY="payments/api"
SUSPECT_DIGEST="sha256:<digest-suspect>"
az acr manifest list-metadata --registry "$ACR" --name "$REPOSITORY" --query "[?digest=='$SUSPECT_DIGEST'].[digest,tags,lastUpdateTime]" --output table
# Exécuter uniquement après validation formelle de la cible.
az acr repository delete --name "$ACR" --image "$REPOSITORY@$SUSPECT_DIGEST" --yes Si l’investigation impose de conserver l’artefact, ne laissez pas cette conservation devenir une possibilité de promotion. Maintenez le blocage dans le pipeline et la politique d’admission, limitez les droits d’écriture et documentez une date de réévaluation.
Valider le confinement et préparer le rollback
Le rollback du rollout ne doit jamais signifier « remettre le digest suspect ». Préparez deux chemins : revenir vers un second digest sûr si la version choisie régresse, ou isoler le workload si aucune image saine ne fonctionne avec l’état courant.
Clôturez seulement lorsque le digest suspect n’est plus exécuté, aucune source de vérité ne le référence, une tentative de promotion est refusée, le digest de remplacement est observé dans chaque cluster, les probes restent conformes et la décision de conservation ou suppression est tracée.
Après suppression, testez un pull contrôlé du digest suspect depuis un environnement sans cache : il doit échouer. Testez ensuite un rescheduling du canary sain sur un nœud qui ne possède pas déjà ses couches. Cette seconde vérification prouve que le digest de remplacement reste réellement récupérable depuis ACR.
Conclusion
Un finding sur une image conteneur devient exploitable quand il est relié à un digest, aux pods qui l’exécutent et aux contrôleurs capables de le recréer. Le bon ordre est de geler la promotion, inventorier, sélectionner un digest sûr, redéployer par digest, valider le comportement puis décider du sort du manifest suspect.
La décision finale doit prouver trois propriétés différentes : le digest vulnérable ne s’exécute plus, il ne peut plus être promu et le service dispose d’un chemin de retour qui ne réintroduit pas le risque.