opencode-config/docs/decisions/028-pr-67-project-map-contract.md
Sergey f06d36140b
feat(pipeline): add check_project_map to DOCS phase (#67)
* feat(pipeline): add check_project_map to DOCS phase

* test(pipeline): add check_project_map unit tests + update check_docs tests

* docs(adr): add ADR-028 project map contract

* docs(project-map): mention check_project_map guard in Update Protocol

* docs(handoff): add PR handoff for check_project_map

* docs(handoff): set PR number 67

* docs(review): fix PR#66 to PR#67 typo in project map and handoff

* fix(ci): ruff lint errors in pipeline-status and project map test

---------

Co-authored-by: opencode-agent <agent@opencode.local>
2026-07-26 00:07:13 +03:00

73 lines
No EOL
5.1 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# ADR-028: Project map contract (mandatory README.md, aspirational modules)
## Статус
Accepted (2026-07-25)
## Контекст
Контракт `docs/project-map/` в репо `slaid098/opencode-config` размазан по 3
файлам с внутренними несоответствиями:
- `.opencode/agents/docs-reviewer.md:158-159,191` — обязывает
docs-reviewer обновлять карту при структурных изменениях и предлагает
один commit message.
- `.opencode/skills/get-project-map/SKILL.md:25-27` — описывает структуру
карты (README.md + модульные файлы per module) и frontmatter
`last_updated`.
- `.opencode/agents/reviewer.md:199-205` — требует от code-reviewer проверять
актуальность карты и предлагает *другой* commit message для той же
операции (несоответствие с docs-reviewer.md).
Фактическое состояние карты: только `README.md` (~140 строк, ASCII-дерево
структуры репо) без frontmatter и без модульных файлов. Полный контракт
(модульные файлы per module) никогда не соблюдался — aspirational документ,
не enforcement.
`pipeline-status.py:check_docs` (DOCS phase) валидировал handoff (4 секции),
ADR (filename pattern) и docs-reviewer comment (heading `## Docs Review
Summary`), но **не валидировал `docs/project-map/`**. Это позволяло PR проходить
DOCS-фазу даже при «тихом провале» docs-reviewer (забыл обновить карту при
структурных изменениях) — детерминированный guard отсутствовал. Зафиксировано
в memory `technical/pipeline-status-no-project-map-check.md`.
## Решение
Минимальный guard в `pipeline-status.py` — новая функция `check_project_map()`
проверяет существование `docs/project-map/README.md` (через
`PROJECT_MAP_DIR.exists()` + `README.md.exists()`). Встроена в `check_docs`
между `check_adr` и `_check_docs_reviewer_comment` (short-circuit на
NOT_DONE). Mandatory для pipeline-driven репо: docs-reviewer автосоздаёт
initial README.md при отсутствии каталога (`docs-reviewer.md:82-84`), поэтому
guard не блокирует первый PR и не требует ручной bootstrap-операции.
Контракт ослаблен под фактическое состояние:
- **README.md обязателен** — единственное, что проверяется детерминированно.
Возвращает DONE с размером файла в detail, либо NOT_DONE с указанием что
docs-reviewer должен создать (с ссылками на строки docs-reviewer.md).
- **Модульные файлы per module и frontmatter `last_updated`** — aspirational,
НЕ enforced. Полный контракт остаётся в `get-project-map/SKILL.md` как
рекомендация для docs-reviewer, но не блокирует пайплайн.
Возвращает только DONE/NOT_DONE (без AMBIGUOUS) — проверка файловой системы
детерминирована, нет внешних API вызовов.
## Альтернативы
- **Полный контракт (модульные файлы per module)** — отклонено: потребовало
бы создания ~12 новых файлов (по одному на модуль) для существующего репо,
блокируя пайплайн до их создания. Фактическое состояние никогда не
соответствовало этому контракту — enforcement сломал бы все открытые PR.
- **Опциональность через env-flag `OPENCODE_REQUIRE_PROJECT_MAP`** —
отклонено: docs-reviewer уже автосоздаёт initial README.md при отсутствии
каталога (`docs-reviewer.md:82-84`), feature-flag избыточен — guard
никогда не блокирует корректно настроенный pipeline-driven репо. Env-flag
добавил бы конфигурационную поверхность без выгоды.
- **Diff-based проверка (карта обновлена в PR через `gh pr view --json
files`)** — отклонено: сложнее в реализации (парсинг diff, фильтр по путям),
не гарантирует валидность содержимого (файл может быть изменён, но остаться
пустым/устаревшим). Существование README.md — более сильный guard (файл
присутствует), diff-based — слабее (файл изменён, но может быть невалиден).