Skip to content

Совместимость с .agent рантайма

Отдельный CleanSlice runtime (cleanslice/runtime) хранит агента как портативную папку .agent/ (SOUL, MEMORY, skills, sessions, secrets, config…). Agentfy.ai 2.0 должен быть совместим с этим форматом, чтобы: импортировать существующих runtime-агентов, запускать цикл агента рантайма без изменений в нашем worker, и экспортировать/бэкапить агента для портативности.

Раскладка .agent/

.agent/
├── SOUL.md                 # персона / системный промпт (managed-файл)
├── USER.md                 # пользовательский контекст
├── MEMORY.md               # курируемая долгосрочная память
├── HEARTBEAT.md            # промпт heartbeat
├── agent.config.json       # IAgentConfig: maxIterations, maxTokens, accessStrategy,
│                           #   heartbeat, session(compaction), memory(limits/review),
│                           #   stopPhrases, managedFiles, syncSkills, tools{...}
├── memory/                 # роллинг дневной памяти  (YYYY-MM-DD.md)
├── skills/<name>/SKILL.md   # скиллы (markdown + frontmatter)
└── data/
    ├── access.json          # users{ id: {status, inviteCode/accessCode, createdAt} }
    ├── secrets/<userId>.json # { "service:key": value }  (напр. gmail:app_password)
    ├── sessions/<chan>:<user>.jsonl  # лог событий: {id,type,ts,data} построчно
    ├── memory.sqlite         # FTS-индекс по памяти
    └── usage.json            # потребление токенов
# + browser-state/<profile>.json  (живые куки/состояние браузера)

Маппинг .agent/ ↔ сущности Agentfy.ai

.agent/Agentfy.ai 2.0 (близкая совместимость — те же имена)
SOUL.mdagent.soul (персона / системный промпт — хранится дословно)
USER.mdagent.user (контекст человека/профиля — хранится дословно)
HEARTBEAT.mdagent.heartbeat (промпт heartbeat)
agent.config.jsonagent.configхранится дословно как IAgentConfig; лимиты / accessStrategy / runtimeProfile читаются из него, а не переименовываются в другие слайсы
MEMORY.md + memory/*.mdagent/memory (curated = MEMORY.md, daily[date] = memory/YYYY-MM-DD.md — тот же текст)
data/memory.sqlite— (FTS-индекс — производный, перестраивается на старте; не хранится/не переносится)
skills/<name>/SKILL.mdagent/skill (имя + frontmatter + тело дословно) (слайс добавить — см. пробелы)
data/sessions/<chan>:<uid>.jsonlchat (события как есть {id,type,ts,data}; idexternalId)
data/access.jsonagent/access (сохраняет форму users{ id:{status,inviteCode/accessCode,createdAt} })
data/secrets/<userId>.jsonagent/secret (сохраняет карту service:key→value; шифруется at-rest)
data/usage.jsonsystem/usage (BillingEvent'ы)
browser-state/*.jsonapp/account (состояние коннектора) / браузер-сессия воркера
workspace//workspace воркера (emptyDir) + результаты → system/file

Близкая совместимость — храним собственные имена рантайма

Мы намеренно сохраняем имена полей рантайма в БД, а не переименовываем их в принятые в CleanSlice. SOUL.md хранится как soul, USER.md — как user, MEMORY.md — как memory, HEARTBEAT.md — как heartbeat, а agent.config.json сохраняется дословно как config. Managed-markdown файлы маппятся 1:1 на колонки с тем же стемом; конфиг-JSON опрашивается на месте (лимиты, accessStrategy, runtimeProfile), а не раскладывается и переименовывается по setting / runtimeProfile / access.

Почему: адаптер становится проекцией, близкой к тождественной, а не семантическим переводом — round-trip без потерь, цикл рантайма читает/пишет те же самые имена, и нет слоя переименований, который мог бы разъехаться. Когда рантайм позже добавит новый managed-файл, он ляжет новым полем с тем же именем без изменения маппинга. (Другие слайсы вроде setting могут зеркалить/читать значения из config для кросс-агентных запросов, но config остаётся источником истины и не переписывается.)

Стратегия: .agent/ — портативный пакет + формат на поде

  • Postgres — нормализованный источник истины (строка Agent, память, чат, секреты, доступ…).
  • .agent/ — проекция этого состояния, используется как (a) пакет обмена/бэкапа и (b) рабочая директория на поде, когда worker крутит цикл рантайма.
  • Двунаправленный адаптер (agent/package) маппит между ними; worker материализует.agent/ из БД перед турном и синхронит дельты назад после.

Именно это позволяет worker'у переиспользовать цикл + тул-исполнители рантайма без изменений — они читают/пишут .agent/, а адаптер держит БД в синхроне.

Материализация / синхронизация на рантайме

турну нужен рантайм
   → менеджер воркера hydrate'ит .agent/ из Postgres (+ object storage) в workspace пода
   → цикл рантайма работает против .agent/ (без изменений — читает SOUL/MEMORY/skills, пишет sessions/…)
   → по завершении: синхронит дельты назад
        sessions/*.jsonl  → chat (новые сообщения)
        MEMORY.md, memory/*.md → agent/memory
        data/secrets/*    → agent/secret (если изменились)
        data/usage.json   → system/usage события
        browser-state/*   → app/account
   → workspace стирается; долговечный стейт уже сохранён

Переиспользуем существующую diff-manifest S3-синхронизацию рантайма (pull-on-boot / push-on-change): под может тянуть материализованный .agent/ из object storage и пушить изменения, так что слой синхронизации — тот, что рантайм уже поставляет; Agentfy.ai владеет лишь проекцией БД↔пакет.

Импорт / экспорт

  • Импорт папки .agent/ → создать/обновить сущности Agentfy.ai (онбординг существующего runtime-агента).
  • Экспорт агента → папка .agent/ (бэкап, портативность или запуск на отдельном рантайме). Round-trip работает, потому что обе стороны говорят на одном формате пакета.

Пробелы для полной совместимости

  • Добавить agent/skill (markdown-скиллы с frontmatter) в группу agent — у рантайма есть скиллы; наша L5-разбивка их потеряла. Также подтвердить наличие сабслайсов agent/secret, agent/access, agent/heartbeat, agent/cron (они маппятся 1:1 на .agent/).
  • sessions/*.jsonlchat: определить маппинг типов событий (user/assistant/tool_call/ tool_result/summary → строки сообщений + tool/summary-записи).
  • access.jsonuser: рантайм ключует пользователей по id канала (напр. Telegram id); смаппить на идентичности user/team Agentfy.ai.
  • Версионирование: запинить версию схемы .agent (рантайм её развивает) и держать адаптер толерантным к отсутствующим/лишним файлам.

Где живёт

  • Адаптер: apiagent/package (импорт/экспорт + маппинг БД↔.agent/).
  • Материализатор/синк: слайс runtime/worker (hydrate перед турном, синк дельт после), переиспользуя S3/diff-синк рантайма.
  • Цикл + тул-исполнители: приложение worker берёт их из cleanslice/runtime и гоняет против материализованной .agent/.