397777089e
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
79 lines
12 KiB
Markdown
79 lines
12 KiB
Markdown
# ADR-020 Split the Claude control layer into a dedicated `claude-brain` repository
|
||
|
||
## Status
|
||
|
||
Accepted. Date: 2026-06-15.
|
||
|
||
**Decision Maker:** User: Дмитрий (владелец Лидерры и управляющего слоя).
|
||
|
||
## Context
|
||
|
||
Управляющий слой Claude (router / mentor / observer / registry / enforcement-машинерия `tools/` — далее «мозг») и продукт **Лидерра** (Laravel + Vue CRM) много месяцев разрабатывались в одном репозитории `Документация`. Они переплетены в общих коммитах: governance-правила, гейт-хуки, observer-эпизоды и реестр инструментов жили рядом с кодом приложения, миграциями БД и доками продукта.
|
||
|
||
Это создало три проблемы. (1) **Когнитивный шум**: оперативная карта `CLAUDE.md` (~352 KB) описывает продукт Лидерру, хотя мозг — самостоятельная система; новый разработчик/сессия не отличает «дом мозга» от «дома продукта». (2) **Связанность тестов и рантайма**: ~3931 vitest-тест мозга (`tools/*.test.mjs`) и тест-конфиг физически лежали в `app/` Лидерры, смешивая регрессии двух систем. (3) **Нет дома развития**: улучшения мозга нельзя было вести и версионировать отдельно от продуктового цикла Лидерры.
|
||
|
||
Триггер решения — намерение владельца развивать мозг как отдельный продукт, не ломая работающую рабочую копию в репозитории Лидерры.
|
||
|
||
## Decision
|
||
|
||
Управляющий слой **копируется** (не вырезается) в новый репозиторий `claude-brain` (`C:\моя\проекты\claude-brain`), который становится единственным домом дальнейшей разработки мозга; в репозитории `Документация` копия остаётся как замороженный рабочий снимок, продолжающий действовать, а связь между репозиториями — односторонний снимок без автоматической синхронизации.
|
||
|
||
Развёртка решения:
|
||
|
||
- **Модель связи — снимок, односторонний.** Канон развивается в `claude-brain`; переносится в `Документация` только по явной команде владельца. Встречных правок нет — направление всегда `claude-brain → Документация`.
|
||
- **Граница копирования** задана инвентарём «три корзины» дизайна v5 ({#D2}): A — копируется в `claude-brain` (рабочие `tools/*.mjs`, их тесты, `docs/observer/`, `docs/registry/`, `router-procedure.md`, `routing-off-phase.md`, `docs/discovery/`, управляющие specs/plans по правилу ключевых слов {#D3}, управляющие ADR, нормативный квинтет, память мозга, агенты `normative-sync` + `reviewer-agent`); B — остаётся в `Документация` (Лидерра + замороженная рабочая копия мозга); C — общие конфиги расщепляются по подмножествам.
|
||
- **Безопасность через порядок** ({#D4}): сначала собрать и автономно верифицировать `claude-brain`, и только после — минимальное удаление в `Документация` (лишь dev-артефакты, которые не читает ни один рабочий процесс).
|
||
|
||
## Alternatives Considered
|
||
|
||
### Alternative A: Вырезать мозг из `Документация` (move, не copy) с чистым разделением git-истории
|
||
|
||
Разрезать историю по путям (`git filter-repo`) так, чтобы каждый репозиторий получил только свои коммиты. Отвергнуто: мозг и Лидерра **переплетены в общих коммитах** — один коммит часто трогает и `tools/`, и `app/`. Чистое разделение истории технически невозможно без потери атомарности или ручного переписывания сотен коммитов. Плюс move оставил бы рабочую копию Лидерры без действующих гейт-хуков до момента переноса — окно, в котором стена опущена.
|
||
|
||
### Alternative B: Монорепо с пакетами (workspace) внутри одного репозитория
|
||
|
||
Оставить один репозиторий, выделить мозг в отдельный npm-workspace/пакет с собственным `package.json` и тестами. Отвергнуто: не решает когнитивный шум (всё ещё один `CLAUDE.md`, одна оперативная карта на два продукта) и сохраняет продуктово-связанный релизный цикл. Workspace-граница — внутрикодовая, а владельцу нужна репозиторная (разные удалённые, разные истории развития, разный доступ).
|
||
|
||
### Alternative C: Ничего не делать — оставить смешанный репозиторий
|
||
|
||
Отвергнуто: три проблемы из Context остаются и усугубляются с каждым off-phase-эпиком (квинтет растёт, `CLAUDE.md` уже ~352 KB). Стоимость бездействия растёт нелинейно.
|
||
|
||
## Consequences
|
||
|
||
**Benefits**
|
||
|
||
- `claude-brain` собран и **верифицирован автономно**: `npm install` чисто, `npx vitest run --config vitest.config.tools.mjs` = 231 файл / 3931 passed / 2 skipped; данных Лидерры нет (`app/`/`db/`/`web/` отсутствуют — проверено рекурсивным glob). См. `docs/superpowers/specs/2026-06-15-claude-brain-split-status-handoff.md` {#H1}.
|
||
- Рабочая копия мозга в `Документация` **не сломана**: удалены только dev-артефакты (227 `tools/*.test.mjs` + тест-конфиг, commit `3aeedb8a`, 28326 удалений); рабочие `tools/*.mjs` и квинтет нетронуты.
|
||
- Дом развития мозга отделён: собственный `package.json` (brain-зависимости), `vitest.config.tools.mjs` в корне, собственный git и origin `github.com/CoralMinister/claude-brain.git`.
|
||
|
||
**Trade-offs**
|
||
|
||
- **Дублирование квинтета** (5 нормативных файлов копируются как есть). Принятая цена за нерискованное разделение: разбор «управление vs продукт» внутри квинтета отложен как отдельная будущая задача.
|
||
- **Ручной перенос** правок governance вместо автосинхронизации — каждое улучшение требует явной команды копирования `claude-brain → Документация`.
|
||
- **История развития мозга остаётся в `Документация`** (чистого разреза нет); `claude-brain` стартует без неё.
|
||
|
||
**Risks and mitigations**
|
||
|
||
- *Risk*: тихий дрейф квинтета между репозиториями (копии расходятся незаметно). *Mitigation* ({#D1}): снимок-штамп «дата + git-хэш `claude-brain`» в заголовке каждого из пяти файлов делает расхождение видимым при открытии; текстовый `diff` двух копий детектирует дрейф по запросу; односторонность переноса делает откат = повторное копирование канона.
|
||
- *Risk*: удалить в `Документация` путь, который читает рабочий процесс. *Mitigation* ({#D4} п.3): до удаления фиксируется полный список активных runtime-процессов и читаемых ими путей; удаление идёт в отдельной ветке/worktree (восстановимо `git restore`).
|
||
- *Risk*: `claude-brain` зависит от `app/node_modules` Лидерры. *Mitigation* ({#D5}): собственный `package.json` + `npm install` + lockfile; автономная верификация подтвердила независимость.
|
||
- *Risk* (известное отклонение от дизайна v5): git-репозиторий `claude-brain` стартовал **не с чистого старта** — новый управляющий слой свален поверх истории старого brain-installer v1.3 (HEAD `7351f03`), старые файлы помечены `D` в рабочем дереве, но не закоммичены. *Mitigation*: зафиксировано здесь как известное состояние; решение о санации git-истории (чистый initial-коммит vs принять наследие) остаётся за владельцем и в этот ADR не входит.
|
||
|
||
## Related Decisions
|
||
|
||
- **ADR-011 (Brain governance)**: разделяемая система (observer / router-procedure / контролёры) — её артефакты входят в корзину A и переезжают в `claude-brain`.
|
||
- **ADR-016 (Universal skill-coverage)**: классификатор-роутер мозга — также корзина A.
|
||
- **ADR-003…010, 012…015, 017, 019 (off-phase tooling)**: ADR управляющего тулинга копируются в `claude-brain`; ADR-001/002/018 (Лидерра) остаются в `Документация`.
|
||
|
||
## References
|
||
|
||
- Дизайн: `docs/superpowers/specs/2026-06-15-claude-brain-split-design-v5.md` (решения {#D1}–{#D6}, инвентарь корзин).
|
||
- Статус и handoff: `docs/superpowers/specs/2026-06-15-claude-brain-split-status-handoff.md` (сделано {#H1}, хвост {#H2}, механика стены {#H3}, баг наставника {#H4}).
|
||
- Снимок-штамп и diff-проверка квинтета: дизайн v5 {#D1}.
|
||
- Прун-коммит в `Документация`: `3aeedb8a` (227 тест-файлов + тест-конфиг, 28326 удалений).
|
||
- Тест-конфиг и пути: `vitest.config.tools.mjs` (`include: ['tools/*.test.mjs']` после правки из `../tools/*` — дизайн v5 {#D5}).
|
||
|
||
## Enforcement
|
||
|
||
Code-surface нет — это governance/process-решение. Механически проверяемая граница (согласованность квинтета) распределена между двумя репозиториями и выражается процедурно: снимок-штамп в заголовках пяти файлов + `diff` двух копий по запросу ({#D1}). Декларативный `adr-judge`-блок здесь не задаётся: правило «канон правится только в `claude-brain`, переносится односторонне» — организационное, не выразимо regex-проверкой staged-diff в одном репозитории. Контроль — через снимок-штамп (видимое расхождение) и ре-перенос канона.
|