Aikido

Shai-Hulud a été la meilleure chose qui soit arrivée à la sécurité de la chaîne d'approvisionnement

C'est peut-être à Shai-Hulud que nous devons d'avoir convaincu la communauté d'adopter le système de publication « Trusted »

Écrit par
Charlie Eriksen

npm a lancé « Package Provenance » fin 2022. Pendant deux ans, le nombre moyen d’adoptions s’est situé entre 20 et 50 paquets par semaine. Cette initiative a été suivie par « Trusted Publishing » en 2024. Des articles de blog ont été publiés. Des avis de la CISA ont été émis. Mais la courbe n’a pratiquement pas bougé. Finalement, « Trusted Publishing » avec OIDC a été mis à la disposition du grand public en juillet 2025.

C'est alors que Shai-Hulud a frappé. Le nombre hebdomadaire d'adoptions a bondi à 430 paquets. En 18 mois, le nombre cumulé d'adoptions a été multiplié par 3,4. Nous n'en sommes encore qu'à 25 % du volume total de téléchargements couverts : seuls 11 001 des 51 370 paquets les plus populaires l'ont adopté. Mais ces attaques ont eu un impact bien plus important que tout ce qu'a pu faire le secteur de la sécurité.

Voici les données.

Qu'est-ce que « Trusted Publishing » ?

Trusted Publishing remplace les jetons API npm à longue durée de vie par des identifiants à courte durée de vie, valables pour une seule exécution, émis via OpenID Connect. Au lieu de stocker indéfiniment le jeton NPM_TOKEN dans les secrets de votre dépôt GitHub, votre pipeline d'intégration continue reçoit un jeton qui expire en quelques minutes. Rien à voler. Rien à exfiltrer.

La vague d'attaques qui a tout changé

26 août 2025 : S1ngularity. Des pirates ont exploité une erreur de configuration de GitHub Actions dans le monorepo Nx pour exécuter du code provenant d’un fork malveillant dans le contexte de confiance du dépôt en amont, dérobant ainsi le jeton de publication npm. Des versions malveillantes de plusieurs paquets Nx ont été actives pendant quatre heures, analysant les machines des développeurs à la recherche d’identifiants, de clés SSH et de portefeuilles cryptographiques — et, notamment, recherchant activement les outils CLI d’IA installés pour les exécuter avec l’option --dangerously-skip-permissions et extraire le contenu du système de fichiers. Cette semaine-là : l’adoption a connu une hausse notable pour la première fois.

8 septembre 2025 : Debug/Chalk. Un responsable de maintenance a été victime d’une tentative d’hameçonnage via un faux e-mail du support npm (envoyé depuis l’adresse npmjs.help) qui a permis de récupérer ses identifiants et son code TOTP en temps réel. 18 paquets, totalisant plus de 2 milliards de téléchargements hebdomadaires, ont été infectés par un code malveillant destiné au vol de cryptomonnaies, qui interceptait discrètement les interactions entre le navigateur et le portefeuille et redirigeait les fonds. Les versions malveillantes sont restées actives pendant deux heures. Cette semaine-là : 103 nouveaux paquets ont adopté Trusted Publishing.

15 septembre 2025 : vague 1 de Shai-Hulud. Un ver autoreproductible a frappé l'écosystème npm. Lorsqu'un paquet compromis détectait d'autres jetons npm dans son environnement, il publiait automatiquement des versions malveillantes de tout ce à quoi il pouvait accéder. Bilan : plus de 700 paquets compromis, 27 000 dépôts GitHub malveillants, 14 000 secrets exposés au sein de 487 organisations. La CISA a émis une alerte le 23 septembre. Cette semaine-là : 109 nouveaux paquets.

23 novembre 2025 : Shai-Hulud 2.0. Une requête « Pwn » ciblant le dépôt asyncapi/cli a permis d’exfiltrer le jeton CI en moins de trois minutes, puis de l’utiliser pour déployer le ver via une extension OpenVSX malveillante. La campagne s’est propagée à plus de 25 000 dépôts malveillants. Microsoft a publié des recommandations le 9 décembre. Cette semaine-là : 372 nouveaux paquets. La moyenne hebdomadaire des deux années précédentes était d’environ 40.

