temporality
Изменить страницу↗
Инженерные документы

Жизненный цикл артефактов (Artifact Lifecycle): создание агентами, согласование человеком

Дата: 2026-10-15 Статус: предложение Связанные: docs/artifact-registry.md (реестр и тулы чтения), docs/sagas.md (саги), docs/knowledge-evolution.md (паттерн «предложил → человек применил»), docs/inbound-messages.md §7 (синтаксис получателей)


#1. Цель

Разрешить агентам создавать и переиспользовать артефакты между собой, сохранив единственный жёсткий инвариант: в навыки попадают только артефакты, утверждённые человеком.

Целевой сценарий (саги):

Агент-аналитик пишет требование          → черновик артефакта (draft)
Отправляет на согласование людям         → запрос ревью (in_review)
Люди дорабатывают сами или с агентом     → правки черновика, новые круги
Человек утверждает                       → артефакт (approved)
Сага реализует требование в фичу         → раны читают артефакт по saga_id

Артефакт перестаёт быть только «справочником, который загрузил админ», и становится общим рабочим материалом системы — при этом статус «утверждён» всегда означает «конкретный человек ответил за этот документ», а не «документ часто встречается».

В UI согласования рецензент может выделить точный фрагмент и сохранить примечание, предлагаемую замену, одобрение или отказ по этому фрагменту. Разметка привязана к номеру версии и остаётся рядом с решением о документе. Для черновика или утверждённой версии тот же набор разметки можно передать выбранному агенту проекта: агент получает цитаты и инструкции, создаёт редакцию через artifact_update и оставляет её на проверку человеку.


#2. Проблематика текущего состояния


#3. Основные понятия

#3.1. Статус и версии

Артефакт получает машину состояний на уровне версии (см. §5):

Правка утверждённой версии невозможна: любое изменение — это новая версия того же id, проходящая цикл заново. Навыки ссылаются на id и всегда резолвятся в последнюю утверждённую версию.

Метаданные свободны от версии. Название, описание, тип (reference/work), привязка к саге и каталожные теги — не то, что утверждает рецензия: они правятся на месте в любом статусе (в том числе под согласованием и у утверждённого), не открывая редакцию и не трогая замок. Версию несут тело и его хранение: content, provider, external_ref, mime_type — их правка подчиняется машине состояний ниже. Агентский artifact_update сохраняет прежние ограничения целиком: approved — отказ, in_review — замок.

#3.2. Происхождение (origin)

origin_type  human | agent
origin_user  кто из людей (для human)
origin_run   какой ран создал (для agent)

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

#3.3. Запрос на согласование (review request)

workspace_artifact_review
    id, artifact_id, artifact_version
    reviewers  TEXT[]   -- user:ivanov | org:backend | role:admin | project_owner
    mode       TEXT     -- all (по умолчанию) | any
    status     TEXT     -- open | approved | rejected | cancelled
    note       TEXT     -- комментарий отправителя
    requested_by / requested_at
    resolved_by / resolved_at / comment

Синтаксис получателей переиспользуется из ask_human (docs/inbound-messages.md §7): конкретный человек, подразделение, роль. mode=any закрывает согласование первым ответом (одобрение или отказ), mode=all собирает все решения и закрывается отказом при первом же «нет».

#3.4. Reference-документы и рабочие продукты (kind)

Один реестр, одна модель доступа; kind разделяет сценарии потребления и группировку в UI, а не права. Граница проницаема: реализованное и закреплённое требование может стать reference-документом нового навыка — той же записью с другим kind после нового круга согласования.

#3.5. Артефакт в саге

workspace_artifact.saga_id TEXT NULL — артефакт, созданный внутри саги, наследует её идентификатор (сага регистрируется тулом saga_register, docs/sagas.md). Это не сужает видимость (орго-модель не меняется), но даёт трассировку: требование → согласование → раны реализации → фича. Обратная связь идёт через события: каждый ран, читавший артефакт, уже эмитит artifact.read; сага связывает их в сквозную историю.


#4. Принципы

  1. Утверждение человеком — единственная дверь в approved. Не сумма сигналов, не частота использования, не агентское ревью. Явное решение именованного человека.
  2. Статус — ограничитель, а не слагаемое. Черновик можно читать, но нельзя выдавать за опору: draft/rejected никогда не резолвятся для навыков, а в ответе тулов всегда видны.
  3. Агент предлагает — человек утверждает. Тот же контракт, что у skill_propose и эволюции агентов: агент делает черновик и запрос ревью, решение и ответственность остаются за человеком.
  4. Иммутабельность утверждённого. Изменение одобренного документа — новая версия и новый круг согласования; воспроизводимость решений восстанавливается по content_hash в событиях чтения (docs/artifact-registry.md §3.2).
  5. Черновики читаемы, но помечены. Переиспользование между агентами — половина ценности: разработчик читает требование аналитика. Ответ тулов несёт status и version; системный промпт прямо говорит: draft — это неподтверждённый материал.
  6. Инвариант проверяется сервером. Валидация ссылок в манифесте навыка — на границе API (422), а не в соглашениях между агентами.

