Руководства по безопасности
Черви в цепочке поставок npm: как учётные данные крадут при установке пакета и как защититься
В августе 2026 года ChainDrop меньше чем за четыре часа заразил 444 пакета npm — и они вышли с действительной подписью provenance. Червь собирает учётные данные при установке, а затем украденным токеном GitHub копирует ваши приватные репозитории в публичные. Что действительно останавливает такую атаку.
Для кого эта статья: для всех, кто разрабатывает с npm или pnpm, хранит код на GitHub или развёртывает из CI. Она основана на публичных исследованиях компаний и лабораторий и не содержит шагов эксплуатации или образцов.
Что произошло (ChainDrop, август 2026)
4 августа 2026
Был взломан аккаунт GitHub мейнтейнера популярных пакетов для кэширования. Атакующий запустил существующие в проектах процессы выпуска релизов в GitHub Actions и опубликовал заражённые версии в npm.В течение четырёх часов
Заражены 444 пакета и 2 212 версий, включая пакеты с суммарным числом загрузок более 500 миллионов в неделю.При установке
Хуки установки собирали учётные данные npm, GitHub, облаков (AWS/GCP/Azure), ключи SSH, данные Kubernetes и CI/CD — по опубликованному анализу, в том числе короткоживущие токены OIDC, извлечённые из памяти раннеров CI.Затем
Украденные учётные данные использовались, чтобы переопубликовать все пакеты, которые жертва могла публиковать (самораспространение), а собранные секреты выгружались в публичные репозитории GitHub, созданные атакующим.
Главный вред в этом семействе: ваши приватные репозитории становятся публичными
Черви семейства Shai-Hulud используют украденный токен GitHub, чтобы скопировать приватные репозитории жертвы в публичные — сообщалось об именах, оканчивающихся на -migration. GitHub взломан не был. Токен, снятый с вашего ноутбука или раннера CI, делает это как обычное разрешённое действие с вашими правами. Поэтому «подождать, пока платформа исправит» здесь не защита.
Почему атаку не остановили
Добавление зависимости / установка в CI
↓ preinstall / postinstall запускаются автоматически
Произвольный код на вашей машине или раннере
↓ собираются секреты npm / GitHub / облаков / SSH / CI
Обычные действия с украденными токенами
приватные репозитории копируются в публичные / пакеты переопубликуются для распространения
Что не помогло
- Подписи и provenance — выданы законно под правами мейнтейнера, поэтому проверка прошла
- «Это большой популярный пакет» — заражённые были именно такими
- Только фиксация версий — при чистой установке или следующем обновлении вы всё равно её получите
- Ожидание исправления от платформы — использовались действительные токены и публичные API
Что помогает
- Скрипты установки отключены по умолчанию — код не выполняется
- Пауза перед переходом на новый релиз — вы пропускаете период между публикацией и удалением
- Короткоживущие токены с узкими правами — ограничивают, что и как долго может сделать украденный токен
- Ограничение исходящего трафика на раннерах CI — закрывает путь для выгрузки данных
Пять дел на сегодня
Проверьте свой lock-файл
Убедитесь, нет ли в нём версий, о заражении которых сообщалось (например, keyv@6.0.0, flat-cache@6.1.24, file-entry-cache@11.1.6). Чистый результат — хорошая новость, но шаги со второго готовят вас к следующей похожей атаке, поэтому продолжайте.
Отключите скрипты установки по умолчанию
Переведите CI на npm ci --ignore-scripts; для pnpm задайте ignore-scripts=true в .npmrc и явно разрешите только те зависимости, которым действительно нужна сборка. Это самое ценное изменение, потому что оно убирает этап выполнения кода, на котором держится эта атака.
Выжидайте несколько дней после релиза
Не берите релиз в момент выхода — достаточно паузы от 3 до 7 дней. Когда между публикацией и удалением проходят часы или дни, как здесь, одно ожидание уже позволяет атаку пропустить. Если вы используете автоматические PR с обновлениями, заложите эту задержку в их настройки.
Добавлено 5 сентября 2026: это больше не обязано держаться на дисциплине. Официальное руководство по безопасности Node.js среди мер против атак на цепочку поставок называет паузу для зависимостей через --min-release-age (npm v11.10.0+), чтобы не устанавливать недавно опубликованные пакеты. Если это можно сделать настройкой, а не дисциплиной, сделайте настройкой. Процедура, которая зависит от чьей-то памяти, в загруженный день обычно пропускается.
Проведите инвентаризацию токенов, сократите срок жизни и права
Замените классические персональные токены GitHub на fine-grained (с детальными правами), сократите срок действия и ограничьте их нужными репозиториями. Не оставляйте токены публикации npm в CI. Обращение с ключами и секретами разобрано в статьях чем опасны .env и API-ключи и минимальные привилегии для SSH-ключей. Цель — чтобы украденный токен мог причинить мало вреда.
Проверьте свой аккаунт GitHub
Ищите публичные репозитории, которые вы не создавали (имена на -migration, незнакомые описания), процессы GitHub Actions, которые вы не добавляли, исполняемые настройки в .vscode/tasks.json или .claude/, а также незнакомые API-ключи и SSH-ключи. Об автоматическом отслеживании известных уязвимостей в зависимостях — в статье начало работы с osv-scanner.
Если подозреваете заражение, соблюдайте порядок
Исследователи подчёркивают один момент, который стоит повторить: удалите оставшиеся на машине резидентные компоненты (скрипты, следящие за токенами, и подобное) ДО отзыва токенов. Если сделать наоборот, резидентная часть может отреагировать на отзыв. Примерный порядок:
1. Отключитесь от сети
2. Удалите механизмы закрепления и подозрительные файлы
3. Отзовите и перевыпустите в порядке npm → GitHub → облака → SSH → Kubernetes
4. Удалите node_modules и кэши и выполните чистую переустановку
5. Проверьте свои публичные репозитории и историю публикации пакетов
Если логов нет, ответ — «неизвестно», а не «чисто». Действуйте так, как будто вас взломали.
Взгляд этого сайта: подпись подтверждает происхождение, а не безопасность
Подписи и provenance годами были главной рекомендацией по защите цепочки поставок — и эта кампания их обошла. Это не удивительно: подпись говорит, кто опубликовал пакет, а не то, безопасно ли его содержимое. Действительная подпись со взломанного аккаунта одновременно действительна и опасна. Поэтому мы рассматриваем provenance не как меру, которая делает вас защищёнными, а как инструмент расследования, чтобы оценить масштаб после инцидента. Профилактика держится на двух других вещах: не выполнять чужой код при установке и не оставлять секреты там, где этот код запускается.
Источники
- Unit 42 (Palo Alto Networks) — ChainDrop: Inside a Self-Propagating npm Worm (распространение, собираемые учётные данные, индикаторы)
- StepSecurity — ChainDrop npm Worm (индикаторы обнаружения и порядок устранения)
- Elastic Security Labs — CHAINDROP worm hits 400+ npm packages
- Node.js, «Security Best Practices» — nodejs.org (векторы атак на цепочку поставок и меры:
--ignore-scripts, lock-файлы,npm ciи пауза--min-release-age; проверено 5 сентября 2026) - SecurityWeek — Over 400 NPM Packages Infected in ChainDrop Supply Chain Attack (масштаб и последовательность)
- Wiz — Shai-Hulud npm Supply Chain Attack (техника копирования приватных репозиториев в публичные)
Что прочитать дальше
- Случай 2026 года: цепочка TanStack, Nx Console и GitHub — что проверить разработчикам (на английском)
- Практика: автоматическое отслеживание CVE в зависимостях с osv-scanner / останавливаем секреты при коммите с gitleaks
- Основы: чем опасны .env и API-ключи / минимальные привилегии для SSH-ключей
- Сравнение: собственный Git-сервер или GitHub — что безопаснее
- Уязвимости, приходящие с зависимостями: загрязнение прототипа в Node.js (считается, даже если merge написан в зависимости)
- Термины: что такое вредоносное ПО
- Закономерность: утечки 2026 года шли через действительные учётные данные (на английском; та же форма — украденный токен выполняет обычные действия)
FAQ
QКак запуск npm install может украсть мои учётные данные?
Пакеты могут содержать скрипты, которые выполняются автоматически при установке (preinstall / postinstall). Поэтому добавить зависимость — то же самое, что разрешить этому коду выполняться с вашими правами. Именно так ChainDrop собирал учётные данные npm, GitHub, облаков, SSH и CI/CD.
QЧто значит «приватные репозитории становятся публичными»?
Черви этого семейства используют украденный токен GitHub, чтобы скопировать приватные репозитории жертвы в публичные — сообщалось об именах, оканчивающихся на -migration. Сам GitHub взломан не был: токен, взятый с вашего компьютера или из вашего CI, выполняет действие с вашими же правами. Поэтому ожидание исправления со стороны платформы вас не защитит.
QРазве подписанные пакеты с provenance не безопасны?
Именно эту защиту здесь и обошли. Атакующий с правами мейнтейнера запустил существующий процесс выпуска релизов проекта, и заражённые версии вышли с действительной подписью provenance. Подпись подтверждает, кто опубликовал пакет, а не то, что его содержимое безопасно. Действительная подпись со взломанного аккаунта остаётся действительной.
QЧто самое полезное можно сделать уже сегодня?
Две вещи: отключить скрипты установки по умолчанию (npm ci --ignore-scripts или ignore-scripts=true для pnpm) и не брать новые релизы сразу — подождать несколько дней. Первое вообще не даёт коду выполниться; второе позволяет пропустить самый опасный период — часы или дни между публикацией и удалением.