Канон 5 объявил «каждый документ docs/ — тема ревью». Правило верно ровно наполовину и потому вредно целиком. Паспорт и схему хранилища ревью читает, но темами они не являются: по ним нельзя сказать «в этом изменении сделано не так», они задают границу, по которой судит чужая тема. Журнал решений и журнал наблюдений ревью изменения не нужны вовсе — ADR объясняет прошлое, а не предъявляет требование. Разметчик, применявший правило буквально, обязан был либо завести фантомные темы passport, adr, database, research и продублировать ими работу architecture и operations, либо потерять четыре документа молча; случались обе ветки, и в собственном образце плана docs/passport.md не попадал ни строкой, а обязательная арифметика покрытия при этом не сходилась. Категорий теперь три, разрез проверяемый. Тема — да, прямо: conventions, security, architecture и любой свой документ проекта. Источник темы — нет, но он задаёт границу для чужой: passport, database, CLAUDE.md, openspec/specs. Процессный — нет, он про то, как мы работаем: tasks, review, adr, research, .pm.json. Открыта одна категория из трёх, две другие перечислены поимённо, так что документ вне раскладки — однозначно своя тема. adr и research прогон больше не открывает ни одним проходом; docs/review остаётся читаемым, но как настройка конвейера, а не критерий. Цена записана и стала обязательной строкой границ покрытия: расхождение с записанным решением ловит теперь только сверка документации, а число под находкой обязано быть снято на этом прогоне, с приложенной командой. Классификация выдаёт задаче метку — small, medium, large. Прежние quick, standard и wide назывались ступенью и описывали ревью: как глубоко смотрим. Классифицируется же задача, и пока величина называлась свойством прогона, её естественно было пересчитывать на каждом прогоне — что конвейер и делал. Слово «ступень» удалено, а не оставлено синонимом: два имени одной вещи расходятся. Выводится метка из двух разведённых осей — размер (малое, среднее, крупное) и сложность (знакомое, незнакомое), — и равна максимуму по ним. Метка не синоним размера: малое незнакомое изменение получает large, трогая один узел, поэтому план печатает три строки с обоснованием каждая и выводить одну из другой запрещено. Оси остались русскими словами — это суждение прозой; метка английская — это идентификатор, который проходы сравнивают. Разметка переехала из ревью кода в шаг 4 пайплайна, сразу после propose. Она шла первым проходом каждого ревью кода, а перед ревью дизайна ту же величину называл сам пайплайн — то есть оркестратор, который только что довёл предложение до propose. Одно и то же измерялось дважды, и один из двух раз без разведённости с автором, ровно в той точке, ради которой разметчик заведён. Теперь запуск один на задачу, диффа он не видит, план обслуживает обе стадии, и метка после кода не пересматривается: расхождение факта с разметкой ловит журнал дефектов постфактум, как и всякую другую ошибку выбора. На диск план не пишется — четвёртый артефакт рядом с proposal, tasks и design пережил бы задачу и разошёлся бы с ней молча. Ревью дизайна тоже растёт меткой: small — specs, medium — плюс rubric, large — плюс architecture и вопрос автору о трёх формах решения. Раньше rubric и architecture включались одним условием, и medium получал ровно один проход, то есть не отличался от quick ничем. Разведены они потому, что зарабатывают на разном: рубрика порождает свойства узла и окупается уже на среднем изменении, её выход уезжает приёмочными критериями в tasks.md; архитектура отвечает на вопрос про второй способ, а он на среднем знакомом изменении отвечается «нет» ещё до запуска. small подешевел тремя способами сразу. Составом: приёмник тем не запускается, три темы ядра переходят к code сверкой по записанным инвариантам CLAUDE.md с потолком в одну находку, и это не «глубина ниже», а другой дом темы. Входом: specs читает только дельта-спеку, code — только индекс конвенций. Потолком: он появился у каждого опиниативного прохода, а не у одного basics, и у половин code он раздельный, потому что конвенционных находок больше по построению и в общем списке они вытеснили бы техническую половину. Сработавший потолок обязан быть объявлен строкой — молчащий срез неотличим от «больше не нашлось». Отрицательный тест small от этого стал жёстче, а не мягче: вопросы про обратимость миграции задавал приёмник тем, и на этой метке их не задаст никто. Пайплайн задачи вырос до двенадцати шагов. Тривиальность перестала решать состав ревью — она влияет только на explore; глубину обеих стадий называет метка. Проверено прогоном ревьюверов по готовому результату: девять расхождений найдено и починено — контракт находок печатал старый перечень проходов вместо плана по темам, три ссылки в task-batch указывали на шаг коммита вместо закрытия, запись changelog не переводила вопросы, адресованные passport и database, ops и adversary утверждали, что на нижних метках их вопросы задаёт basics, шаблон покрытия в review-code зашивал потолки small намертво, триггеры метки рассыпались на два списка против трёх, тема из директивы CLAUDE.md могла остаться без запуска исполнителя. Гейт зелёный: фронтматтеры, копии, одиннадцать диаграмм, ruff, pyrefly; docs.py прогнан на живом фикстуре и печатает категорию в отказе. Канон повышен до версии 6 с записью, выполнимой upgrade. Решения — 40–44. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
13 KiB
name, description
| name | description |
|---|---|
| docs | Вести содержимое документов канона по ходу разработки — синк после сделанной задачи с построчным отчётом по каждому документу, заведение ADR промоутом из архивного design.md, запись наблюдения в research, запись дефекта и настройки конвейера в review.md, чистка architecture.md от поведения с маркерами долга. Использовать, когда задача сделана и надо обновить документацию, когда просят завести ADR или записать решение, занести находку о внешних данных, записать проскочивший дефект, разгрузить разросшуюся архитектуру. Раскладку и соответствие канону проверяет скилл canon. |
Ведение содержимого канона
Скилл владеет содержимым документов канона; раскладкой владеет canon.
Определение канона и роли документов — канон,
здесь не пересказывается.
Главный вызывающий — шаг синка документации в пайплайне задачи. Пайплайн живёт в другом плагине и зовёт этот скилл по имени; проект без пайплайна ведёт документацию тем же скиллом вручную.
Правило, из которого всё следует
Принуждённое отрицание. Синк обязан назвать каждый документ канона: либо чем он обновлён, либо «не требуется, потому что…». Нетронутые группируются одной строкой с общей причиной.
Причина, по которой правило именно такое, измерена: у ADR был список триггеров прозой — и он дал 6 записей на 43 изменения. Прозаический триггер, который некому проверить, не срабатывает. Отличить «не написал» от «написал, что не требуется» можно только тогда, когда отрицание обязательно.
Это тот же приём, что «границы покрытия» в отчёте ревью и «пустое называется пустым» в каноне.
Чек-лист синка
Идёт сверху вниз; каждая строка попадает в доклад.
| Документ | Обновляется, когда | Проверка |
|---|---|---|
openspec/specs/ |
всегда при изменении поведения | вливает opsx:archive |
database.md |
тронуты миграции | docs.py check --base |
architecture.md |
новый компонент, граница, внешняя зависимость, изменилось окружение | docs.py: capability без упоминания |
adr/ |
дорогой откат, намеренный отказ, пересмотр прежнего | нет — только этот чек-лист |
research/ |
узнали новое о внешнем формате или данных | нет |
security.md |
новый недоверенный вход, токен, путь наружу, сдвиг периметра | нет |
conventions/ |
находка принята и не специфична для одного места | промоут |
review.md |
дефект воспроизведён; сузили или расширили проверку | нет |
passport.md |
новый потребитель, сдвиг границы «чем не является» | нет |
CLAUDE.md |
изменился инвариант, гейт, запрет, необратимое | нет |
Пример доклада:
Синк документации:
- architecture.md — добавлен воркер свёртки, ссылка на capability reindex
- database.md — миграция 00006, таблица bucket
- adr/ — заведён ADR-2026-08-03-queue-as-table: отказ от внешней очереди
- research/ — новое о формате не узнано
- passport, security, conventions, review — не требуется: изменение внутреннее
Сверка — не здесь, а на сессии
Синк правит документы поодиночке, а расходятся они между собой: факт,
дописанный в architecture.md, уже живёт в CLAUDE.md; периметр в
security.md не знает про новый эндпоинт. Поймать это на своей же правке нельзя,
и судит это агент doc-consistency.
Но синк его не зовёт. Оба судьи документов — doc-consistency и
doc-code-drift — зовутся раз в спринт, шагом сессии, на весь канон разом.
Причина в цене: doc-consistency на opus по каждой сделанной задаче — самая
дорогая церемония процесса, а doc-code-drift хоть и на sonnet, но читает
репозиторий целиком. К тому же расхождение между двумя документами по определению
требует двух документов, а на большинстве задач синк правит один.
Что теряется: привязка находки к задаче, которая её породила. Что выигрывается, кроме денег: синк перестаёт отбирать пачку, и в неё попадают документы, которых работа не касалась, — расхождение, внесённое правкой в одном месте, там и живёт.
ADR — промоут, а не второе сочинение
Обоснование уже написано: opsx:propose кладёт design.md в каждый change, и
после архивации он лежит в openspec/changes/archive/<id>/design.md с разделами
Context / Goals / Non-Goals / Decisions / Risks / Trade-offs.
ADR цитирует решение оттуда и ссылается на источник. Не пересказывает и не сочиняет заново.
Триггер заведения, форма имени и правило замены — в
каноне, раздел adr/. Здесь они не
повторяются: копия правила расходится с оригиналом на первой же смене версии
канона, а расходится незаметно.
Твоя часть — применить триггер к этой задаче и сказать вслух, сработал он или нет. Строка «adr/ — не требуется: решение рутинное» и есть то, ради чего чек-лист существует; её отсутствие неотличимо от «забыл посмотреть».
Порядок работы: открой архивный design.md change, найди в Decisions то, что
проходит триггер, процитируй решение и его причину, сошлись на источник, добавь
строку в индекс docs/adr/README.md сверху.
Чистка architecture.md
Обзор не держит поведение — его нормативный дом openspec/specs/. Форма
маркера долга и правило «гейт от них не краснеет» — в
каноне, раздел architecture.md.
Разбирается порциями: раздел вычищает та задача, которая его касается. Содержимое не выбрасывается, а переезжает — требования в дельта-спеку change, обоснование в ADR, обзор остаётся строкой со ссылкой на capability.
Запись в research/
Наблюдение о внешнем мире: что реально шлёт источник, чем документация формата
расходится с практикой. Требование провенанса и правило про расходящееся
число — в каноне, раздел research/.
Твоя часть — заметить, что по ходу задачи узналось новое о внешних данных, и не дать этому остаться в контексте. Признак: ты правил разбор, опираясь на то, чего нет ни в одном документе.
Запись в review.md
Файл держит два раздела с разными сроками жизни — журнал дефектов и настройку
конвейера. Что в каком и в какой форме — в
каноне, раздел review.md; подробности формы
записи и выбор адреса, куда она ведёт, — у конвейера ревью проекта (при
av-dev-pipeline — Skill av-dev-pipeline:review-pipeline, его
references/review-journal.md). Конвейера в проекте нет — пиши по форме из
скелета review.md, которую положил канон, и скажи в докладе, что подробностей
формы взять негде.
Твоя часть на синке: дефект пишется сразу, а не «потом, когда починим». Со временем теряется не факт, а то, почему дефект не поймали, — единственное, ради чего журнал есть. И решение сузить проверки (перестали звать проход, понизили метка) обязано попасть в раздел настройки, а не остаться в отчёте ревью.
Промоут в конвенции
Находка → конвенция → правило линтера → удаление из прозы. Процедура целиком
принадлежит конвейеру ревью проекта (при av-dev-pipeline — его
references/promote.md, читается через Skill av-dev-pipeline:review-pipeline);
роль каталога конвенций — в каноне. Конвейера
нет — три шага всё равно твои, просто без его процедуры: сформулируй правило,
поищи, чем оно механизируется, и вычеркни прозу, если механизировалось.
Твоя часть — третий шаг, который пропускают чаще всего: правило заработало, а формулировка осталась в прозе, и проход продолжает проверять уже проверенное. На синке это отдельная строка: «conventions/ — правило X механизировано, формулировка удалена» либо «не требуется».
Чего этот скилл не делает
- Не проверяет раскладку — это
canon. - Не заводит недостающие документы — их скелет кладёт
canon adoptилиinit. - Не сочиняет содержание. Нечего записать — так и пишется, честной строкой.
- Не переоформляет документы «заодно»: правится то, чего коснулась работа.