#5. Машина состояний

                 ┌──────────────────────────────────────────┐
                 │                                          │ edit
                 ▼                                          │
создание ──► draft ──submit──► in_review ──approve──► approved
(human/agent)   ▲                  │                        │
                │ edit             │ reject                 │ новая версия
                └──────────────────┘                        ▼
                                                          draft(v+1)
              approved(v) при approve(v+1) ──► superseded(v)

Правила переходов (проверяются в Store, не в клиентах):


#6. Согласование несколькими людьми


#7. Инструменты агента

Новые тулы (ядро ходит в workspace API от service-identity, как artifact_search; origin фиксируется сервером по RunID):

artifact_create  { title, description, content?, mime_type?, kind=work,
                   saga_id? }                    → draft
artifact_update  { artifact_id, title?, description?, content?, … }
                                               → только draft/rejected версии
artifact_submit  { artifact_id, reviewers[], mode=all, note? }
                                               → in_review + уведомления

Изменения существующих:

Политика безопасности: три новых тула добавляются в policySafeTools — они не имеют внешних эффектов (черновик внутри реестра, submit — запрос к людям, не действие), ровно как ask_human и skill_propose.

Системная секция промпта (рядом со Skills) дополняется: «рабочие продукты создавай как артефакты (kind=work), указывай saga_id; draft — не утверждён: не выдавай его за опору и не ссылайся на него в навыках».


#8. Связь с навыками (инвариант)


#9. API

POST   /v1/workspace/artifacts                         — создание (status по origin:
                                                        human → approved, agent → draft)
PUT    /v1/workspace/artifacts/{id}                    — правка draft/rejected;
                                                        approved → 409 + подсказка о новой версии
POST   /v1/workspace/artifacts/{id}/submit             — { reviewers[], mode, note } → 202
                                                        (идемпотентно на версию)
POST   /v1/workspace/artifacts/{id}/reviews/{rid}/approve  — { comment }
POST   /v1/workspace/artifacts/{id}/reviews/{rid}/reject   — { comment }
GET    /v1/workspace/artifacts?status=&kind=&saga=     — фильтры списков
GET    /v1/workspace/artifacts/{id}/reviews            — история согласований

RBAC: создание/правка — writer (тул агента — service-identity с origin=agent); approve/reject — writer, но не сервисный токен рана (только человек); удаление — operator, как сегодня.


#10. UI

Страница «Артефакты» (уже в основном меню):


#11. Аудит и события

Журнал (outbox, durable — не best-effort, как artifact.read):

artifact.proposed        { artifact_id, version, origin, kind, saga_id? }
artifact.updated         { artifact_id, version, actor }
artifact.review.requested{ artifact_id, version, reviewers, mode }
artifact.review.approved { artifact_id, version, resolved_by }
artifact.review.rejected { artifact_id, version, resolved_by, comment }
artifact.superseded      { artifact_id, from_version, to_version }

API-действия дублируются в access audit (create/update/approve), как сегодня.


#12. Фазы реализации

#Фаза 1 — жизненный цикл и создание агентами (ядро ценности)

Миграция (status/kind/version/origin/saga_id; существующие записи → approved v1, kind=reference, origin=human — они загружены людьми, это и есть их утверждение); машина состояний в Store; тулы artifact_create / artifact_update / artifact_submit; статус в artifact_search/read; guard навыков (422); review-таблица и approve/reject API; события; UI-минимум: чипы статусов, бейджи, кнопки решения, происхождение. Уведомление согласующим — текстовое со ссылкой.

#Фаза 2 — согласование в каналах (реализовано)

Обобщение human_requests на запросы вне рана (orphan-RunID artifact-review/<round>): уведомление согласующему создаёт строку human_request с выдачами (deliveries) по каналам; ответ в чате согласующего решает круг тем же переходом стора, что и кнопка в UI (первое слово ответа — решение, остальное — комментарий). Пост в thread-транспортах закрепляется как корень обсуждения — тредматчится точно в этот круг. Напоминания по дедлайну (env ARTIFACT_REVIEW_TIMEOUT, по умолчанию 72ч, 0 выключает) и эскалация эффективному главе орг-единицы артефакта (без головы/единицы — админам) после второго таймаута молчания; каждый шаг — один раз на круг. Настоящие инлайн-кнопки (Telegram/Matrix) — отдельная работа по драйверам.

#Фаза 3 — версии, комплаенс, трассировка

Полная история тел: снапшоты утверждённых версий при открытии новой редакции и просмотр архивных тел в UI — реализовано (таблица workspace_artifact_version, эндпоинт GET /artifacts/{id}/versions, блок «История версий» в карточке). Осталось: восстановление на дату — закрывает открытый вопрос docs/artifact-registry.md §12; UI-трассировка саги: артефакт → круги согласования → раны реализации → итоговый PR/фича; пиннг версии в манифесте навыка (опционально, для комплаенса); конвертация work → reference как самостоятельный сценарий.


#13. Критерии готовности

#Фаза 1

#Фаза 2

#Фаза 3


#14. Открытые вопросы


#15. Архитектурные ограничения