Безопасность

Hermes Agent разработан с использованием модели глубокоэшелонированной защиты. На этой странице рассматриваются все границы безопасности — от утверждения команд до изоляции контейнера и авторизации пользователей на платформах обмена сообщениями.

Обзор

Модель безопасности имеет восемь уровней:

  1. Авторизация пользователя — кто может разговаривать с агентом (белые списки, соединение DM)
  2. Одобрение опасного командования — участие человека в разрушительных операциях
  3. Безопасность записи файлов — список запретов и дополнительная изолированная среда записи для write_file/patch
  4. Изоляция контейнера — Docker/Singularity/модальная песочница с усиленными настройками.
  5. Фильтрация учетных данных MCP — изоляция переменных среды для подпроцессов MCP.
  6. Сканирование контекстных файлов — оперативное обнаружение внедрения в файлы проекта.
  7. Межсессионная изоляция — сеансы не могут получить доступ к данным или состоянию друг друга; Пути хранения заданий cron защищены от атак с обходом пути
  8. Очистка ввода — параметры рабочего каталога в бэкэнде терминального инструмента проверяются на соответствие списку разрешенных, чтобы предотвратить внедрение оболочки.

Утверждение опасной команды

Прежде чем выполнить любую команду, Hermes сверяет ее с тщательно подобранным списком опасных шаблонов. Если совпадение найдено, пользователь должен явно одобрить его.

Режимы одобрения

Система утверждения поддерживает три режима, настроенных через approvals.mode в ~/.hermes/config.yaml:

approvals:
  mode: smart                     # smart | manual | off
  timeout: 300                    # seconds to wait for user response (default: 300)
  cron_mode: deny                 # deny | approve — what cron jobs do when they hit a dangerous command
  mcp_reload_confirm: true        # /reload-mcp asks before invalidating the MCP tool cache
  destructive_slash_confirm: true # /clear, /new, /reset, /undo prompt before discarding state

Полный комплект ключей:

Ключ По умолчанию Что он контролирует
режим умный Политика одобрения опасных команд оболочки — см. таблицу ниже.
тайм-аут 300 Секунды Hermes ожидает ответа об утверждении, прежде чем истечет время ожидания.
cron_mode отрицать Как задания cron ведут себя бездумно, когда вызывают опасную командную строку. deny блокирует команду (агент должен найти другой путь); approve автоматически одобряет все в контексте cron.
mcp_reload_confirm правда Если это правда, /reload-mcp запрашивает перед пересборкой набора инструментов MCP. Перестроение делает недействительным кэш подсказок поставщика (схемы инструментов находятся в системной подсказке), поэтому следующее сообщение повторно отправляет полные входные токены. Пользователи, которые нажимают Всегда одобрять, переключают этот ключ на «ложь».
destructive_slash_confirm правда Если установлено значение true, деструктивные команды слэша сеанса (/clear, /new, /reset, /undo) запрашивают перед отменой состояния диалога. Диалоговое окно с тремя опциями (Однократное одобрение/Всегда утверждать/Отмена), направляемое через встроенные кнопки «да/нет» в Telegram, Discord и Slack; резервный текст в другом месте. Пользователи, которые нажимают Всегда одобрять, переключают этот ключ на «false». TUI использует собственное модальное наложение (задайте HERMES_TUI_NO_CONFIRM=1, чтобы отказаться от него).
Режим Поведение
умный (по умолчанию) Используйте вспомогательный LLM для оценки риска. Команды с низким уровнем риска (например, python -c "print('hello')") автоматически одобряются только для этой команды. Действительно опасные команды автоматически отклоняются. Сомнительные случаи переходят к подсказке вручную.
руководство Всегда запрашивайте у пользователя подтверждение опасных команд.
выкл. Отключите все проверки одобрения — это эквивалентно запуску с --yolo. Все команды выполняются без подсказок.
Установка approvals.mode: off отключает все запросы безопасности. Используйте только в доверенных средах (CI/CD, контейнеры и т. д.).
### Режим ЙОЛО

Режим YOLO обходит все запросы на одобрение опасных команд для текущего сеанса. Его можно активировать тремя способами:

  1. Флаг CLI: запустите сеанс с помощью hermes --yolo или hermeschat --yolo
  2. Команда косой черты: введите /yolo во время сеанса, чтобы включить или выключить ее.
  3. Переменная среды: установите HERMES_YOLO_MODE=1

Команда /yolo представляет собой переключатель — каждое ее использование включает или выключает режим:

> /yolo
  ⚡ YOLO mode ON — all commands auto-approved. Use with caution.

> /yolo
  ⚠ YOLO mode OFF — dangerous commands will require approval.

Режим YOLO доступен как в сеансах CLI, так и в сеансах шлюза. Внутри он устанавливает переменную среды HERMES_YOLO_MODE, которая проверяется перед каждым выполнением команды.

