Перейти к основному содержанию

Hermes в телефоне: свой клиент вместо мессенджеров

28 октября 2026

Работать с Hermes через мессенджеры неудобно, поэтому я написал для него свой клиент под Android. Сегодня вышла первая сборка, v0.1.0-rc11.

Что такое Hermes

Hermes — открытый агент от Nous Research под лицензией MIT2. Он работает на сервере, а не на ноутбуке: модель выбирается любая (OpenRouter, OpenAI, свой endpoint и другие), инструменты выполняются в выбранном окружении — локально, в Docker, по SSH. У агента есть память, навыки, которые он сам создаёт и правит, поиск по прошлым сессиям, планировщик cron и подключение MCP-серверов.

С агентом можно говорить из терминала (hermes), а можно запустить шлюз (hermes gateway) и писать ему из мессенджеров. Список каналов большой: Telegram, Discord, Slack, WhatsApp, Signal, Matrix, Mattermost, Email, SMS, Microsoft Teams и ещё десяток платформ3. Шлюз — один процесс: он держит подключения ко всем каналам, ведёт сессии по каждому чату, запускает задачи cron и доставляет их результаты в нужный канал.

Третий способ — веб-панель hermes dashboard. В ней есть чат, а ещё настройки: модель, config.yaml, секреты, задачи cron, навыки, каналы, журналы.

У меня Hermes крутится в контейнере на домашнем сервере, каналов два: бот в Telegram и бот на моём Matrix-сервере. Память агенту даёт memcue, о ней я писал вчера.

Чем неудобны мессенджеры

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

Треды. Каждой задаче нужна своя сессия, иначе контексты разных разговоров смешиваются. В личке с ботом мессенджер даёт для этого треды, но их надо создавать руками. В Telegram это темы в личке: режим включается командой /topic, а новая тема создаётся кнопкой «+»4. Эта схема у меня ещё и ломалась: мобильный клиент иногда присылает первое сообщение новой темы без номера темы, и ответ уходит в общий чат. Разбор этой истории — в отдельном посте. В Matrix Hermes по умолчанию не заводит треды в личке, их включает отдельная настройка, либо тред приходится начинать самому5.

Поиск. Через неделю нужно вернуться к разговору, а где он был? В Telegram или в Matrix, в какой теме или треде? Поиск мессенджера находит сообщение, но про сессии Hermes ничего не знает и ищет только в своём канале. Команда /sessions search фильтрует сессии лишь по названию или идентификатору3, а содержимое разговоров ей не видно.

Hermes for Android

Приложение — клиент для hermes dashboard, проверенное на Hermes v0.22.56. Сервер ставить отдельно не нужно: приложение пользуется тем же API, что и веб-панель. Код на Kotlin и Jetpack Compose, лицензия MIT.

Чат

Чат устроен как в приложении ChatGPT. Список чатов — в боковой панели. Каждый чат — отдельная сессия, и новый открывается кнопкой с карандашом или если потянуть ленту вверх за последнее сообщение. Создавать тред руками больше не нужно. Ответ приходит потоком через WebSocket панели: Markdown, рассуждения модели над ответом, а вызовы инструментов свёрнуты в одну строку, которую можно раскрыть. Код в ответе копируется одним нажатием. На вопросы агента и запросы на подтверждение отвечают кнопками на панели, которая выезжает снизу чата.

В боковой панели чаты сгруппированы по дате и по источнику: свои, из Telegram, из Matrix. Закреплённые чаты сверху, архив и запуски cron — в отдельных разделах. Поиск идёт по полнотекстовому индексу на сервере, то есть по тексту разговоров, и находит в том числе то, что писалось из Telegram и Matrix.

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

Работа в фоне и уведомления

Ход агента не обрывается, если свернуть приложение: сокет держит foreground-сервис, а ответ приходит уведомлением. На запрос подтверждения можно ответить прямо из уведомления.

