Security Blog

Не повинно бути нічого, що можна зібрати

#95

October 2, 2026 · By Marketing team

← All posts

Скомпрометований Bitwarden CLI зібрав SSH-ключі, хмарні облікові дані та npm-токени з 334 машин розробників. Справжня проблема не в тому, як шкідливий код потрапив усередину. А в тому, що кожен секрет лежав собі як звичайний файл і чекав, поки його прочитають. <<<CLV-SUBTITLE>>>

Учора скомпрометована версія CLI від Bitwarden зібрала SSH-ключі, облікові дані AWS, npm-токени, змінні середовища, історію shell та секрети Git із 334 машин розробників.

Сьогодні це був Bitwarden. Минулого місяця — Axios. До того — Checkmarx. Завтра це буде розширення для VS Code, або Acrobat, або формула Homebrew, або образ Docker. Вектор змінюється щотижня. Результат завжди однаковий.

Шкідливий код потрапляє на машину. Він читає ~/.ssh/. Він читає ~/.aws/credentials. Він читає ~/.npmrc. Він читає ~/.git-credentials. Він читає історію shell, змінні середовища, сховища паролів браузера. Пакує все це й надсилає на сервер C2.

І це працює. Щоразу.

Збір урожаю

Навантаження Bitwarden — 10-мегабайтний обфускований файл під назвою bw1.js — не намагалося зламати жодного шифрування. Це було не потрібно. Ось що воно зібрало, згідно з документацією Socket та Aikido:

  • SSH-ключі та відбитки хостів
  • Хмарні облікові дані AWS, GCP та Azure
  • Токени автентифікації npm
  • Облікові дані Git та віддалені URL-адреси
  • Змінні середовища
  • Історію shell
  • Автентифікацію Claude Code та конфігурації MCP

Далі воно використало викрадені npm-токени, щоб повторно опублікувати інші пакети, які підтримувала жертва, поширюючись далі. Жертви ставали векторами.

Нічого з цього не потребувало зламу шифрування. Кожен із цих секретів був файлом у файловій системі, доступним для читання будь-яким процесом, що запущений від імені користувача.

Це не історія про Bitwarden

Шифрування сховища Bitwarden не було зламано. Їхня архітектура з нульовим знанням витримала. Шкідливий код навіть не торкався сховища.

І не мусив.

Сховище захищає те, що всередині нього. Але SSH-ключі ніколи не були в сховищі. Облікові дані AWS ніколи не були в сховищі. npm-токени, облікові дані Git, ключі API у файлах .env — нічого з цього не зберігається в менеджерах паролів. Усе це лежить у dotfiles, у відкритому вигляді, на кожній машині розробника.

Атакувальник це зрозумів. Сховище — це замкнений сейф у будинку, де кожна шухляда відкрита.

Справжня поверхня атаки

Відкрийте термінал просто зараз. Подивіться, що є на вашій машині.

~/.ssh/id_ed25519 — ваш особистий ключ. Файл у відкритому вигляді.

~/.aws/credentials — ваш доступ до хмари. Файл у відкритому вигляді.

~/.npmrc — ваш токен публікації. Файл у відкритому вигляді.

~/.git-credentials — ваш доступ до репозиторію. Файл у відкритому вигляді.

~/.env у десятку директорій проєктів — ключі API, паролі баз даних, секрети підпису. Усі файли у відкритому вигляді.

Будь-який процес, запущений від вашого імені, може прочитати все це. Без підвищення привілеїв. Без експлойту. Достатньо cat.

Це типова конфігурація розробника у 2026 році. Ми кладемо паролі в зашифроване сховище, а все інше залишаємо відкритим.

Неправильне запитання

Після кожної атаки на ланцюг постачання індустрія ставить одне й те саме запитання: як не допустити потрапляння шкідливого коду?

Краща безпека CI/CD. Підписування коду. Сканування залежностей. Пісочниці для середовищ виконання. Усе це добре. Нічого з цього не є достатнім. Поверхня атаки занадто широка. Занадто багато векторів — менеджери пакетів, розширення браузера, плагіни IDE, застосунки OAuth, скомпрометовані інструменти збірки. Ви не можете закрити кожну точку входу.

Правильне запитання таке: коли шкідливий код неминуче отримує виконання на машині розробника, що він там знаходить?

Якщо відповідь — «сотні облікових даних у відкритому вигляді в передбачуваних місцях файлової системи», жодне зміцнення ланцюга постачання не має значення. Ви граєте в обороні на полі, де ворота за вашою спиною відкриті навстіж.

Не повинно бути нічого, що можна зібрати

Рішення — не краще виявлення шкідливого коду. Рішення — не пісочниця для npm install. Рішення — не швидше реагування на інциденти.

Рішення таке: секрети не повинні існувати як файли на диску.

SSH-ключі, що виводяться з апаратного забезпечення в момент автентифікації, — а не зберігаються в ~/.ssh/. Хмарні облікові дані, що видаються на кожну сесію з ідентичністю, прив'язаною до апаратного забезпечення, — а не записуються в ~/.aws/. Токени API з обмеженим обсягом прав, короткочасні та захищені апаратним ключем, — а не лежать у файлах .env.

Коли облікові дані існують лише всередині апаратного модуля безпеки та в тимчасовій пам'яті процесу під час використання, шкідливому коду немає чого читати. Немає файлу для витоку. Немає dotfile для збирання. Процес запускається, нічого не знаходить і рухається далі.

Це не теорія. Облікові дані, прив'язані до апаратного забезпечення, існують уже сьогодні. WebAuthn PRF може виводити криптографічні ключі з фізичного дотику до автентифікатора — ключі, які ніколи не потрапляють у файлову систему. Технологія вже є. Просто галузь ще не зробила її типовою.

Що робити зараз

Якщо Ви постраждали через компрометацію CLI Bitwarden:

  • Замініть кожні облікові дані на машині — SSH-ключі, токени хмари, npm-токени, ключі API, усе в dotfiles та змінних середовища
  • Перевірте, чи не були повторно опубліковані npm-пакети, які Ви підтримуєте
  • Проведіть аудит активності GitHub та робочих процесів CI/CD щодо несанкціонованих змін

Якщо Ви не постраждали — дії ті самі. Подивіться на свою машину. Порахуйте секрети у відкритому вигляді. Запитайте себе, що станеться, коли — не «якщо», а «коли» — щось шкідливе запуститься від Вашого імені.

Відповідь має бути: нічого. Не повинно бути нічого, що можна зібрати.