Когда YOLO активен, Hermes показывает два постоянных визуальных напоминания, поэтому трудно забыть, что запросы на одобрение игнорируются:

Жесткий черный список (всегда на этаже)

Некоторые команды настолько катастрофичны — необратимые очистки файловой системы, форк-бомбы, прямая запись на блок-устройства — что Hermes отказывается выполнять их независимо от:

Черный список находится этажом ниже --yolo. Он срабатывает до того, как уровень утверждения увидит команду, и флаг переопределения отсутствует. Рассматриваемые на данный момент шаблоны (не исчерпывающие; синхронизируются с tools/approval.py::UNRECOVERABLE_BLOCKLIST):

Узор Почему это жестко
rm -rf / и очевидные варианты Очищает корень файловой системы
rm -rf --no-preserve-root / Явный вариант «да, я имею в виду root»
:(){:\|:& };: (бомба-вилка) Привязывает хост до перезагрузки
mkfs.* на смонтированном корневом устройстве Форматирует живую систему
dd if=/dev/zero of=/dev/sd* Обнуляет физический диск
Передача ненадежных URL-адресов в sh на верхнем уровне rootfs Вектор атаки с удаленным выполнением кода слишком широк, чтобы его можно было одобрить

Если вы попадете в черный список, вызов инструмента вернет агенту пояснительную ошибку, и ничего не запустится. Если законному рабочему процессу требуется одна из этих команд (например, вы являетесь оператором конвейера очистки и переустановки), запустите ее вне агента.

Пользовательские правила запрета (approvals.deny)

Жесткий черный список фиксирован и поставляется в виде кода. approvals.deny является его редактируемым пользователем аналогом: список шаблонов glob, которые безоговорочно блокируют соответствующие команды терминала — перед проверяются --yolo, /yolo и approvals.mode: off. Используйте его для запуска yolo-with-Exceptions: «позволяйте агенту делать все, кроме этих конкретных вещей, когда-либо».

approvals:
  deny:
    - "git push --force*"
    - "*curl*|*sh*"
    - "dd if=* of=/dev/*"

Подробности:

Как и остальная часть конфигурации утверждения, изменения вступают в силу немедленно (кеш конфигурации имеет ключ mtime) — перезапуск сеанса не требуется.

📝 Note

Модель угроз Правила запрета — это ограждение от честного, но неправильного агента, та же модель угроз, что и детектор опасных шаблонов. Они не являются «песочницей» против заведомо состязательного процесса — для этого используйте изолированный бэкэнд (Docker, Modal) или среду с ограниченным исходящим доступом.

Тайм-аут одобрения

При появлении опасной командной строки у пользователя есть настраиваемое время для ответа. Если в течение таймаута не получен ответ, команда по умолчанию отклонена (закрытие при сбое).

Настройте таймаут в ~/.hermes/config.yaml:

approvals:
  timeout: 300  # seconds (default: 300)

Что вызывает одобрение

Следующие шаблоны вызывают запросы на одобрение (определенные в tools/approval.py):

Узор Описание
rm -r / rm --recursive Рекурсивное удаление
рм... / Удалить в корневом пути
chmod 777/666 / o+w / a+w Разрешения на запись для всех/других
chmod --recursive с небезопасными разрешениями Рекурсивный мир/записываемый другими (длинный флаг)
chown -R root / chown --recursive root Рекурсивное управление root
мкфс Формат файловой системы
дд, если= Копия диска
> /dev/sd Записать на блокировку устройства
УДАЛЕНИЕ ТАБЛИЦЫ/БАЗЫ ДАННЫХ SQL ПАДЕНИЕ
УДАЛЕНИЕ ОТ (без ГДЕ) SQL DELETE без WHERE
УСЕЧАТЬ ТАБЛИЦУ SQL УСЕЧЕНИЕ
> /etc/ Перезаписать конфигурацию системы
systemctl стоп/перезапуск/отключение/маска Остановить/перезапустить/отключить системные службы
убить -9 -1 Убить все процессы
pkill -9 Принудительное уничтожение процессов
Выкройки вилочных бомб Вилочные бомбы
bash -c / sh -c / zsh -c / ksh -c Выполнение команд оболочки через флаг -c (включая комбинированные флаги, такие как -lc)
python -e / perl -e / ruby -e / node -c Выполнение скрипта через флаг -e/-c
завиток... \| sh/wget...\| ш Перенаправить удаленный контент в оболочку
bash <(curl...) / sh <(wget...) Выполнить удаленный скрипт через подстановку процесса
tee в /etc/, ~/.ssh/, ~/.hermes/.env Перезаписать конфиденциальный файл через тройник
> / >> в /etc/, ~/.ssh/, ~/.hermes/.env Перезаписать конфиденциальный файл с помощью перенаправления
xargs rm xargs с rm
найти -exec rm / найти -удалить Находка с разрушительными действиями
cp/mv/install в /etc/ Скопировать/переместить файл в конфигурацию системы
sed -i / sed --in-place в /etc/ Редактирование конфигурации системы на месте
pkill/killall Hermes/шлюз Предотвращение самоликвидации
gateway run с &/disown/nohup/setsid Предотвращает запуск шлюза за пределами диспетчера служб
docker stop/kill/restart, docker Compose down/stop/kill/restart Жизненный цикл контейнера (также отслеживает глобальные флаги и docker-compose)
docker -H/--host/--context, DOCKER_HOST=/DOCKER_CONTEXT= Перенаправление демона Docker — команда нацелена на другой (часто удаленный) демон
использование контекста докера Переключает демон по умолчанию для всех будущих команд Docker
podman --remote/-r/--url/--connection/--identity, CONTAINER_HOST= Перенаправление удаленного демона Podman
Обход контейнера: при работе в бэкэндах docker, singularity, modal, daytona или vercel_sandbox проверки опасных команд пропускаются, поскольку контейнер сам по себе является границей безопасности. Деструктивные команды внутри контейнера не могут нанести вред хосту.
### Поток утверждения (CLI)