Чтобы узнавать о готовых ответах без постоянного соединения, в репозитории лежит плагин hermes-push для сервера. Он отправляет Web Push после каждого хода в приложении, в Telegram, в Matrix или в cron. Доставка идёт через UnifiedPush, например через ntfy. Сообщение шифруется ключами телефона (RFC 8291), так что сервер push видит только шифротекст. Без плагина приложение проверяет новости периодически, не чаще раза в 15 минут, или держит постоянное соединение, если его включить: своего push у панели нет.

Управление сервером

Раздел сервера показывает состояние и позволяет менять то, ради чего раньше открывался SSH: шлюз, модель, config.yaml (по схеме или сырым YAML), секреты .env, задачи cron, навыки, наборы инструментов, MCP-серверы и каналы. Здесь же журналы и расход токенов. Всё, что может сломать или удалить что-то на сервере, сначала спрашивает подтверждение.

Соединение

У каждого сервера свой маршрут:

МаршрутКогда
НапрямуюТелефон видит панель сам: публичный адрес, приложение Tailscale, домашний Wi-Fi
Встроенный TailscaleПриложение само входит в tailnet через tsnet, слот VPN не нужен
SOCKS5, HTTPЕсть прокси, который видит сервер; логин по желанию

Встроенный Tailscale — это узел Tailscale, собранный из Go через gomobile и запущенный внутри процесса приложения. VpnService он не использует, поэтому работает рядом с любым другим VPN. Узлу нужен адрес control-сервера Tailscale или Headscale и, по желанию, pre-auth ключ; без ключа приложение покажет ссылку для входа. Журналы узла остаются на телефоне.

Сервер можно добавить по ссылке, чтобы не набирать ключ на телефоне:

org.evsyukov.hermes://add-server?url=hermes.example.org&route=tailscale&control=https://hs.example.org&key=<pre-auth key>

Вход идёт через поток native_pkce панели. Если сервер доступен напрямую, вход открывается в Custom Tab, и там работают passkey. Если сервер за прокси или во встроенном tailnet, страница входа открывается во WebView, чей трафик идёт тем же маршрутом.

Интерфейс и язык

Интерфейс на английском с русским переводом. На Android 13 и новее язык приложения можно выбрать отдельно от системного.

Ограничения и статус

Это первая сборка, и пока выходят только release candidate. Приложение совсем новое, и проверено оно пока на одном сервере — моём. Известные ограничения перечислены в README:

  • без плагина hermes-push новости приходят с задержкой или требуют постоянного соединения;
  • на обычном hermes dashboard REST-методы сессий не трогают сессии, созданные в процессе панели. Поэтому переименование, архив и удаление идут через сокет, а закрепить такой чат может не получиться: метода для этого в сокете нет;
  • режим панели со шлюзом (session_authority) поддержан только для основных вызовов.

APK подписан, собран для arm64 и требует Android 12 или новее. Скачать можно на странице релизов1.

Попробуйте

Если вы держите Hermes у себя и пишете ему с телефона, поставьте приложение и скажите, что не так. Что неудобно, чего не хватает, на каком сервере и маршруте что-то сломалось — всё это лучше всего оставлять в issue в juev/hermes. Пожелания по функциям туда же: приложение только начинается, и сейчас самое время решить, каким оно будет.


  1. Hermes 0.1.0-rc1, pre-release, файл hermes-0.1.0-rc1.apk. ↩︎ ↩︎

  2. NousResearch/hermes-agent, README и документация. ↩︎

  3. Messaging Gateway, список платформ и команд внутри чата, в том числе /sessions, /resume, /approve, /deny. ↩︎ ↩︎

  4. Telegram, раздел про темы в личке и режим /topic. ↩︎

  5. Matrix: треды в личке включают MATRIX_DM_AUTO_THREAD или MATRIX_DM_MENTION_THREADS, по умолчанию обе выключены. ↩︎

  6. juev/hermes, README. ↩︎