
SDK npm Tensorlake zostało zatrute, by wykradać poświadczenia agentów AI — i wymazać twój katalog domowy, jeśli unieważnisz token
- OrcaNOWOŚĆOrca: OrcaCyber Zero 1.52026-10-10$3.00 / $7.50 za 1 mln tokenów · 56 tok/s
- openaiOpenAI: GPT-6.1 Sol2026-09-2952Inteligencja
- anthropicAnthropic: Claude Sonnet 5.52026-09-2856Inteligencja
- typesafeTypeSafe: Jev 1.132026-09-24$0.04 / $0.00 za 1 mln tokenów · 993 tok/s
- OpenAIOpenAI: GPT-6 Luna2026-09-2238Inteligencja
- OpenAIOpenAI: GPT-6 Sol2026-09-2248Inteligencja
- AnthropicAnthropic: Claude Opus 5.52026-09-2258Inteligencja
- xAIGrok 4.72026-09-2146Inteligencja
- OrcaOrca: OrcaCyber Zero 1.02026-09-17$3.00 / $7.50 za 1 mln tokenów · 40 tok/s
- OrcaOrca: OrcaVerify Text 1.02026-09-16$2.00 / $0.00 za 1 mln tokenów · 2230 tok/s
- DeepSeekDeepSeek: DeepSeek V4.1 Flash2026-09-1040Inteligencja
- OpenAIOpenAI: GPT-6 Astra2026-09-0453Inteligencja77Kod
- GoogleGoogle: Gemini 3.8 Flash2026-09-0241Inteligencja76Kod
- AlibabaQwen: Qwen3.8 Max (0902)2026-09-0245Inteligencja76Kod
- AnthropicAnthropic: Claude Fable 5.12026-09-0153Inteligencja82Kod
- TencentTencent: Hy4 preview2026-08-28$0.83 / $2.50 za 1 mln tokenów · 57 tok/s
- AlibabaQwen: Qwen3.8 Flash2026-08-26$0.15 / $0.47 za 1 mln tokenów · 125 tok/s
- z-aiZ.ai: GLM 5.3 Flash2026-08-2642Inteligencja72Kod
- DeepSeekDeepSeek: DeepSeek V4 Flash Vision (Exp)2026-08-21$0.22 / $0.66 za 1 mln tokenów · 206 tok/s
- z-aiZ.ai: GLM 5.32026-08-1845Inteligencja75Kod
8 października 2026 r. zatrute wydanie tensorlake — zestaw SDK npm dla platformy Tensorlake, która uruchamia niezaufany kod generowany przez LLM w izolowanych piaskownicach — trafiło do rejestru npm. Wersja 0.5.144 została opublikowana o 01:12:07 UTC; badacze z Socket twierdzą, że oznaczyli je po około jedenastu minutach. Nie było to autoryzowane wydanie. Tensorlake podaje, że atakujący wypchnął kod bezpośrednio do firmowego repozytorium GitHub i opublikował go przez własny proces wydawniczy projektu, więc pakiet miał ważną proweniencję npm — podpisane poświadczenie pokazujące, gdzie został zbudowany, dla źródła, które zostało już zatrute. Firma twierdzi, że wersja była dostępna przez około 1 godzinę 40 minut, od 01:12 do 02:54 UTC, zanim npm ją usunął.
Ładunek nie wymagał importu ani działającego agenta. Hak preinstall w manifeście pakietu uruchamiał node lib/setup.mjs, zaciemniony loader, który wgrał na maszynę środowisko uruchomieniowe Bun i użył go do uruchomienia lib/Math_Symbol.js, 856 501-bajtowego programu kradnącego poświadczenia i samorozprzestrzeniającego się robaka. Każdy, kto wykonał zwykłą instalację tej jednej wersji, uruchomił go. Ponieważ był to latest tag pakietu, to właśnie tę wersję wybierała domyślna instalacja, dopóki pozostawała aktywna.
To, co czyni ten rekord wartym zachowania, to nie rozmiar ładunku — rodzina Shai-Hulud była już wcześniej dokumentowana. Jest nim lista celów. Obok tokenów npm i GitHub, poświadczeń AWS, sekretów Kubernetes i Vault, kluczy SSH, .env plików, haseł przeglądarek i portfeli kryptowalutowych, ten build w szczególności zbierał konfigurację narzędzi programistycznych AI i pliki MCP — te powiązane z Claude Code, Cursor, Kiro, Windsurf i Zed, według Socket. Zapisywał również własne .claude/settings.json i .vscode/tasks.json do repozytoriów, do których mógł dotrzeć, aby kod uruchomił się ponownie, gdy następnym razem programista otworzy ten projekt w Claude Code lub VS Code. To atak na łańcuch dostaw wymierzony prosto w maszyny, na których ludzie budują agentów.
Jak wydanie wydostało się z konta opiekuna
Socket, SafeDep i Aikido opublikowały 8 października własne analizy, a ich opisy mechanizmu są zgodne. Ocena wiarygodności tego rekordu w archiwum to A, nie jest on oznaczony jako sporny, a nic znalezionego w źródłach nie stoi w sprzeczności z żadną z nich.
Artykuł SafeDep śledzi osiem commitów w gałęzi main repozytorium między 01:20 a 03:57 UTC w dniu 7 października, przypisanych do konta administratora repozytorium i dokonanych przez interfejs webowy GitHub. Commit, który archiwum wskazuje jako pierwszy złośliwy, to 41b38f0, rewizja czterech plików z 7 października o 03:44:48 UTC, której komunikat brzmi "Add files via upload" i która nosi verified podpis GitHub — GitHub podpisuje commity tworzone w swoim własnym edytorze webowym, więc "verified" odnotowuje powierzchnię edycji, nie osobę. Ten commit nie dotknął żadnych plików poza typescript/lib/Math_Symbol.js i typescript/lib/setup.mjs, zgodnie z API GitHub: ładunek i nic więcej.
SafeDep przedstawia interpretację zachowania operatora, oznaczoną jako jego własne wnioskowanie: pierwsza edycja hooka preinstall zepsuła składnię JSON pliku, a dziewiętnaście minut później nastąpił commit naprawczy, co opisuje jako spójne z tym, że pliki edytuje osoba w przeglądarce, a nie skryptowy potok. Żadna publikacja Socket, SafeDep, Aikido, StepSecurity ani Tensorlake nie nazywa metody, za pomocą której przejęto konto opiekuna.
Atakujący nie potrzebował tokenu npm. SafeDep donosi, że konto uruchomiło ręcznie workflow projektu o nazwiepublish_npm.yaml 8 października o 00:08 UTC; dziennik kompilacji pokazuje pliki ładunku w opublikowanym archiwum tar. Wydanie użyłonpm trusted publishing, a siostrzane pakietytensorlake-native-* opublikowane w tym samym uruchomieniu mają ważne pochodzenie SLSA — pochodzenie autentycznie ważne dla kompilacji zatrutego kodu źródłowego. Wydanie ukazało się dwanaście minut po rozpoczęciu workflow.
Archiwum odnotowuje, że repozytorium było skompromitowane przez około 20 godzin, zanim doszło do publikacji — lukę, którą poniższa os czasu rozkłada commit po commicie — co jest zgodne z własnym oświadczeniem Tensorlake, że atakujący opublikował „poprzez nasz własny workflow wydawniczy".
Co zrobił payload po uruchomieniu