В интерактивном интерфейсе командной строки опасные команды отображают встроенный запрос на одобрение:

  ⚠️  DANGEROUS COMMAND: recursive delete
      rm -rf /tmp/old-project

      [o]nce  |  [s]ession  |  [a]lways  |  [d]eny

      Choice [o/s/a/D]:

Четыре варианта:

Поток утверждения (шлюз/обмен сообщениями)

На платформах обмена сообщениями агент отправляет в чат сведения об опасной команде и ждет ответа пользователя:

– Ответьте да, да, одобрить, ок или идти, чтобы одобрить. – Чтобы отклонить, ответьте нет, n, отклонить или отменить.

Переменная среды HERMES_EXEC_ASK=1 автоматически устанавливается при запуске шлюза.

Постоянный белый список

Команды, одобренные с помощью «всегда», сохраняются в ~/.hermes/config.yaml:

# Permanently allowed dangerous command patterns
command_allowlist:
  - rm
  - systemctl

Эти шаблоны загружаются при запуске и автоматически одобряются во всех последующих сеансах.

💡 Tip

Используйте hermes config edit, чтобы просмотреть или удалить шаблоны из вашего постоянного белого списка.

История разрешений на добычу полезных ископаемых («подсказывают утверждения Hermesа»)

Вместо того, чтобы отвечать на одни и те же запросы сеанс за сеансом, вы можете прошлые решения об утверждении в предложениях по белому списку:

hermes approvals suggest            # dry run — prints a numbered proposal
hermes approvals suggest --apply 1,3  # merge picks into command_allowlist
hermes approvals suggest --json     # machine-readable output

Команда сканирует базу данных сеанса (~/.hermes/state.db) на наличие классифицированные как опасные команды, которые фактически выполнялись, т. е. команды, которые вы утверждено — объединяет их в шаблоны (git push * или Опасный класс ключ для составных команд) и ранжирует их по частоте одобрения:

Proposed command_allowlist additions (from approval history, last 90 days):

  1. git push *    — approved 14x
  2. docker restart/stop/kill (container lifecycle)    — approved 9x (class key)

Правила безопасности:

Полезные флаги: --days N (окно истории, по умолчанию 90), --min-count N (минимальное количество разрешений для соответствия, по умолчанию 2), --limit N и --db PATH.