24 novembre 2025 : SHA1-Hulud. Une vague parallèle a touché Zapier, ENS Domains et d’autres. Des identifiants à durée de vie prolongée ont été découverts dans des dépôts compromis. L’équipe de sécurité de npm a explicitement recommandé l’utilisation de « Trusted Publishing » comme solution. Cette semaine-là : 120 nouveaux paquets.

20-21 mars 2026 : CanisterWorm. L'équipe TeamPCP a déployé un ver npm à l'aide de jetons volés. Plus de 28 paquets ont été infectés en moins de 60 secondes ; la charge utile a récupéré des identifiants et s'est propagée de manière autonome. Cette semaine-là : 112 nouveaux paquets.

31 mars 2026 : Axios. Sapphire Sleet (Corée du Nord) a piraté le compte d’un responsable de maintenance et publié deux versions contenant une porte dérobée à 39 minutes d’intervalle, chacune injectant une fausse dépendance qui téléchargeait à l’insu de l’utilisateur un cheval de Troie d’accès à distance multiplateforme. Les paquets malveillants sont restés en ligne pendant trois heures. Axios enregistre plus de 100 millions de téléchargements par semaine. Cette semaine-là : 138 nouveaux paquets.

Du 8 au 22 avril 2026 : CanisterSprawl. Un deuxième ver npm de TeamPCP utilisant un nouveau canister ICP. Lorsque des jetons PyPI ont été détectés dans les environnements infectés, il a propagé la menace à d’autres écosystèmes via une injection .pth. Cette semaine-là : 163 nouveaux paquets.

29-30 avril 2026 : Mini Shai-Hulud I. L'équipe TeamPCP est passée du vol de jetons au vol d'identifiants CI. Une attaque inter-écosystèmes a touché npm, PyPI et Packagist en 24 heures via des jetons CircleCI compromis. Cette semaine-là : 121 nouveaux paquets.

Du 7 au 11 mai 2026 : Mini Shai-Hulud II / TanStack. Voici l’escalade qui a tout changé : ils n’ont pas volé de jeton. L’équipe TeamPCP a utilisé une requête « Pwn Request » pour corrompre le cache de GitHub Actions, puis a attendu que le workflow de publication légitime s’exécute. Lorsque celui-ci s’est exécuté — avec des droits d’écriture sur l’id-token —, du code contrôlé par l’attaquant, issu du cache corrompu, a extrait le jeton OIDC de la mémoire du runner et l’a échangé via le point de terminaison dédié aux jetons de npm. Les paquets publiés comportaient des attestations de provenance SLSA de niveau 3 valides. La fonctionnalité « Trusted Publishing » n’a pas été contournée. Elle a été utilisée comme vecteur d’attaque. Plus de 170 paquets sur npm et PyPI en 5 heures.

18-19 mai 2026 : Mini Shai-Hulud III / Nx & AntV. L’extension VS Code « Nx Console » a été compromise à l’aide d’identifiants volés lors de l’attaque TanStack — cinq jours de temps de latence avant son utilisation. 639 versions npm de @antv ont été corrompues via un compte de responsable volé, chacune installant une porte dérobée persistante « kitty-monitor ». Cette semaine-là : 144 nouveaux paquets. La semaine suivante : 430. Un record historique.

Du 1er au 7 juin 2026 : Miasma / Hades. La stratégie d’attaque a encore évolué. La vague 1 a vu la publication de 90 versions malveillantes de npm ciblant les paquets des services d’ Cloud s de Red Hat — non pas en volant des jetons OIDC, mais en exploitant directement le point de terminaison de publication OIDC. La vague 2 a introduit une technique « binding.gyp » pour contourner la détection des scripts d’installation. À la quatrième vague (Hades), la campagne s’était étendue à PyPI via l’exécution de fichiers .pth au démarrage, contaminant 37 roues réparties sur 19 paquets. Red Hat a publié le bulletin RHSB-2026-006. Cette semaine-là : 209 nouveaux paquets.

Le schéma et son aggravation

