server-monitor-manager/agents/hermes/inbox/from-smm-deliverables/Старые задачи/smm-hermes-task-monitor-format-and-release-2026-08-10.md
Ochenstarik 23eb3f5233 chore(agents): разбор рабочих папок с диска на 2026-08-18
Задания, отчёты и патчи, лежавшие в C:\Users\Ochenstarik\projects и в
домашней папке, перенесены в agents/. Разложено по агентам там, где имя
файла позволяло определить автора; остальное — в _salvage-2026-08-18/
и разбирается вручную.

Патчи в notes/salvage-2026-08-18/ — незакоммиченная работа из брошенных
рабочих копий: она существовала только на диске.

Тяжёлое (релизные архивы, инсталляторы, наборы данных) в репозиторий не
попало: оно лежит рядом, в Agent_projects/_archive и Agent_projects/_data.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-18 14:19:54 +07:00

8.2 KiB
Raw Blame History

Hermes: формат снимка Monitor, совместимость БД, дисциплина релизов

Состояние

  • main @ f9205c3, роль Monitor слита (#29), подписанная поставка Queue A слита (#26);
  • v0.1.0-alpha.8 пересобран, все Linux-артефакты и server-monitor-manager-manifest.sig на месте;
  • открыт PR #31 с починкой путей Windows-артефактов.

Ветка: hermes/monitor-snapshot-contract.


Часть 1 — снимок Monitor не читается Desktop · блокирующий

Роль Monitor установлена, но мониторинг работать не будет. Скрипт /usr/local/libexec/ochenstarik-smm-metrics выдаёт имена полей, которых не понимает ни парсер Desktop, ни собственный контракт проекта.

Ждёт SshMonitorService.QueryAsync:

PROTOCOL HOSTNAME UPTIME_SECONDS LOAD1 CPU_COUNT
MEM_TOTAL_KB MEM_AVAILABLE_KB SWAP_TOTAL_KB SWAP_FREE_KB
DISK_TOTAL_KB DISK_AVAILABLE_KB DISK_INODES_TOTAL DISK_INODES_FREE
NETWORK_RX_BYTES NETWORK_TX_BYTES SYSTEMD_SSH SYSTEMD_WIREGUARD

Выдаёт скрипт:

CPU_COUNT LOAD1 MEM_TOTAL MEM_AVAIL SWAP_TOTAL SWAP_FREE
DISK_TOTAL DISK_AVAIL INODES_TOTAL INODES_FREE
NET_RX NET_TX UPTIME KERNEL DF_OUT DF_INODES MESH_STATUS

Совпадают два поля из шестнадцатиCPU_COUNT и LOAD1. Остальные не совпадают по имени, а PROTOCOL, HOSTNAME, SYSTEMD_SSH, SYSTEMD_WIREGUARD отсутствуют вовсе.

Практический результат: в Desktop имя сервера подставится из профиля, память, диск, swap, inode и сеть покажут нули, состояния SSH и WireGuard — unknown. Формально роль установлена, фактически функция, ради которой существует Desktop, не работает.

Формат уже зафиксирован в docs/installer-contract.md §7 — его и надо соблюсти дословно, а не изобретать заново.

Что сделать

  1. Привести вывод скрипта к docs/installer-contract.md §7: PROTOCOL=1, HOSTNAME, UPTIME_SECONDS, LOAD1, CPU_COUNT, MEM_TOTAL_KB, MEM_AVAILABLE_KB, SWAP_TOTAL_KB, SWAP_FREE_KB, DISK_TOTAL_KB, DISK_AVAILABLE_KB, DISK_INODES_TOTAL, DISK_INODES_FREE, NETWORK_RX_BYTES, NETWORK_TX_BYTES, KERNEL.
  2. Добавить SYSTEMD_SSH и SYSTEMD_WIREGUARD — их читает Desktop, но в §7 их нет. Дописать в §7, чтобы контракт снова был единственным источником.
  3. Внутренние переменные вроде DF_OUT и DF_INODES из вывода убрать: снимок не должен содержать ничего, кроме полей контракта.

Контрактный тест — переделать

tests/acceptance/test_monitor_snapshot.sh проверяет скрипт против списка полей, который живёт в самом тесте. Именно поэтому расхождение с Desktop не поймалось.

Список ожидаемых полей должен существовать в одном месте и использоваться обеими сторонами:

  • тестом shell-скрипта — что все поля присутствуют и лишних нет;
  • тестом парсера Desktop — что он читает ровно эти поля.

Как реализовать — на ваше усмотрение: общий файл-фикстура с эталонным снимком, из которого обе стороны берут набор ключей, либо генерация списка из installer-contract.md. Требование одно: изменение имени поля с одной стороны обязано ронять тест другой стороны.

SshMonitorService.cs при этом не менять — правится скрипт, а не парсер. Если парсер тоже потребует правки, описать в REPORT.md.


Часть 2 — совместимость существующей БД с SQLitePCLRaw 3.0.5

Пункт из прошлого задания, оставшийся невыполненным. Сейчас он не горит только по счастливой случайности: alpha.8 собран из коммита, где ещё 2.1.12. Но в main уже 3.0.5, и следующий релиз его унесёт.

На живом Hub пользователя база создана версией 2.1.12. Если совместимости нет, это проявится в момент update-control.

Проверить: открытие существующей control.db сборкой из текущего main, PRAGMA user_version без повторного применения миграций, чтение агентов, identities, links, provisioning и аудита, backup-create и backup-restore на этой же базе, и то же самое на linux-arm64 self-contained trimmed single-file.

Добавить постоянный тест на открытие базы предыдущей схемы — эталонная control.db в репозитории либо скрипт её воспроизведения. Без него следующее обновление SQLite повторит эту историю.

Если хоть одна проверка не проходит — откатить #23 отдельным PR и написать об этом прямо.


Часть 3 — дисциплина релизов

Тег v0.1.0-alpha.8 был сдвинут: сначала указывал на 80b4797, теперь на ad180e9. Так делать нельзя, и теперь особенно: релиз содержит server-monitor-manager-manifest.json и подпись manifest.sig, которые описывают конкретное содержимое. Если тег двигается, подпись перестаёт что-либо доказывать, а у того, кто сверялся с прежним тегом, проверка не сойдётся.

  1. Зафиксировать правило в docs/installer-contract.md: опубликованный тег неизменяем; ошибка в сборке исправляется выпуском следующей версии, а не переписыванием тега.
  2. Следующий релиз выпускать как v0.1.0-alpha.9 после частей 1 и 2.
  3. Убрать из smm-setup.sh (ассет релиза) временный обход бага validate_control_url — дефект исправлен в #24, обход помечен комментарием в коде.
  4. Довести или закрыть PR #31.

Критерий приёмки

  • снимок Monitor совпадает с installer-contract.md §7 плюс два поля systemd; лишних полей нет;
  • переименование любого поля роняет тест противоположной стороны — продемонстрировать намеренной поломкой во временном коммите со ссылкой на красный прогон;
  • существующая база открывается новой сборкой, есть постоянный тест на предыдущую схему;
  • правило неизменяемости тега записано в контракте;
  • обход validate_control_url из smm-setup.sh удалён;
  • Control suite прогнан на Linux, CI зелёный.

Отчёт

Раздельно: локально, в CI со ссылками, не запускалось и почему.