V červnu 2026 odhalili výzkumníci další evoluci malwarové rodiny Mini Shai-Hulud, pojmenovanou Miasma. Na rozdíl od tradičního npm malwaru, který míří na hrstku balíčků, tato kampaň ukázala, jak rychle se může kompromitace jediného kusu vývojářské infrastruktury rozšířit napříč ekosystémy: npm, GitHub Actions a dokonce i Go moduly.
Útočníci necílili na koncové uživatele. Cílili na vydavatele balíčků, CI/CD pipeline a mechanismy důvěry, které umožňují softwaru putovat z notebooku vývojáře až do produkce, aniž by ho někdo po cestě znovu kontroloval. Na nic z toho neexistuje CVE, protože v dotčeném kódu nikdy žádná chyba nebyla. Vstupním bodem byly ukradené přihlašovací údaje, ne zranitelnost.
Jednu věc je třeba zmínit hned na začátku: 12. května 2026 skupina TeamPCP, která za touto rodinou červů původně stála, veřejně zpřístupnila kompletní zdrojový kód Shai-Hulud/Mini Shai-Hulud na GitHubu pod licencí MIT. To mění způsob, jakým je potřeba tento příběh číst. Čtyři vlny, které následovaly, sdílejí stejnou sadu nástrojů i techniky, ale sdílené nástroje už neznamenají sdíleného operátora. Jakmile je framework veřejný, může kampaň k nerozeznání od té původní od TeamPCP spustit jakýkoli technicky schopný aktér. Následující text je proto třeba číst jako popis překrývajících se taktik, technik a postupů (TTP), ne jako potvrzenou atribuci jedné skupině.
Dotčené balíčky (npm a Go)
| Balíček | Kompromitovaná verze |
|---|---|
hexo-deployer-wrangler | 1.0.4 |
hexo-shoka-swiper | 0.1.10 |
leo-auth | 4.0.6 |
leo-aws | 2.0.4 |
leo-cache | 1.0.2 |
leo-cdk-lib | 0.0.2 |
leo-cli | 3.0.3 |
leo-config | 1.1.1 |
leo-connector-elasticsearch | 2.0.6 |
leo-connector-mongo | 3.0.8 |
leo-connector-mysql | 3.0.3 |
leo-connector-oracle | 2.0.1 |
leo-connector-redshift | 3.0.6 |
leo-cron | 2.0.2 |
leo-logger | 1.0.8 |
leo-sdk | 6.0.19 |
leo-streams | 2.0.1 |
prism-silq | 1.0.1 |
rstreams-metrics | 2.0.2 |
rstreams-shard-util | 1.0.1 |
serverless-convention | 2.0.4 |
serverless-leo | 3.0.14 |
solo-nav | 1.0.1 |
github.com/verana-labs/verana-blockchain (Go) | v0.10.1-dev.20 |
Socket ve vyšetřování pokračuje; nová zjištění průběžně doplňuje na svou stránku sledující kampaň Miasma.
Pokud váš strom závislostí obsahuje kterýkoli z těchto balíčků v uvedené verzi (nebo balíčky z dřívějších kompromitovaných vln téže kampaně z počátku června), považujte prostředí za potenciálně kompromitované a postupujte podle okamžitých nápravných kroků níže.
Časová osa
24. června 2026
↓
Kompromitován účet správce LeoPlatform
↓
Publikováno 23 škodlivých verzí balíčků (v rozmezí sekund)
↓
Payload v binding.gyp se spouští při instalaci
↓
Ukradeny přihlašovací údaje vývojářů i CI/CD
↓
Nasazen workflow v GitHub Actions („Run Copilot“)
↓
Ukradené secrets exfiltrovány do veřejných GitHub repozitářů
↓
Příbuznou technikou kompromitován Go modul (Verana Blockchain)
↓
Výzkumníci ze Socket, Wiz, Sonatype a dalších firem kampaň identifikují a zveřejňují
Jde o čtvrtou vlnu téže rodiny kampaní za necelý měsíc: poprvé se objevila 1. června proti npm namespace Red Hatu, 3. června následovala vlna s 57 balíčky a 24. až 25. června tato vlna LeoPlatform/Go. Jak bylo řečeno výše, TeamPCP zveřejnila zdrojový kód červa 12. května, takže „stejná rodina kampaní“ odráží sdílené TTP napříč vlnami, ne potvrzený důkaz, že za všemi čtyřmi stojí jeden operátor.
Co se vlastně stalo
- Správci npm ekosystému LeoPlatform někdo ukradl přihlašovací údaje k účtu nebo npm token, nejspíše pomocí infostealeru.
- Útočník tento ukradený přístup využil k publikování trojanizovaných verzí balíčků, které správce už legitimně vlastnil. Nic nebylo třeba „hacknout“ v tradičním slova smyslu, útočník už měl důvěryhodnou publikační identitu.
- Každý, kdo některou z těchto verzí nainstaloval, spustil skrytý payload, který mu ukradl jeho vlastní přihlašovací údaje.
- Část ukradených údajů patřila prostředím GitHub Actions, což útočníkovi umožnilo podstrčit škodlivý workflow a vytáhnout CI/CD secrets přímo z runneru.
- Nezávisle na tom byl příbuznou, ale odlišnou technikou kompromitován Go modul, což ukazuje, že kampaň není vázaná na jeden jazyk ani jeden správce balíčků.
- Celé to bylo odhaleno jen proto, že několik nezávislých výzkumných týmů sledovalo přesně tento vzor z dřívějších vln téže kampaně.
Technický rozbor
Fáze 1: Kompromitovaný správce
Npm účet czirker, spojený s LeoPlatform, byl kompromitován, nejspíše přes uniklé přihlašovací údaje nebo token vytažený infostealerem, který už na správcově stroji běžel.
Fáze 2: Publikace škodlivých balíčků
S ukradeným tokenem útočník publikoval 23 škodlivých verzí balíčků napříč ekosystémy LeoPlatform a RStreams v okně šesti sekund. Taková rychlost ukazuje na skriptovaný, automatizovaný publikační nástroj, ne na člověka ručně nahrávajícího soubory.
Nejkonkrétnější detail celé kampaně se skrývá právě v této fázi: útočník nejen publikoval škodlivé verze, ale také přesměroval dist-tag latest balíčku leo-sdk na otrávenou verzi 6.0.19, zatímco čistá verze 7.1.21 zůstala dostupná jen pod méně nápadným tagem awsv3. V praxi to znamená, že každé prostředí, které spustilo npm install leo-sdk bez explicitního semver pinu, bylo aktivně nasměrováno k červu, i když čistá verze existovala celou dobu. Praktické ponaučení je neúprosné: rozdíl mezi čistou instalací a kompromitací dělal pin na konkrétní verzi, ne na tag.
Fáze 3: Spuštění při instalaci
Tady je to chytré. Většina škodlivých npm balíčků je odhalena proto, že skenery hlídají pole preinstall a postinstall v package.json. Miasma je úplně obchází a místo toho přidává soubor binding.gyp, konfiguraci, kterou Node.js používá ke kompilaci nativních modulů během instalace. Protože je binding.gyp zcela běžnou součástí sestavování nativních doplňků, spouští kód během npm install, aniž by se dotkl polí, která většina nástrojů sleduje.
Proti této technice existovala dvě skutečná zmírnění a stojí za to být u obou přesný. První už existovalo: npm install --ignore-scripts podle vlastní dokumentace npm skutečně potlačí implicitní hook node-gyp rebuild, který soubor binding.gyp spouští. Samo o sobě to není úplná obrana, protože škodlivý balíček se stále stáhne a rozbalí a pozdější rebuild bez tohoto přepínače ho stále může spustit, ale tuto konkrétní cestu spuštění to blokuje. Druhé zmírnění přišlo o tři týdny pozdě: npm v12, vydané v červenci 2026, tento vektor ve výchozím nastavení zavírá a implicitní node-gyp rebuild spouštěný přes binding.gyp bere přesně jako jakýkoli jiný instalační skript, tedy blokovaný, pokud balíček není explicitně na allowlistu. Technika „Phantom Gyp“, kterou Miasma použila, byla v podstatě přímým zneužitím právě té mezery, kterou mělo npm v12 zavřít.
Fáze 4: Sběr secrets
Po spuštění payload sesbírá širokou sadu přihlašovacích údajů, mimo jiné:
- npm a PyPI tokeny
- GitHub Personal Access Tokeny a GitHub OIDC tokeny
- přihlašovací údaje k AWS, Azure a GCP
- SSH klíče
- konfigurační soubory a cesty k přihlašovacím údajům pro Claude Code, Cursor a další AI asistenty pro programování
- OpenAI API klíče
- Slack a Twilio tokeny, Docker auth soubory, Kubernetes configy, data z Vaultu a historii shellu
Fáze 5: Zneužití GitHubu
Malware podstrčí workflow do GitHub Actions (viděný pod názvem „Run Copilot“), který během běhu vytahuje secrets přímo z paměti CI runneru. Ukradená data jsou zašifrována a odeslána do nově vytvořených veřejných GitHub repozitářů sloužících jako mrtvé schránky; v době psaní článku nese exfiltrační značku kampaně více než 550 repozitářů. Při souvisejícím incidentu téhož dne útočník force-pushnul škodlivý commit do široce používané GitHub Action a přesměroval na něj verzovací tagy, takže každý workflow, který od té chvíle proti těmto tagům běžel, spouštěl útočníkův payload přímo v runneru GitHub Actions.
Fáze 6: Šíření
Kompromitován stroj vývojáře
↓
Ukradeny GitHub přihlašovací údaje vývojáře
↓
Z runneru vytaženy secrets CI/CD pipeline
↓
Ukradený npm token použit k publikaci dalších škodlivých balíčků
↓
Kompromitované balíčky instalují další vývojáři
↓
(opakovat)
Každá úspěšná kompromitace se stává odrazovým můstkem pro další. Právě proto jde o samošířící se kampaň, a ne o jednorázový incident.
V čem je tento útok jiný
| Dřívější supply chain útoky | Miasma |
|---|---|
| Jeden balíček | Celý ekosystém |
| Krádež kryptoměn | Plošná krádež přihlašovacích údajů |
| Jeden jazyk | Více jazyků (npm, nyní i Go) |
| Jeden správce | Vývojářská infrastruktura jako celek |
| Statický malware | Samošířící se, mezi vlnami se vyvíjí |
Dřívější npm supply chain incidenty byly převážně „vezmi a uteč“: kompromitovat balíček, ukrást klíče k peněženkám nebo session tokeny, jít dál. Miasma se chová spíš jako červ s obchodním modelem. Každou úspěšnou infekci bere jako palivo pro další vlnu a po více než třech týdnech a čtyřech samostatných vlnách se prokazatelně stále vyvíjí.
Proč se cílem staly GitHub Actions
GitHub Actions sedí v softwarovém dodavatelském řetězci na mimořádně cenném místě: drží OIDC tokeny používané pro důvěryhodné publikování bez přihlašovacích údajů do cloudových poskytovatelů a registrů, uchovává dlouhodobé CI secrets a už z principu běží automatizovaně a bez dohledu. Kompromitace CI runneru neodhalí jen notebook jednoho vývojáře, odhalí každou deployment pipeline, každou publikaci do registru a každý cloudový přihlašovací údaj, kterého se daný workflow dotkne. To je mnohem větší dosah než lokální prostředí kteréhokoli jednotlivého vývojáře, a přesně proto si kampaň postavila nástroje cílené specificky na něj.
Proč je expanze do Go důležitá
Většina zpráv o této kampani se soustředila na npm, protože tam žije většina balíčků. Kompromitace Go modulu je ale pravděpodobně nejdůležitějším detailem celého příběhu, a zároveň tím, který většina článků přeskakuje.
Go vzorek nepoužívá binding.gyp. Nespoléhá vůbec na mechanismy řešení modulů ani sestavování v Go. Místo toho může vývojář, který repozitář jen naklonuje nebo ho otevře v důvěryhodném IDE či AI asistentu pro programování, spustit payload pouze skrze konfiguraci projektu.
To říká něco důležitého: útočníky v jádru nezajímá JavaScript, npm ani mechanika konkrétního správce balíčků. Zajímají je vývojáři, a to kdekoli, kde vývojáři vkládají důvěru do automatizovaných nástrojů, ať je to instalační skript, build krok nebo IDE otevírající složku. Na jazyku nezáleží. Na přihlašovacích údajích vývojářů ano.
Širší ponaučení
Staré myšlení:
Skenujeme závislosti
↓
Patchujeme známé CVE
↓
Jsme v bezpečí
Dnešní realita:
Je kompromitován vývojář
↓
Je kompromitováno CI/CD
↓
Legitimní balíček je publikován se škodlivým kódem
↓
Každý downstream konzument si ho nainstaluje
↓
V žádném kroku není potřeba jediná CVE
Skenování závislostí odpovídá na otázku „má tento kód známou chybu“. Miasma odhaluje úplně jinou otázku, na kterou většina bezpečnostních programů vůbec není připravena odpovědět: „důvěřuji lidem a automatizovaným systémům, kteří smějí publikovat kód do mého prostředí, právě teď, dnes?“
Příležitosti k detekci
Užitečnější než ptát se „jak to zastavit“ je zeptat se, kde měl obránce reálnou šanci si všimnout, že něco není v pořádku. Právě tady většina textů o Miasmě končí, a proto stojí za to projít to podrobněji.
Rychlost publikace. 23 verzí balíčků publikovaných v okně šesti sekund není něco, co dělá člověk. Každá organizace provozující vlastní mirror npm registru nebo sledující události veřejného registru u balíčků, na kterých závisí, by takové publikační dávky mohla automaticky označit. Jeden version bump je normální. Dvě desítky během sekund jsou signál samy o sobě, nezávisle na tom, co balíček skutečně obsahuje.
Změny dist-tagů bez version bumpu, o který si uživatelé řekli. Únos leo-sdk fungoval právě proto, že se latest přesunul na nižší, starší vypadající číslo verze (6.0.19), zatímco novější čistá verze (7.1.21) seděla pod jiným tagem. Jakýkoli nástroj, který porovnává dist-tagy balíčku v čase, a ne jen seznam jeho verzí, by zachytil latest ukazující ve verzovací posloupnosti dozadu, což téměř nikdy není legitimní chování.
Build artefakty, které neodpovídají zdrojovému kódu. Kompromitovaný balíček leo-sdk narostl z 10 kB souboru index.js v čisté verzi na 5 MB index.js v otrávené verzi, plus soubor binding.gyp, který nikde ve skutečném GitHub repozitáři projektu neexistuje. Porovnání toho, co je publikováno v registru, s tím, co je commitnuté ve správě verzí, balíček po balíčku, by to odhalilo okamžitě. Většina organizací toto porovnání nedělá vůbec.
Nečekané nativní buildy u čistě JavaScriptových balíčků. leo-sdk je JavaScriptové SDK bez legitimní potřeby nativní kompilace. Soubor binding.gyp, který se objeví u balíčku, jenž ho nikdy dřív neobsahoval nebo k němu nemá žádný věrohodný důvod, je silný signál anomálie sám o sobě, dávno předtím, než kdokoli zkoumá, co soubor skutečně dělá.
Nové workflow soubory bez odpovídajícího pull requestu. Workflow soubor s názvem „Run Copilot“, který se objeví v .github/workflows/ bez navázaného PR, bez review a s autorem, kterého nikdo nezná, je přesně ten typ změny, kvůli kterému existují branch protection a povinná review, pokud jsou na workflow souborech skutečně vynucována.
Odchozí provoz do čerstvě vytvořených GitHub repozitářů. Protože exfiltrace spoléhala na nově vytvořené veřejné repozitáře jako mrtvé schránky, CI runnery nebo vývojářské stroje volající odchozí API pro vytvoření nových repozitářů, nebo pushující do repozitářů, které před hodinou neexistovaly, představují detekovatelný a poměrně neobvyklý vzor chování.
Použití OIDC a tokenů mimo obvyklý vzor. GitHub OIDC token nebo npm publikační token použitý z IP rozsahu, workflow nebo časového okna, odkud nikdy dřív použit nebyl, je klasický signál anomálie identity, a k jeho zachycení není potřeba vědět nic o této konkrétní kampani.
Nic z toho nevyžaduje databázi CVE ani předchozí znalost Miasmy. Vyžaduje to skutečně sledovat, jak se ve vašem prostředí v čase pohybují důvěra, publikační chování a identita, ne jen to, co je v manifestu uvedené v jednom okamžiku.
Co by organizace měly udělat
Okamžitě
- Rotujte přihlašovací údaje v každém prostředí, které si nainstalovalo dotčený balíček, ale až po odstranění škodlivé verze a ověření, že zmizela i persistence, ne dřív.
- Aktualizujte nebo odstraňte dotčené verze balíčků napříč lockfily, cache, kontejnery a CI runnery, nejen v manifestu nejvyšší úrovně.
- Zrušte a znovu vydejte všechny GitHub tokeny, OIDC konfigurace nebo npm tokeny, které mohly být vystaveny.
- Pinujte GitHub Actions na hash commitu místo měnitelných verzovacích tagů.
Střednědobě
- Zaveďte allowlisty balíčků povolených v CI/CD a produkčních buildech.
- Vyžadujte provenance a podepisování balíčků tam, kde jsou k dispozici.
- Udržujte skutečný Software Bill of Materials (SBOM), ne jednorázový snapshot.
- Přidejte ochrannou lhůtu, než budou nově publikované verze balíčků v buildu považovány za důvěryhodné.
Dlouhodobě
- Průběžná validace toho, co ve vašem prostředí skutečně běží, ne periodické audity.
- Monitoring repozitářů a CI/CD na nečekané změny workflow nebo publikačního chování.
- Průběžná analýza útočných cest: nejen „je tento balíček zranitelný“, ale „kam by se někdo dostal, kdyby tento balíček byl škodlivý“.
- Monitoring identit vývojářů, protože v této kampani byla skutečným útočným povrchem právě identita.
Proč na tom Penetrify záleží
Miasma nebyla problém npm. Byla to problém identity. Problém CI/CD. Problém důvěry. Problém útočných cest.
Útočníci neobjevili zranitelnost. Objevili cestu od pracovní stanice jediného vývojáře k tisícům downstream systémů, a ta cesta vedla výhradně skrze vztahy, které většina bezpečnostních programů ve skutečnosti nikdy nesleduje: kteří lidé mohou publikovat kód, které tokeny mohou spustit deployment, které workflow běží bez dohledu s reálným přístupem do produkce.
Npm v12 zavírá konkrétní vektor spuštění, na který Miasma spoléhala. S problémem identity, který leží pod ním, nedělá nic. Jak to v souvislosti s nasazením npm v12 formuloval Moshe Siman Tov Bustan z OX Security: jakmile útočník ovládá přihlašovací údaje legitimního správce, blokování instalačních skriptů nepomůže, protože škodlivý kód přichází jako důvěryhodné, podepsané vydání.
To je celý argument tohoto článku, řečený jednodušeji, než bychom to dokázali my. Moderní zabezpečení softwarového dodavatelského řetězce se musí posunout za hranice skenování závislostí k průběžnému porozumění tomu, jak se vztahy důvěry vyvíjejí napříč repozitáři, build pipeline, identitami a produkčními prostředími, ne jen k tomu, jaké CVE existují v manifestu.
Zdroje
- The Hacker News: Miasma Malware Targets npm Packages and GitHub Actions in Supply Chain Attack
- Socket: Miasma Mini Shai-Hulud Hits LeoPlatform npm Packages and Go Ecosystem
- StepSecurity: Mass npm Supply Chain Attack: 20 Leo Platform Packages Compromised a Supply Chain Compromise: codfish/semantic-release-action
- Endor Labs: Shai-Hulud Strikes Leo Platform npm
- Corgea: Leo Platform npm packages compromised with Phantom Gyp Miasma toolkit
- Snyk: Node-gyp Supply Chain Compromise
- Datadog Security Labs: Shai-Hulud Goes Open Source
- The Register: Malware crew TeamPCP open-sources its Shai-Hulud worm on GitHub
- GitHub Changelog: Upcoming breaking changes for npm v12
- TechTimes: npm v12 Ships This Month, Blocking Install Scripts That Enabled Year of Supply Chain Attacks