Les premières attaques suivaient un schéma bien connu : hameçonnage d'un responsable de maintenance, vol d'un jeton à longue durée de vie, publication d'un logiciel malveillant, propagation à tout ce que le jeton permettait d'atteindre. L'attaque contre Debug/Chalk était une attaque par hameçonnage. Dans le cas d'Axios, il s'agissait d'un compte de responsable de maintenance piraté.

Mais les attaques les plus sophistiquées visaient le pipeline de CI lui-même. S1ngularity et Shai-Hulud 2.0 ont tous deux utilisé des « Pwn Requests », c'est-à-dire des pull requests malveillantes qui exploitaient les vulnérabilités des workflows GitHub Actions « pull_request_target » pour exécuter le code des attaquants au sein du contexte de confiance du dépôt en amont. Ils n’avaient pas besoin de voler un jeton stocké. Il leur suffisait que le runner de CI en possède un.

Mini Shai-Hulud II constituait l'aboutissement logique d'une évolution. Une fois le « runner » sous contrôle, il est possible d'extraire toutes les informations d'authentification ambiantes présentes, y compris les jetons OIDC à durée de vie limitée. Les paquets qu'il publiait semblaient légitimes à tous les contrôles automatisés : provenance valide, identité réelle du responsable de maintenance, signature correcte. L'attaque était passée de l'exploitation de secrets stockés à celle du processus de compilation lui-même.

Miasma a encore intensifié ses attaques. Il n'avait même pas besoin d'extraire de jeton : il exploitait directement le point de terminaison de publication OIDC. Chaque vague introduisait une nouvelle technique permettant de contourner la détection. Les analyses a posteriori ne cessaient de mettre en évidence les mêmes failles. Les attaques ne cessaient de trouver de nouveaux moyens de contourner les correctifs recommandés.

Attaque Date Nouveaux colis cette semaine-là
Lancement d'une fonctionnalité décembre 2022 4
Moyenne sur deux ans 2023-2024 ~35
S1ngularité 26 août 2025 52
Débogage/Chalk 8 septembre 2025 103
Shai-Hulud v1 15 sept. 2025 109
Shai-Hulud 2.0 23 nov. 2025 372
SHA1-Hulud 24 nov. 2025 120
CanisterWorm 20 mars 2026 112
Axios 31 mars 2026 138
CanisterSprawl 8 avril 2026 163
Mini Shai-Hulud I 29 avril 2026 121
Mini Shai-Hulud II 7 mai 2026 126
Mini Shai-Hulud III 18 mai 2026 144
Mini Shai-Hulud (sommet) 25 mai 2026 430
Miasma 1er juin 2026 209

La surface d'attaque est désormais nettement plus réduite qu'il y a 18 mois. Non pas parce que le secteur de la sécurité a réussi à convaincre les gens, mais parce que des paquets ont été piratés, ce qui a poussé les responsables de leur maintenance à modifier leur configuration.

Ce n'est pas un succès pour la sensibilisation à la sécurité. C'est simplement un élément d'information qui montre comment les décisions en matière de sécurité sont réellement prises dans la pratique.

Qui était-ce ?

Au cours de la campagne « Shai-Hulud 2.0 », l’attaquant a renommé son compte GitHub « UnknownWonderer1 » — une référence quasi certaine aux « Zensunni Wanderers » de *Dune*: ces nomades persécutés qui sont devenus les Fremen, la seule culture à avoir appris à vivre en harmonie avec Shai-Hulud. Ce nom n’est pas le fruit d’une personne tombée par hasard dans cet écosystème. C’est le nom de quelqu’un qui y avait mûrement réfléchi.

La conception du logiciel malveillant confirme cette interprétation. S1ngularity ne s'est pas contenté d’exfiltrer discrètement des identifiants : il a injecté une commande d’arrêt dans le profil du shell, ce qui aurait visiblement provoqué le plantage de votre machine dès la prochaine ouverture d’un terminal. Ce n’est pas le comportement de quelqu’un qui cherche à rester discret. Chaque campagne s’est arrêtée bien avant d’atteindre son plein potentiel. Un ver qui se propage de lui-même dans plus de 700 paquets mais qui limite sa charge utile fait un choix.