Ocena Socket wskazuje na zbieranie danych z lokalnych plików, środowisk CI, Kubernetesa i źródeł Vault, a także eksfiltrację, utrzymanie dostępu i wykonywanie zdalnie dostarczonego kodu. SafeDep odtworzył zdekodowany ładunek: lib/setup.mjs pobiera Bun 1.3.13 z oficjalnego wydania na GitHubie i używa go do uruchomienia robaka, a kończy działanie na runnerach CI — celem jest maszyna dewelopera, a nie agent budujący. SafeDep odkrył również, że ładunek zawiera zwykłą kopię tego samego loadera, którą umieszcza w innych pakietach i repozytoriach.
Ładunek wykorzystuje trzy warstwy obfuskacji, które SafeDep zdekodował bez uruchamiania próbki: tablicę ciągów obfuskatora, niestandardowy szyfr wykorzystujący sól svksjrhjkcejg — identyczną z tą zgłoszoną we wcześniejszym keyv incydencie — oraz AES-256-GCM na jedenastu osadzonych plikach, w tym skryptach, hookach i dwóch kluczach publicznych RSA. Jego pierwsza linia zawiera tag kompilacji WORMTAG='tensrlake', zapisany z błędem ortograficznym, i właśnie po tym SafeDep odróżnia tę kompilację od trwającej reinfekcji.
Poza konfiguracją narzędzi AI lista zbieranych danych jest szeroka i konkretna: ~/.claude.json oraz ~/.kiro/settings/mcp.json dla ustawień agenta; klucze SSH, pliki CLI chmur, .npmrc, .env, pliki Dockera i Kubernetes oraz historia powłoki; wallet.dat plus dane Exodus, Electrum i Ledger Live oraz rozszerzenia portfeli przeglądarki, takie jak MetaMask i Phantom; AWS STS, SSM Parameter Store i Secrets Manager; sekrety GitHub Actions odczytywane z pamięci procesu Runner.Worker; a także tokeny konta usługi Kubernetes i tokeny Vault. Pobrał binarkę dla konkretnej platformy z iseekaigogo[.]com/hbd/<platform> i uruchomił ją z argumentami „dump -b all -c password -f json” — argumentami zgodnymi z narzędziem HackBrowserData, choć SafeDep zauważa, że sama binarka nie została odzyskana, i określa tę identyfikację jako przypuszczenie. Robak — dodaje SafeDep — kończy działanie w przypadku rosyjskich ustawień regionalnych.
![A screenshot of a card titled 'Persistence, resolution, and the wipe trigger', kicked 'tensorlake@0.5.144 · staying power', subtitled 'The release was removed in under two hours; the implant it installed was built to outlive that.' Three columns sit side by side. 'Persistence: gh-token-monitor' lists a systemd user service on Linux, a LaunchAgent com.user.gh-token-monitor on macOS, a scheduled task with a PowerShell monitor on Windows, and files left behind in ~/.local/bin, ~/.config and %LOCALAPPDATA%. 'Endpoint resolution order' lists, in numbered order, the primary endpoint iseekaigogo[.]com:443/router; an Ethereum contract 0xb614155Fd88...1Df091B9; the public RPC endpoints that contract is read through, given as ~30 by Socket and 35 by SafeDep; signed GitHub commits found by the string thebeautifulmarchoftime; and public dead-drop repositories described as 'Shai-Hulud: Here We Go Again'. 'The dead-man switch' lists a poll of api.github.com/user every 60s, for 24 hours, firing on a 40x response to that token, with the effect rm -rf ~/ (advisory: home dir), armed only if the account has no orgs, and the order that matters: remove monitor, then revoke. A footer reads 'Per Socket's blog and SafeDep's analysis, with the C2 endpoint, the contract and the gh-token-monitor service confirmed in Tensorlake's advisory. Socket and SafeDep give different counts of the public RPC endpoints the contract is read through.'](https://cms.orcarouter.ai/api/media/file/3-1820.png)
Persystencja jest zamierzona. Socket napisał o ładunku: „Ta kombinacja rozszerza ryzyko poza pojedynczy skradziony klucz API", dodając, że „persystencja może pozwolić napastnikowi zachować dostęp po usunięciu zaatakowanej zależności". SafeDep donosi, że robak zatwierdza pliki hooków Claude Code i VS Code jako autor git claude i umieszcza przepływ pracy „Run Copilot", który zrzuca wszystkie sekrety repozytorium, a następnie usuwa przebieg i gałąź. Porada Tensorlake mówi deweloperom przeglądającym swoje logi, aby szukali gałęzi o nazwie dependabot/github_actions/format/setup-formatter oraz zatwierdzeń autorstwa tej samej tożsamości.
Rozprzestrzenianie opiera się na skradzionych tokenach, a nie na drugiej podatności. Socket twierdzi, że robak wylicza pakiety powiązane z tożsamością publikowania ofiary, tworzy proweniencję Sigstore i publikuje ponownie zatrute wersje. SafeDep dodaje szczegół, że wewnątrz CI dodaje zależność git i podpisuje swoje dane wyjściowe za pomocą Fulcio i Rekor — więc proweniencja pakietu, który opublikuje jako następny, jest tak samo wiarygodna, jak proweniencja wersji 0.5.144.
Dwadzieścia godzin przed publikacją
Luka między pierwszym wrogim commitem a wydaniem to część osi czasu, która wyjaśnia, jak zatruty pakiet zaczął mieć prawidłowe pochodzenie. Wszystkie czasy podano w UTC; czasy commitów pochodzą od SafeDep i z GitHub API, a czasy publikacji, usunięcia i ostrzeżenia pochodzą od Tensorlake.

Analizując całość: pliki payloadu trafiły do głównej gałęzi repozytorium 7 października, wersję ustawiono na 0.5.144 o 03:57 tego ranka, a nic nie zostało opublikowane, dopóki konto nie uruchomiło ręcznie procesu wydania o 00:08 następnego dnia. Skompromitowany kod źródłowy pozostawał w gałęzi przez około dwadzieścia godzin, zanim zbudował go własny potok projektu. To całość ataku na ścieżkę wydania — żadnego sfałszowanego poświadczenia, żadnego ponownie opublikowanego tarballa. Informacje o pochodzeniu były zgodne z prawdą w odniesieniu do kompilacji kodu, którego nigdy nie powinno było być w gałęzi.
Przełącznik bezpieczeństwa
Ta część tego incydentu, która nie ma precedensu we wcześniejszych naruszeniach bezpieczeństwa npm, dotyczy tego, co dzieje się po tym, jak ofiara zareaguje prawidłowo. Jeśli ukradziony token GitHub należy do konta bez organizacji, jak podaje SafeDep, robak instaluje gh-token-monitor: usługę, która odpytuje api.github.com/user za pomocą tego ukradzionego tokenu co 60 sekund przez 24 godziny. Gdy GitHub zwraca kod 40x — co ma miejsce w momencie unieważnienia tokenu — monitor uruchamia procedurę obsługi dostarczoną przez atakującego i usuwa katalog domowy użytkownika.
Socket opisuje ten sam komponent jako wykorzystujący monitor PowerShell, który utrzymuje się przez zaplanowane zadanie ONLOGON, wykonujący dostarczony przez atakującego handler poprzez Invoke-Expression, i zauważa, że kod zawiera dosłowny ciąg „IfYouRevokeThisTokenItWillWipeTheComputerOfTheOwner”, widziany we wcześniejszych falach Shai-Hulud. SafeDep nazywa ten handler rm -rf ~/. Sformułowanie Socket wprost mówi, że uruchamia się to niezależnie od tego, gdzie następuje odwołanie; monitor jest lokalny, a odwołanie nie. Wszystkie cztery źródła — Socket, SafeDep, StepSecurity oraz własny biuletyn Tensorlake — podają tę samą kolejność działań: najpierw usuń monitor, potem odwołaj.
Co jest ustalone, a co tylko wywnioskowane
Archiwum odnotowuje brak potwierdzonych szkód dla tego wpisu, a źródła to potwierdzają, a nie tylko nie przeczą temu.
• Tensorlake podaje, że ta wersja nie jest używana. W swoim biuletynie firma podaje, że monitoruje użycie SDK za pomocą nagłówków user-agent i „nie odnotowała żadnego użycia tej wersji od czasu jej wydania”. To oświadczenie dostawcy dotyczące jego własnej telemetrii, a nie zweryfikowana liczba.
• Liczba pobrań nie jest liczbą infekcji. Socket podaje, że pakiet ma około 12 000 pobrań tygodniowo i zauważa, że opisuje to ogólne użycie pakietu, a nie pobrania złośliwej wersji; SafeDep podaje około 106 000 pobrań miesięcznie dla tego samego pakietu. Żadna z tych liczb nie dowodzi, że 0.5.144 kiedykolwiek gdzieś uruchomiono. Okno oznaczonego wydania w Socket i dwugodzinne okno Tensorlake są spójne z wersją, którą usunięto, zanim się rozprzestrzeniła.
• Własne błędy payloadu mogły go ograniczyć. SafeDep znalazł dwa: ścieżka propagacji npm potrzebuje ./dist/Math_Symbol.js na dysku i zatrzymuje się bez niego, a wstawiony loader szuka ai_init.js, podczas gdy robak zapisuje math_init.js. SafeDep określa te ustalenia jako ograniczenia rozprzestrzeniania, a artykuł traktuje je jako interpretację kodu przez jedną z analiz, a nie jako gwarancję, że nic się nie rozprzestrzeniło.
• Poświadczenie pochodzenia jest prawdziwe. To nie jest sporne twierdzenie: npm provenance rejestruje, gdzie pakiet został zbudowany i przez jaki workflow, a w tym przypadku zapisano prawdę — własny workflow wydania projektu, budujący zatrute źródło. Biuletyn Tensorlake stwierdza to wprost: „pakiet posiada ważne npm provenance”. Socket ujmuje to samo prosto, zauważając, że provenance „mówi, gdzie pakiet został zbudowany. Nie mówi, że kod jest bezpieczny.”
Kilka krążących szczegółów to twierdzenia oparte na pojedynczej analizie i tak należy je odczytywać. Konkretny mechanizm, za pomocą którego atakujący przejął konto opiekuna, nie został opublikowany przez żadną z firm prowadzących dochodzenie ani przez Tensorlake. Adres kontraktu Ethereum i jego rola w rozwiązywaniu adresu endpointu pojawiają się w relacjach SafeDep i Socket — Socket twierdzi, że ładunek rozwiązuje swój endpoint za pośrednictwem kontraktu Ethereum, korzystając z około 30 publicznych punktów końcowych RPC z mechanizmem awaryjnym opartym na GitHubie, natomiast SafeDep podaje liczbę punktów RPC jako 35 i informuje, że 8 października kontrakt zwrócił iseekaigogo.com — a Tensorlake potwierdza endpoint i kontrakt w swoim biuletynie. Dokładna liczba punktów RPC różni się między tymi dwoma opracowaniami; sam projekt już nie.
Jedną lukę w publicznym zapisie warto wskazać wprost. Żadne ze źródeł przeanalizowanych na potrzeby tego artykułu nie donosi o potwierdzonym zakażeniu wtórnym — innym pakiecie lub repozytorium zatrutym przez robaka przy użyciu poświadczeń skradzionych z tego pakietu. Kod propagacji istnieje i SafeDep go przeczytał; nie wiadomo, czy spowodował drugą ofiarę.
Co się potem zmieniło?
Reakcja była szybsza i lepiej skoordynowana niż sam incydent.
• Ta wersja zniknęła. Według Tensorlake była dostępna od 01:12 do 02:54 UTC 8 października; SafeDep podaje, że npm ją usunął. Przy bezpośrednim odpytaniu rejestru npm 10 października na potrzeby tego artykułu 0.5.144 nie pojawia się już wśród opublikowanych wersji pakietu, a najnowszy tag pakietu to 0.5.148. Biuletyn Tensorlake wskazuje programistom wersję 0.5.143 jako ostatnią nieobjętą problemem.
• Biuletyn opublikowano wraz z poprawką. W biuletynie GHSA-8g63-53c9-65j2 firmy Tensorlake stwierdzono, że pakiety z PyPI i crates.io o nazwie tensorlake oraz tensorlake CLI nie zostały objęte — dotyczyło to tylko pakietu npm — a wersje 0.5.143 i wcześniejsze nie są objęte. SafeDep podaje, że opiekunowie cofnęli zmiany w źródle w żądaniu scalenia #1016 i wydali 0.5.145.
• Wątek ujawnienia jest niezwykle kompletny. Badacz z StepSecurity Ashish Kurmi otworzył zgłoszenie na GitHubie #1014 dnia 8 października o 01:22:02 UTC — około dziesięć minut po publikacji — wskazując na własne opracowanie StepSecurity na temat tego, co nazywa „robakiem hostage token”. Oliver Smith z Aikido skomentował, że ładunek został wprowadzony w commicie 41b38f0 i zidentyfikował go jako nowy program kradnący informacje Shai-Hulud. Opiekun David Lorenzo — tożsamość opiekuna wymieniona w pakiecie npm jako calavera — odpowiedział 9 października, potwierdzając biuletyn bezpieczeństwa i zamykając zgłoszenie jako ukończone tego samego dnia. Sam tytuł zgłoszenia odzwierciedla dowody: początkowo był raportem „potencjalnie złośliwym”, a do czasu zamknięcia przemianowano go tak, by bez zastrzeżeń opisywać ładunek jako złośliwy.
• Kampania, do której to należy, jest większa niż ten pakiet. Zarówno Socket, SafeDep, jak i Aikido umieszczają wydanie Tensorlake w fali ChainDrop / Mini Shai-Hulud po raz pierwszy udokumentowanej na początku sierpnia 2026 r., której ofiarami w npm były między innymi keyv, cacheable i powiązane pakiety. W komunikacie doradczym Tensorlake napisano to samo, powołując się na Socket, SafeDep i Aikido.
Wskazówka Socket dla każdego, kto zainstalował tę wersję, jest taka, że host należy uznać za skompromitowany: sprawdź pliki lock, manifesty i dzienniki kompilacji pod kątem tej wersji; usuń gh-token-monitorusługę przed unieważnieniem jakiegokolwiek tokenu; następnie przeprowadź rotację poświadczeń z czystej maszyny. Zalecenie Tensorlake dodaje tę samą kolejność i sugeruje sprawdzenie rejestrów pakietów i repozytoriów, do których ujawnione tokeny mogłyby zapisywać, pod kątem nieoczekiwanych wydań. Artykuł Aikido zaleca ustawienie ignore-scripts=true w .npmrc, aby zablokować hooki instalacyjne, i uznanie każdej maszyny, na której uruchomił się hook, za w pełni skompromitowaną.
To jeden rekord, zgłoszony przez innych i cytowany tutaj za nimi. Pozostałe udokumentowane incydenty z agentami, każdy z własnymi źródłami, wagą, stopniem pewności i oznaczeniem sporności, znajdują się w archiwum incydentów AI — dzięki temu kompromitację łańcucha dostaw wymierzoną w narzędzia agentowe można odczytać obok reszty tego, co faktycznie się wydarzyło.