Безопасность записи в файл {#file-write-safety}

Прежде чем write_file или patch коснутся диска, Hermes проверяет целевой путь на наличие списка запрещенных файлов и дополнительной песочницы. Заблокированные записи немедленно возвращают агенту сообщение об ошибке — нет запроса на одобрение и нет возможности переопределить его из пользовательского интерфейса чата. Модель по-прежнему может утверждать, что редактирование прошло успешно; когда display.file_mutation_verifier включен (по умолчанию), доверяйте нижнему колонтитулу проверки мутации файла, а не итоговой сводке помощника.

Защищенные пути (всегда заблокированы)

Эти категории всегда запрещены, даже если HERMES_WRITE_SAFE_ROOT не установлен:

Категория Примеры
Хранилища учетных данных ОС ~/.ssh/, ~/.aws/, ~/.kube/, /etc/sudoers, ~/.netrc
Магазины сертификатов Hermes auth.json, .env, .anthropic_oauth.json, mcp-tokens/, pairing/ под HERMES_HOME (активный профиль и глобальный корень)
Секретные файлы проекта .env, .env.local, .env.production, .envrc в любом месте на диске

Чувствительные пути внутри безопасного корня по-прежнему заблокированы — указание HERMES_WRITE_SAFE_ROOT на $HOME не позволяет писать ~/.ssh/id_rsa.

Нарушения безопасного root-доступа возвращают Запись запрещена: '…' находится за пределами HERMES_WRITE_SAFE_ROOT (…). Блоки пути к учетным данным используют Запись запрещена: '…' — это защищенный файл системы/учетных данных.

HERMES_WRITE_SAFE_ROOT (необязательная песочница)

Если они установлены, write_file и patch могут указывать только на пути внутри перечисленных префиксов каталогов. Все, что находится снаружи, жестко блокируется и не проходит через одобрение опасного командования.

Чтобы разрешить одновременно рабочее пространство и дом Hermes:

export HERMES_WRITE_SAFE_ROOT=/path/to/project:/home/you/.hermes

Снимите настройку переменной, чтобы восстановить неограниченную запись (с учетом списка запретов защищенного пути). Полная ссылка: HERMES_WRITE_SAFE_ROOT.

Крон и прочие состояния Hermesа

Не просите агента «исправить» ~/.hermes/cron/jobs.json напрямую. Используйте инструмент cronjob, hermes cron или /cron — они обновляют хранилище заданий через поддерживаемый API. То же самое относится и к другим управляющим файлам Hermes, когда безопасность записи блокирует прямое редактирование.:::Примечание: Глубокоэшелонированная защита, а не жесткие границы Защита от записи применяется только к write_file и patch. Инструмент «терминал» запускается от имени того же пользователя ОС и по-прежнему может «кошать» или перезаписывать запрещенные пути с помощью команд оболочки. Список запретов уменьшает случайные повреждения и дает моделям четкий сигнал остановки; он не помещает в «песочницу» враждебный или скомпрометированный агент.

Авторизация пользователя (шлюз)

При запуске шлюза обмена сообщениями Hermes контролирует, кто может взаимодействовать с ботом, через многоуровневую систему авторизации.

Порядок проверки авторизации

Метод _is_user_authorized() проверяет в следующем порядке:

  1. Флаг разрешения всех событий для каждой платформы (например, DISCORD_ALLOW_ALL_USERS=true)
  2. Список одобренных сопряжений DM (пользователи, одобренные с помощью кодов сопряжения)
  3. Списки разрешений для конкретной платформы (например, TELEGRAM_ALLOWED_USERS=12345,67890)
  4. Глобальный белый список (GATEWAY_ALLOWED_USERS=12345,67890)
  5. Глобальное разрешение всех (GATEWAY_ALLOW_ALL_USERS=true)
  6. По умолчанию: запретить

Белые списки платформы

Установите разрешенные идентификаторы пользователей в виде значений, разделенных запятыми, в ~/.hermes/.env:

# Platform-specific allowlists
TELEGRAM_ALLOWED_USERS=123456789,987654321
DISCORD_ALLOWED_USERS=111222333444555666
WHATSAPP_ALLOWED_USERS=15551234567
SLACK_ALLOWED_USERS=U01ABC123

# Cross-platform allowlist (checked for all platforms)
GATEWAY_ALLOWED_USERS=123456789

# Per-platform allow-all (use with caution)
DISCORD_ALLOW_ALL_USERS=true

# Global allow-all (use with extreme caution)
GATEWAY_ALLOW_ALL_USERS=true
```<div class="admonition admonition-warning"><p class="admonition-title">⚠️ Warning</p>
Если **списки разрешенных не настроены** и не задан параметр GATEWAY_ALLOW_ALL_USERS, **всем пользователям запрещено**. Шлюз регистрирует предупреждение при запуске:

No user allowlists configured. All unauthorized users will be denied. Set GATEWAY_ALLOW_ALL_USERS=true in ~/.hermes/.env to allow open access, or configure platform allowlists (e.g., TELEGRAM_ALLOWED_USERS=your_id). ```

Система сопряжения DM

Для более гибкой авторизации Hermes включает систему сопряжения на основе кода. Вместо того, чтобы заранее требовать идентификаторы пользователей, неизвестные пользователи получают одноразовый код сопряжения, который владелец бота утверждает через CLI.

Как это работает:

  1. Неизвестный пользователь отправляет боту в Директ
  2. Бот отвечает 8-значным кодом сопряжения.
  3. Владелец бота запускает hermes Pairing Approv <платформа> <код> в CLI.
  4. Пользователь навсегда одобрен для этой платформы.

Управляйте обработкой неавторизованных прямых сообщений в ~/.hermes/config.yaml:

unauthorized_dm_behavior: pair

whatsapp:
  unauthorized_dm_behavior: ignore

Функции безопасности (на основе рекомендаций OWASP + NIST SP 800-63-4):

Особенность Подробности
Формат кода 8-значный из 32-значного однозначного алфавита (без 0/O/1/I)
Случайность Криптографический (secrets.choice())
Код ТТЛ Срок действия 1 час
Ограничение скорости 1 запрос на пользователя за 10 минут
Ожидаемый лимит Максимум 3 ожидающих кода на платформу
Локаут 5 неудачных попыток одобрения → блокировка на 1 час
Безопасность файлов chmod 0600 для всех файлов данных сопряжения
Ведение журнала Коды никогда не выводятся на стандартный вывод

Сопряжение команд CLI:

# List pending and approved users
hermes pairing list

# Approve a pairing code
hermes pairing approve telegram ABC12DEF

# Revoke a user's access
hermes pairing revoke telegram 123456789

# Clear all pending codes
hermes pairing clear-pending
```<div class="admonition admonition-tip"><p class="admonition-title">💡 Tip</p> Пользователям Docker: запускайте команды сопряжения от имени пользователя Hermes.
Официальный образ Docker запускает шлюз от имени непривилегированного пользователя Hermes.
(uid 10000) через `gosu`, но `docker exec` по умолчанию использует root. Файлы одобрения
созданные пользователем root записываются с режимом `0600 root:root` и шлюзом
не могу их прочитать  одобрение молча игнорируется ([#10270][i10270]).

Всегда передавайте `-u hermes`:
```bash
docker exec -u hermes hermes-agent hermes pairing approve telegram ABC12DEF

Если вы уже выполнили команду от имени пользователя root, а пользователь все еще не авторизован, перезапустите контейнер — точка входа зафиксирует право собственности при следующем запуске.

Хранение: Данные о сопряжении хранятся в ~/.hermes/pairing/ вместе с файлами JSON для каждой платформы: - {platform}-pending.json — ожидающие запросы на сопряжение - {platform}-approved.json — одобренные пользователи - _rate_limits.json — ограничение скорости и отслеживание блокировки

Изоляция контейнера

При использовании серверной части терминала docker компания Hermes применяет строгие меры безопасности к каждому контейнеру.

Флаги безопасности Docker

Каждый контейнер запускается с этими флагами (определенными в tools/environments/docker.py):

_BASE_SECURITY_ARGS = [
    "--cap-drop", "ALL",                          # Drop ALL Linux capabilities
    "--cap-add", "DAC_OVERRIDE",                  # Root can write to bind-mounted dirs
    "--cap-add", "CHOWN",                         # Package managers need file ownership
    "--cap-add", "FOWNER",                        # Package managers need file ownership
    "--security-opt", "no-new-privileges",         # Block privilege escalation
    "--pids-limit", "256",                         # Limit process count
    "--tmpfs", "/tmp:rw,nosuid,size=512m",         # Size-limited /tmp
    "--tmpfs", "/var/tmp:rw,noexec,nosuid,size=256m",  # No-exec /var/tmp
]

SETUID/SETGID нет в базовом списке — они добавляются условно, когда контейнер запускается от имени пользователя root и точка инициализации/входа должна отказаться от привилегий (путь сброса привилегий s6). Они пропускаются, если контейнер уже запущен от имени пользователя без полномочий root. tmpfs /run также отделяется от базового списка и монтируется для каждого образа (усиленный noexec по умолчанию, exec только для изображений с наложением s6, которые выполняются из /run).

Ограничения ресурсов

Ресурсы контейнера настраиваются в ~/.hermes/config.yaml:

terminal:
  backend: docker
  docker_image: "nikolaik/python-nodejs:python3.11-nodejs20"
  docker_forward_env: []  # Explicit allowlist only; empty keeps secrets out of the container
  container_cpu: 1        # CPU cores
  container_memory: 5120  # MB (default 5GB)
  container_disk: 51200   # MB (default 50GB, requires overlay2 on XFS)
  container_persistent: true  # Persist filesystem across sessions

Сохранение файловой системы

Сравнение безопасности серверной части терминала

Бэкэнд Изоляция Опасная проверка CMD Лучшее для
местный Нет — работает на хосте ✅ Да Развитие, доверенные пользователи
тсс Удаленная машина ✅ Да Запуск на отдельном сервере
докер Контейнер ❌ Пропущено (контейнер является границей) Производственный шлюз
необычность Контейнер ❌ Пропущено среды HPC
модальный Облачная песочница ❌ Пропущено Масштабируемая изоляция облака
дайтона Облачная песочница ❌ Пропущено Постоянные облачные рабочие пространства
vercel_sandbox Облачная микроВМ ❌ Пропущено Облачное выполнение с сохранением моментальных снимков

Передача переменной среды {#environment-variable-passthrough}

И «execute_code», и «terminal» удаляют чувствительные переменные среды из дочерних процессов, чтобы предотвратить кражу учетных данных с помощью кода, сгенерированного LLM. Однако навыки, которые объявляют required_environment_variables, законно нуждаются в доступе к этим переменным.

Как это работает

Два механизма позволяют определенным переменным проходить через фильтры песочницы:

1. Передача на уровне навыка (автоматически)

Когда навык загружается (с помощью skill_view или команды /skill) и объявляет required_environment_variables, любая из тех переменных, которые фактически установлены в среде, автоматически регистрируется как транзитная. Отсутствующие переменные (все еще находящиеся в состоянии, необходимом для установки) не регистрируются.

# In a skill's SKILL.md frontmatter
required_environment_variables:
  - name: TENOR_API_KEY
    prompt: Tenor API key
    help: Get a key from https://developers.google.com/tenor

После загрузки этого навыка «TENOR_API_KEY» передается на «execute_code», «терминал» (локальный) ** и удаленные серверные части (Docker, Modal) — ручная настройка не требуется.

ℹ️ Info

Докер и модал До версии 0.5.1 «forward_env» в Docker была отдельной системой, не связанной с передачей навыков. Теперь они объединены — переменные окружения, объявленные навыками, автоматически пересылаются в контейнеры Docker и модальные песочницы без необходимости добавлять их в docker_forward_env вручную.
2. Передача на основе конфигурации (вручную)**

Для переменных env, не объявленных каким-либо навыком, добавьте их в terminal.env_passthrough в config.yaml:

terminal:
  env_passthrough:
    - MY_CUSTOM_KEY
    - ANOTHER_TOKEN

Передача файла учетных данных (токены OAuth и т. д.) {#credential-file-passthrough}

Некоторым навыкам необходимы файлы (а не только переменные окружения) в песочнице. Например, Google Workspace хранит токены OAuth как google_token.json в HERMES_HOME активного профиля. Навыки объявляют это во вступительной части:

required_credential_files:
  - path: google_token.json
    description: Google OAuth2 token (created by setup script)
  - path: google_client_secret.json
    description: Google OAuth2 client credentials

При загрузке Hermes проверяет, существуют ли эти файлы в HERMES_HOME активного профиля, и регистрирует их для монтирования:

Вы также можете вручную перечислить файлы учетных данных в config.yaml:

terminal:
  credential_files:
    - google_token.json
    - my_custom_oauth_token.json

Пути указаны относительно ~/.hermes/. Файлы монтируются в каталог /root/.hermes/ внутри контейнера. Этот список читается tools/credential_files.py (terminal.credential_files) — он находится в блоке terminal:, но загружается модулем credential-files, а не основным сервером терминала, поэтому он не является частью связанного снимка DEFAULT_CONFIG.

Что фильтрует каждая песочница

Песочница Фильтр по умолчанию Переопределение проходного режима
execute_code Блокирует переменные, содержащие KEY, TOKEN, SECRET, PASSWORD, CREDENTIAL, PASSWD, AUTH в имени; разрешает только переменные с безопасным префиксом через ✅ Вары Passthrough обходят обе проверки
терминал (локальный) Блокирует явные переменные инфраструктуры Hermes (ключи провайдера, токены шлюза, ключи API инструментов) ✅ Вары Passthrough обходят черный список
терминал (Докер) По умолчанию нет переменных окружения хоста ✅ Передаваемые переменные + docker_forward_env через -e
терминал (модальный режим) По умолчанию нет хост-окружения/файлов ✅ Файлы учетных данных смонтированы; передача env через синхронизацию
MCP Блокирует все, кроме безопасных системных переменных + явно настроенной env ❌ Не зависит от сквозной передачи (вместо этого используйте конфигурацию MCP env)

Вопросы безопасности

Обработка учетных данных MCP

Подпроцессы сервера MCP (Model Context Protocol) получают фильтрованную среду для предотвращения случайной утечки учетных данных.

Переменные безопасной среды

Только эти переменные передаются от хоста к подпроцессам MCP stdio:

PATH, HOME, USER, LANG, LC_ALL, TERM, SHELL, TMPDIR

Плюс любые переменные XDG_*. Все остальные переменные среды (ключи API, токены, секреты) удалены.

Переменные, явно определенные в конфигурации env сервера MCP, передаются через:

mcp_servers:
  github:
    command: "npx"
    args: ["-y", "@modelcontextprotocol/server-github"]
    env:
      GITHUB_PERSONAL_ACCESS_TOKEN: "ghp_..."  # Only this is passed

Редактирование учетных данных

Сообщения об ошибках от инструментов MCP обрабатываются перед возвратом в LLM. Следующие шаблоны заменены на [УДАЛЕНО]:

Политика доступа к веб-сайту

Вы можете ограничить доступ агента к веб-сайтам с помощью веб-инструментов и инструментов браузера. Это полезно для предотвращения доступа агента к внутренним службам, панелям администратора или другим конфиденциальным URL-адресам.

# In ~/.hermes/config.yaml
security:
  website_blocklist:
    enabled: true
    domains:
      - "*.internal.company.com"
      - "admin.example.com"
    shared_files:
      - "/etc/hermes/blocked-sites.txt"

При запросе заблокированного URL-адреса инструмент возвращает ошибку, объясняющую, что домен заблокирован политикой. Черный список применяется к web_search, web_extract, browser_navigate и всем инструментам, поддерживающим URL-адреса.

Подробную информацию см. в разделе Черный список веб-сайтов в руководстве по настройке.

SSRF-защита

Все инструменты с поддержкой URL-адресов (веб-поиск, веб-извлечение, Vision, браузер) проверяют URL-адреса перед их получением, чтобы предотвратить атаки подделки запросов на стороне сервера (SSRF). К заблокированным адресам относятся:

Защита SSRF всегда активна при использовании с выходом в Интернет, а сбои DNS рассматриваются как заблокированные (закрытые при сбое). Цепочки перенаправления повторно проверяются на каждом прыжке, чтобы предотвратить обходы на основе перенаправления.

Намеренное разрешение частных URL-адресов

Некоторым установкам законно необходим доступ к частному/внутреннему URL-адресу — домашние сети, которые разрешают home.arpa в пространство RFC 1918, конечные точки Ollama/llama.cpp только для локальной сети, внутренние вики-сайты, отладка облачных метаданных и тому подобное. В таких случаях предусмотрен глобальный отказ:

security:
  allow_private_urls: true   # default: false

При включении веб-инструменты, браузер, выборка URL-адресов Vision и загрузка мультимедиа через шлюз больше не отклоняют RFC 1918/loopback/link-local/CGNAT/адреса назначения облачных метаданных. Это преднамеренная граница доверия — включайте ее только на компьютерах, где агент, запускающий произвольные URL-адреса, введенные из подсказки, в локальной сети, представляет собой приемлемый риск. Общедоступные шлюзы должны его отключить.

Защита подстроки хоста (которая блокирует похожие трюки с доменом Unicode, даже если базовый IP-адрес общедоступен) остается включенной независимо от этого параметра.

Тирит Предварительное сканирование безопасности

Hermes интегрирует tirith для сканирования команд на уровне контента перед выполнением. Тирит обнаруживает угрозы, которые пропускает только сопоставление с образцом:

Тирит автоматически устанавливается из выпусков GitHub при первом использовании с проверкой контрольной суммы SHA-256 (и проверкой происхождения cosign, если cosign доступен).

# In ~/.hermes/config.yaml
security:
  tirith_enabled: true       # Enable/disable tirith scanning (default: true)
  tirith_path: "tirith"      # Path to tirith binary (default: PATH lookup)
  tirith_timeout: 5          # Subprocess timeout in seconds
  tirith_fail_open: true     # Allow execution when tirith is unavailable (default: true)

Когда tirith_fail_open имеет значение true (по умолчанию), команды продолжаются, если tirith не установлен или истекло время ожидания. Установите значение false в средах с высоким уровнем безопасности, чтобы блокировать команды, когда Тирит недоступен.

Тирит поставляет готовые двоичные файлы для Linux (x86_64/aarch64) и macOS (x86_64/arm64). На платформах без предварительно созданного двоичного файла (Windows и т. д.) тирит автоматически пропускается — средства защиты сопоставления с образцом все равно работают, а интерфейс командной строки не отображает баннер «недоступно». Чтобы использовать Тирит в Windows, запустите Hermes под WSL.

Вердикт Тирита интегрируется с потоком одобрения: безопасные команды проходят, в то время как как подозрительные, так и заблокированные команды вызывают одобрение пользователя с полным выводом тирита (серьезность, заголовок, описание, более безопасные альтернативы). Пользователи могут одобрить или отклонить — по умолчанию выбран вариант «Отклонить», чтобы обеспечить безопасность автоматических сценариев.

Защита от внедрения контекстного файла

Файлы контекста (AGENTS.md,.cursorrules, SOUL.md) сканируются на предмет внедрения подсказки перед включением в системную подсказку. Сканер проверяет:

Заблокированные файлы показывают предупреждение:

[BLOCKED: AGENTS.md contained potential prompt injection (prompt_injection). Content not loaded.]

Лучшие практики для производственного развертывания

Контрольный список развертывания шлюза

  1. Установите явные списки разрешенных — никогда не используйте GATEWAY_ALLOW_ALL_USERS=true в рабочей среде.
  2. Использовать серверную часть контейнера — установите terminal.backend: docker в config.yaml.
  3. Ограничить ограничения ресурсов — установите соответствующие ограничения на ЦП, память и диск.
  4. Надежное хранение секретов — храните ключи API в ~/.hermes/.env с соответствующими правами доступа к файлам.
  5. Включить сопряжение DM — по возможности используйте коды сопряжения вместо жесткого кодирования идентификаторов пользователей.
  6. Просмотр списка разрешенных команд — периодически проверяйте command_allowlist в config.yaml.
  7. Установите terminal.cwd — не позволяйте агенту работать из конфиденциальных каталогов.
  8. Запускать от имени пользователя без полномочий root — никогда не запускайте шлюз от имени пользователя root.
  9. Отслеживать журналы — проверьте ~/.hermes/logs/ на наличие попыток несанкционированного доступа.
  10. Поддерживайте обновления — регулярно запускайте «hermes update» для получения обновлений безопасности.

Защита ключей API

# Set proper permissions on the.env file
chmod 600 ~/.hermes/.env

# Keep separate keys for different services
# Never commit.env files to version control

Сетевая изоляция

Для максимальной безопасности запустите шлюз на отдельном компьютере или виртуальной машине. Установите terminal.backend: ssh в config.yaml, затем укажите сведения о хосте через переменные среды в ~/.hermes/.env:

# ~/.hermes/config.yaml
terminal:
  backend: ssh
# ~/.hermes/.env
TERMINAL_SSH_HOST=agent-worker.local
TERMINAL_SSH_USER=hermes
TERMINAL_SSH_KEY=~/.ssh/hermes_agent_key

Детали подключения SSH хранятся в файле.env (а не config.yaml), поэтому они не возвращаются и не передаются вместе с экспортом профиля. Благодаря этому соединения шлюза для обмена сообщениями отделены от выполнения команд агента.

Консультативная проверка цепочки поставок

Hermes поставляется со встроенным консультативным сканером, который помечает пакеты Python в активной версии, которые соответствуют тщательно подобранному каталогу известных скомпрометированных версий (черви цепочки поставок, такие как отравление mistralai 2.4.6 в мае 2026 года). Реализация находится в hermes_cli/security_advisories.py.

Как это работает:

Каждая рекомендация имеет стабильный идентификатор. После того, как вы прочитали и приняли меры, вы можете отклонить это навсегда:

hermes doctor --ack <advisory-id>

Подтверждение сохраняется в config.security.acked_advisories и выдерживает перезапуск. Старые рекомендации намеренно не удаляются из каталога — если оставить их на месте, новые установки будут предупреждены об исторически зараженных версиях, которые все еще могут кэшироваться в частном зеркале.

Сама проверка выполняется только для стандартной библиотеки и запускается из одного поиска importlib.metadata.version() для каждой рекомендации, поэтому ее можно безопасно запускать при каждом запуске.

Отложенная установка дополнительных зависимостей

Многие функции (Mistral TTS, ElevenLabs, Honcho Memory, Bedrock, Slack, Matrix и т. д.) зависят от пакетов Python, которые нужны не каждому пользователю. Hermes устанавливает их лениво при первом использовании, а не с энтузиазмом под hermes-agent[all]. Реализация находится в tools/lazy_deps.py.

Компромисс, который это исправляет:

Как это работает:

  1. Серверный модуль вызывает ensure("feature.name") в начале пути первого импорта.
  2. Если deps отсутствуют, ensure проверяет security.allow_lazy_installs в config.yaml (по умолчанию true) и запускает pip install в области venv для спецификаций из разрешенного списка.
  3. Если установка не удалась или пользователь отключил отложенную установку, вызов вызывает FeatureUnavailable с фактическим stderr pip и указателем на инструменты Hermes.

Гарантии безопасности, обеспечиваемые tools/lazy_deps.py:

Гарантия Что это значит
Только для Venv Устанавливает целевой sys.executable в активный venv — никогда не системный Python
PyPI только по имени Спецификации принимают синтаксис "package>=1.0,<2". Никаких путей --index-url, git+https:// или file: — вредоносный config.yaml не может перенаправить установку
Белый список По этому пути можно установить только те спецификации, которые отображаются на древовидной карте LAZY_DEPS. Опечатка в имени функции НЕ получает семантики «установить что-либо»
Отказаться Установите security.allow_lazy_installs: false, чтобы полностью отключить установку во время выполнения. Полезно для сетей с ограниченным доступом или строгих мер безопасности
Никаких повторных попыток Сбои отображаются как FeatureUnavailable — нет кэширования плохого состояния, нет повторных попыток

Чтобы отключить установку во время выполнения:

# ~/.hermes/config.yaml
security:
  allow_lazy_installs: false

Если этот параметр отключен, бэкэнды, которым требуются дополнительные deps, будут предлагать пользователю запустить установку вручную («pip install…») или выбрать другой бэкэнд с помощью «инструментов Hermes».