Vous écrivez probablement actions/checkout@v7 dans vos workflows, comme tout
le monde. Ce suffixe paraît anodin : c'est en réalité une référence mobile,
et elle a déjà servi à des attaques réelles contre des milliers de dépôts.
Cette page explique le mécanisme, puis la parade, qui tient en une ligne de
YAML.
Ce que vous allez apprendre
Section intitulée « Ce que vous allez apprendre »- Comprendre le danger des tags mobiles (
@v4,@main,@latest) - Reconnaître une attaque par déplacement de tag, façon
tj-actions/changed-files - Épingler une action sur le SHA de son commit, avec commentaire de version
- Trouver le SHA d'une action via l'API, la CLI ou l'interface GitHub
- Automatiser la conversion et la mise à jour avec
pin-github-actionet Dependabot - Vérifier la couverture de l'épinglage sur l'ensemble d'un dépôt
C'est quoi le problème avec @v4 ?
Section intitulée « C'est quoi le problème avec @v4 ? »Le suffixe @v4 que l'on voit partout dans les workflows désigne un tag
Git. Derrière cette habitude anodine se cache une référence mobile, une
faille structurelle que cette section décortique, d'abord par l'image, puis en
termes techniques.
En termes techniques
Section intitulée « En termes techniques »Un tag Git comme @v7 n'est qu'une étiquette posée sur un commit, et
rien ne la fixe. Quiconque dispose d'un accès en écriture au dépôt peut la
déplacer vers un autre commit, y compris vers du code publié après votre
dernière relecture. Votre workflow, lui, continuera de demander « la v7 ».
❌ Tag (@v4)
- C'est une étiquette mobile
- Peut pointer vers n'importe quel code
- Modifiable par le mainteneur (ou un attaquant)
✅ SHA (empreinte)
- C'est une empreinte cryptographique
- Identifie un code précis et unique
- Impossible à modifier ou falsifier
Comment une attaque se déroule ?
Section intitulée « Comment une attaque se déroule ? »Ce n'est pas de la science-fiction. En mars 2025, l'action populaire tj-actions/changed-files a été compromise exactement de cette façon.
-
Jour 1 : Vous utilisez
action/exemple@v4qui pointe vers le commitabc123, du code légitime, testé et validé. -
Jour 30 : Un attaquant compromet le compte du mainteneur (phishing, mot de passe faible, token volé...).
-
L'attaquant déplace le tag :
@v4pointe maintenant vers un nouveau commitxyz789contenant du code malveillant. -
Jour 31 : Votre workflow se lance. Il récupère
@v4... et exécute le code malveillant sans que vous ne remarquiez rien ! -
Résultat : Vos secrets (
GITHUB_TOKEN, clés API, credentials) sont exfiltrés vers l'attaquant.
La solution : épingler sur SHA
Section intitulée « La solution : épingler sur SHA »Plutôt que de faire confiance à une étiquette mobile, désignez le commit par son empreinte cryptographique, le SHA. Vous ne demandez plus « la dernière v7 », vous demandez cette révision précise, celle que vous avez relue.
# ❌ Dangereux : tag mutable, peut changer à tout moment- uses: actions/checkout@v4
# ✅ Sécurisé : SHA immuable, toujours le même code- uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2Pourquoi le commentaire # v4.2.2 ? Il indique à quelle version
correspond ce SHA. C'est purement informatif pour vous (et Dependabot), mais
c'est le SHA qui compte pour la sécurité.
Comment trouver le SHA d'une action ?
Section intitulée « Comment trouver le SHA d'une action ? »Vous avez compris pourquoi utiliser un SHA. Maintenant, comment le trouver ? Plusieurs méthodes existent, de la plus simple à la plus automatisée.
Méthode 1 : Via l'API GitHub (rapide)
Section intitulée « Méthode 1 : Via l'API GitHub (rapide) »La requête la plus directe interroge l'API REST de GitHub : elle renvoie le SHA du commit derrière n'importe quel tag, sans rien installer.
# Obtenir le SHA du tag v4.2.2 de l'action checkoutcurl -s https://api.github.com/repos/actions/checkout/commits/v4.2.2 \ | jq -r .shaRésultat attendu : 11bd71901bbe5b1630ceea73d27597364c9af683
Méthode 2 : Via la CLI GitHub (si installée)
Section intitulée « Méthode 2 : Via la CLI GitHub (si installée) »Si la CLI gh est installée et authentifiée, un seul appel suffit : elle
gère l'authentification et l'extraction du SHA sans curl ni jq.
gh api repos/actions/checkout/commits/v4.2.2 --jq .shaMéthode 3 : Via l'interface web
Section intitulée « Méthode 3 : Via l'interface web »Sans terminal, l'interface GitHub donne le SHA en quelques clics depuis la page des releases du dépôt.
- Ouvrez le dépôt de l'action, par exemple
github.com/actions/checkout - Allez dans les Releases, listées dans la barre latérale
- Repérez la version exacte visée, par exemple
v7.0.1 - Suivez le lien du commit associé à ce tag
- Copiez le SHA complet, ses 40 caractères, jamais la forme abrégée
Automatiser l'épinglage (ne le faites pas à la main !)
Section intitulée « Automatiser l'épinglage (ne le faites pas à la main !) »Convertir manuellement chaque action serait fastidieux et source d'erreurs. Heureusement, des outils font le travail pour vous.
Option 1 : pin-github-action (en ligne de commande)
Section intitulée « Option 1 : pin-github-action (en ligne de commande) »Cet outil analyse vos workflows et remplace automatiquement les tags par leurs SHA :
# Installer l'outilnpm install -g pin-github-action
# Convertir un seul workflowpin-github-action .github/workflows/ci.yml
# Convertir TOUS les workflows d'un coupfind .github/workflows -name "*.yml" -exec pin-github-action {} \;Avant (vulnérable) :
- uses: actions/checkout@v7.0.1 # ❌ tag exact, mais déplaçable- uses: actions/setup-node@v7.0.0 # ❌ idem : une étiquette, pas un contenuAprès (sécurisé) :
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # pin@v7.0.1- uses: actions/setup-node@820762786026740c76f36085b0efc47a31fe5020 # pin@v7.0.0Option 2 : StepSecurity (interface web)
Section intitulée « Option 2 : StepSecurity (interface web) »Si vous préférez une interface graphique, app.stepsecurity.io offre une solution simple :
- Collez votre workflow YAML dans l'interface
- L'outil convertit les tags rencontrés en SHA
- Relisez le résultat, puis copiez-le
- Remplacez votre fichier, et vérifiez le diff avant de valider
Bonus : StepSecurity analyse aussi d'autres aspects de sécurité de vos workflows (permissions, secrets exposés, etc.).
Garder les SHA à jour (sans effort)
Section intitulée « Garder les SHA à jour (sans effort) »L'épinglage a une contrepartie qu'il faut assumer : un SHA figé ne reçoit aucun correctif. Les actions publient pourtant des mises à jour de sécurité, et votre pipeline doit les suivre. Toute la question est de le faire sans revenir aux tags mobiles.
Solution 1 : Dependabot (recommandé)
Section intitulée « Solution 1 : Dependabot (recommandé) »Dependabot surveille vos dépendances et crée automatiquement des Pull Requests quand de nouvelles versions sont disponibles :
version: 2updates: - package-ecosystem: "github-actions" directory: "/" schedule: interval: "weekly" # Vérifie chaque semaine cooldown: default-days: 7 # Quarantaine : jamais une version publiée le jour même commit-message: prefix: "ci" # Préfixe des commits : "ci: ..."Comment ça marche : Dependabot
détecte le commentaire # v4.2.2 dans vos workflows. Quand v4.2.3 sort, il
crée une PR qui met à jour le SHA et le commentaire. Vous n'avez qu'à review
et merger !
Solution 2 : Renovate (alternative)
Section intitulée « Solution 2 : Renovate (alternative) »Renovate est une alternative à Dependabot avec plus d'options de configuration :
{ "$schema": "https://docs.renovatebot.com/renovate-schema.json", "extends": ["config:recommended"], "github-actions": { "enabled": true, "pinDigests": true }}Vérifier que tout est bien épinglé
Section intitulée « Vérifier que tout est bien épinglé »Comment savoir si vos workflows sont correctement sécurisés ? L'outil Scorecard de l'OpenSSF analyse votre dépôt et note vos pratiques de sécurité :
scorecard --local . --checks Pinned-Dependencies --show-detailsInterprétation du score :
| Score | Signification |
|---|---|
| 10/10 | Parfait ! Toutes les actions sont épinglées par SHA |
| 5-9/10 | Certaines actions utilisent encore des tags |
| 0/10 | Danger ! Tags mutables partout (@v1, @latest, @main) |
Les actions GitHub officielles, on les épingle aussi ?
Section intitulée « Les actions GitHub officielles, on les épingle aussi ? »Oui ! Même si les actions maintenues par GitHub (actions/*) sont plus
fiables que les actions tierces, l'épinglage reste une bonne pratique :
| Action | Usage | Pourquoi l'épingler |
|---|---|---|
actions/checkout | Cloner le repo | A accès à votre code source |
actions/setup-node | Installer Node.js | Exécute des scripts sur le runner |
actions/setup-python | Installer Python | Idem |
actions/cache | Cache des dépendances | Manipule des fichiers |
actions/upload-artifact | Sauvegarder des artifacts | A accès aux fichiers produits |
actions/download-artifact | Récupérer des artifacts | Peut injecter des fichiers |
Le principe : tout code qui s'exécute dans votre CI mérite d'être vérifié et épinglé, quelle que soit sa source.
Actions tierces : comment évaluer le risque ?
Section intitulée « Actions tierces : comment évaluer le risque ? »Toutes les actions ne se valent pas. Avant d'ajouter une action tierce à vos workflows, posez-vous ces questions :
✅ Signaux positifs
- Beaucoup d'étoiles et d'utilisateurs
- Commits réguliers, issues traitées
- Maintenue par une organisation connue
- Code source lisible et documenté
- Releases avec changelog
⚠️ Signaux d'alerte
- Peu d'étoiles, pas de maintenance
- Demande
permissions: write-all - Pas de releases tagguées
- Code obfusqué ou minifié
- Maintenue par un compte anonyme
Exemple complet : workflow sécurisé
Section intitulée « Exemple complet : workflow sécurisé »Voici un workflow qui applique toutes les bonnes pratiques :
name: CI
# Aucune permission par défaut : chaque job demande ce qu'il lui fautpermissions: {}
on: push: branches: [main] pull_request:
jobs: build: runs-on: ubuntu-24.04 permissions: contents: read steps: # Toutes les actions sont épinglées par SHA - name: Récupérer le code uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: persist-credentials: false
- name: Installer Node.js uses: actions/setup-node@820762786026740c76f36085b0efc47a31fe5020 # v7.0.0 with: node-version: '20' cache: 'npm'
- name: Installer les dépendances run: npm ci
- name: Lancer les tests run: npm test
- name: Publier la couverture uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 with: name: coverage path: coverage/Ce qui rend ce workflow sécurisé :
Cinq décisions rendent ce workflow défendable, et chacune se lit dans le fichier :
permissions: {}au niveau workflow,contents: readaccordé au seul job qui en a besoin- toutes les actions épinglées par SHA, avec la version en commentaire
persist-credentials: falsesuractions/checkout, pour que leGITHUB_TOKENne reste pas dans la configuration Git du runner- des commentaires de version exploitables par Dependabot
- aucune action tierce dont l'éditeur ne soit identifié
Récapitulatif : les 3 étapes pour sécuriser vos workflows
Section intitulée « Récapitulatif : les 3 étapes pour sécuriser vos workflows »Trois actions concrètes suffisent à passer d'un dépôt vulnérable à des workflows épinglés et maintenus.
-
Convertir tous vos workflows avec
pin-github-actionou StepSecurity -
Configurer Dependabot pour garder les SHA à jour automatiquement
-
Vérifier régulièrement avec Scorecard que rien n'a été oublié
Contrôle de connaissances
Section intitulée « Contrôle de connaissances »Vérifiez que l'essentiel de ce guide est acquis. Les questions portent uniquement sur ce qui vient d'être expliqué ici.
Contrôle de connaissances
Validez vos connaissances avec ce quiz interactif
Informations
- Le chronomètre démarre au clic sur Démarrer
- Questions à choix multiples, vrai/faux et réponses courtes
- Vous pouvez naviguer entre les questions
- Les résultats détaillés sont affichés à la fin
Lance le quiz et démarre le chronomètre
Vérification
(0/0)Profil de compétences
Quoi faire maintenant
Ressources pour progresser
Des indices pour retenter votre chance ?
Nouveau quiz complet avec des questions aléatoires
Retravailler uniquement les questions ratées
Retour à la liste des certifications
À retenir
Section intitulée « À retenir »- Un tag Git (
@v4,@main,@latest) est une référence mobile : le mainteneur, ou un attaquant, peut la déplacer vers n'importe quel code. - L'attaque
tj-actions/changed-filesde mars 2025 a exploité exactement ce mécanisme pour exfiltrer les secrets de milliers de pipelines. - Épingler une action sur le SHA de commit (40 caractères) garantit que le pipeline exécute toujours le même code vérifié.
- Le commentaire
# v4.2.2après le SHA est informatif : il permet à Dependabot de proposer les mises à jour de version. - On n'épingle pas à la main :
pin-github-actionou StepSecurity convertissent les workflows, Dependabot ou Renovate maintiennent les SHA à jour. - Les actions officielles
actions/*s'épinglent aussi, tout code exécuté dans la CI mérite d'être figé.
Pour aller plus loin
Section intitulée « Pour aller plus loin »- Auditer avec zizmor : Repérer automatiquement les actions restées sur un tag mutable dans tous vos workflows.
- Scanner avec poutine : Étendre le contrôle d'épinglage à une organisation entière, dépôt par dépôt.
- Checklist sécurité : Situer l'épinglage parmi les autres vérifications à passer avant de fusionner.