Ils comprenaient également mieux la structure des incitations que l’écosystème lui-même. Les responsables de maintenance sont rarement rémunérés pour sécuriser les paquets. Les conséquences d’une faille se répercutent sur les utilisateurs en aval, et non sur la personne qui a laissé le jeton dans l’environnement de développement (CI). Les plateformes ayant le pouvoir d’imposer des normes de sécurité lors de la publication sont celles qui souffrent le moins lorsque les choses tournent mal. Il s’agit d’un échec classique de l’action collective — et les 40 000 paquets non protégés après trois ans d’avis de sécurité sont exactement le résultat de cette structure. Cet attaquant avait compris pourquoi rien ne bougeait. Et il a décidé d’exercer une pression d’un autre type.

Coups de semonce

J’avais déjà abordé ce sujet à l’époque: le choix du nom, la retenue dont faisait preuve la conception du logiciel malveillant, et la manière dont les attaques s’arrêtaient systématiquement avant d’aller jusqu’au bout de leur exploitation. À mon sens, Shai-Hulud n’était pas avant tout une opération criminelle. C’était un message — envoyé par quelqu’un qui comprenait suffisamment bien l’écosystème pour savoir exactement quels points sensibles le feraient réagir.

Les Fremen prient pour que le passage du Créateur purifie le monde. L'agresseur semble être parvenu à une conclusion similaire : seule une souffrance visible pourrait contraindre l'écosystème à affronter ce qui a rendu le ver possible. Pour les Fremen, Shai-Hulud n'est pas simplement un animal destructeur. C'est le Créateur. Son passage déchire le désert, mais il purifie également et fait respecter les lois auxquelles tout ce qui vit dans cet écosystème doit se plier.

Ils ne se sont pas contentés de libérer Shai-Hulud.

Ils ont choisi d'incarner le Vagabond qui comprenait pourquoi il devait venir.

Pourquoi nous n'avons toujours pas résolu ce problème

L'alerte avait été lancée. L'écosystème n'a pas réagi assez vite. Le guide d'attaque open source « Shai-Hulud » a alors été repris par des acteurs qui n'avaient aucun intérêt à faire passer un message : TeamPCP, Sapphire Sleet et d'autres qui se sont directement attaqués au vol d'identifiants, aux portefeuilles cryptographiques et à l'accès à distance. Des frameworks comme Mastra en ont fait les frais. Le ver qui n'était au départ qu'une démonstration est devenu un modèle à suivre.

Ce qui est frustrant, c’est que cet obstacle n’est pas d’ordre technique. Trusted Publishing est gratuit et ne prend que dix minutes. Le problème, c’est que le coût de ne pas le faire n’a pas encore été imputé à la bonne personne. Les responsables de paquets assument le risque de réputation si leur paquet est compromis, mais le préjudice réel se répercute en aval sur des équipes qui n’ont pas écrit une seule ligne du paquet concerné. Ce décalage est structurel. Les attaques entraînent un pic d’adoption temporaire, puis l’urgence s’estompe, et la prochaine vague de paquets revient par défaut à des jetons à longue durée de vie.

Regardez le graphique. Les pics sont bien réels. Tout comme la baisse qui les sépare.

Et Mini Shai-Hulud a apporté un nouvel élément : même les paquets qui ont adopté Trusted Publishing peuvent être compromis si le pipeline de CI sous-jacent n'est pas sécurisé. Extraire un jeton OIDC de la mémoire d'un runner est plus difficile que de voler un secret stocké. Mais ce n'est pas impossible, et cette attaque dispose désormais d'une preuve de concept publique. Trusted Publishing élimine un vecteur d'attaque. Il ne les élimine pas tous.

Le déficit de responsabilité, et comment y remédier

Axios enregistrait plus de 100 millions de téléchargements hebdomadaires et n’avait pas encore adopté le système « Trusted Publishing » lorsque la Corée du Nord a piraté son site. Quelqu’un aurait pu déposer une demande de « PR » un an plus tôt. Personne ne l’a fait.

C’est là que réside le déficit de responsabilité. La communauté de la sécurité publie des avis de sécurité, rédige des analyses rétrospectives et attend la prochaine attaque pour faire bouger les choses. Il existe pourtant une manière plus constructive d’exercer cette même pression : s’attaquer de manière proactive aux 40 000 paquets qui n’ont pas encore été mis à jour, à l’instar de ce qu’a fait Let’s Encrypt avec le protocole HTTP. Soumettez des PR. Ouvrez des tickets. Identifiez les paquets les plus téléchargés qui utilisent encore des jetons à longue durée de vie. Faites en sorte que le coût social de la non-adoption de TP soit supérieur aux dix minutes nécessaires pour y remédier.

C'est exactement le genre d'action dont l'écosystème a réellement besoin. Pas encore un avis de la CISA. Pas encore un article de blog qui sera lu puis oublié. Une pression concrète, ciblée et qui met mal à l'aise, exercée sur les responsables de paquets spécifiques — ceux qui enregistrent plus de 10 millions de téléchargements hebdomadaires et qui ne sont qu'à un identifiant piraté de devenir le prochain incident.

Le secteur de la sécurité connaît la solution depuis trois ans. La question est de savoir si nous sommes prêts à faire en sorte qu'il devienne socialement inacceptable de l'ignorer.

40 000 des 51 000 paquets les plus populaires n'ont toujours pas changé de version

11 001 paquets ont adopté le système « Trusted Publishing ». Ces 11 000 paquets représentent environ 25 % du volume total de téléchargements, car certains des paquets les plus importants ont effectué la transition après chaque vague d'attaques. Il reste toutefois 40 369 paquets (soit 75 % du volume de téléchargements) qui continuent d'être publiés avec des jetons à longue durée de vie.

Si vous gérez un paquet npm, faites-le dès maintenant. La documentation est disponible ici. Quatre lignes de YAML et une case à cocher. Assurez-vous ensuite que vos workflows GitHub Actions ne comportent pas de `pull_request_target` sans limites de confiance explicites ; c'est en effet le vecteur d'attaque utilisé par Mini Shai-Hulud pour extraire le jeton OIDC, même après la mise en place de TP.

Si vous dépendez de paquets qui n'ont pas encore été mis à jour, signalez le problème. Créez un ticket sur PR. Il se peut que le responsable ne connaisse pas l'existence de Trusted Publishing, ou qu'il ait simplement besoin que quelqu'un lui fasse comprendre que l'inaction est plus gênante que cette correction qui ne prendrait que dix minutes.

Le ver des sables de « Dune » s'appelle Shai-Hulud, ce qui signifie « le grand vieillard du désert ». Les Fremen ne se réjouissent pas lorsqu'il détruit quelque chose. Ils comprennent que son passage façonne l'écosystème d'une manière dont rien d'autre n'est capable.

C'est là la vérité dérangeante qui est au cœur de cet article. Les attaques ont porté leurs fruits. La douleur a eu un impact que trois années d'avis de sécurité n'avaient pas réussi à produire.

Nous en avons tiré les leçons. L'écosystème évolue sous l'effet de pressions, qui ne proviennent pas forcément d'un ver. Le Wanderer a compris pourquoi le Créateur devait intervenir. Nous travaillons à rendre la prochaine intervention superflue.

Nous y reviendrons bientôt.

Partager :

https://www.aikido.dev/blog/shai-hulud-trusted-publishing

S'abonner aux actualités

4,7/5
Fatigué des faux positifs ?
Essayez Aikido, comme 100 000 autres.
Commencez maintenant
Obtenez une démonstration personnalisée

Approuvé par plus de 100 000 équipes

Réserver maintenant
Analysez votre application à la recherche d'IDORs et de chemins d'attaque réels

Approuvé par plus de 100 000 équipes

Démarrer l'analyse
Découvrez comment le pentest IA teste votre application

Approuvé par plus de 100 000 équipes

Démarrer les tests

Sécurisez votre environnement dès maintenant.

Sécurisez votre code, votre cloud et votre environnement d’exécution dans un système centralisé unique.
Détectez et corrigez les vulnérabilités rapidement et automatiquement.

Aucune carte de crédit requise | Résultats en 32 secondes.