канон 4: тип записи стал единственной осью и задаёт схему
Осей было две — тип записи (goal/idea/task) и род работы (kind:<род> тегом), — и ортогональность у них была фальшивой: из двенадцати клеток произведения законны шесть. У цели род запрещён, у задачи обязателен, у идеи пуст и на практике не ставится. Плюс «алгоритм работы над записью такого типа» крепится не к task, а к fix и research, то есть к роду: ось, к которой пишется алгоритм, и была настоящим типом. Схлопнуто в одну ось из пяти значений: goal | feature | fix | chore | research. Тип idea упразднён отдельно и по другой причине: он значил не род работы, а незаполненность, а состояние типом быть не может — оно меняется по мере того, как запись дописывают, а тип меняют командой. Теперь состояние выводится из заполненности: research без раздела «Вопрос» это сырьё. В спринт не берётся, как и прежняя идея, лежит в конце категории, отбирается list --raw. Дом типа — поле меты «Тип» первой строкой, эмодзи в H1 производна. Прежнее «отдельного поля типа нет: два места для одного факта разъезжаются» отменено собственным аргументом: он был против префикса плюс поля, а при переносе дома место остаётся одно. Эмодзи стоит в H1, а не в строке индекса, чтобы инвариант «заголовок в индексе дословно» остался нетронутым. Поле места названо по типу: «Секция» у цели (часть роадмапа, состояние очереди), «Категория» у задачи (полка домена, куда её вернёт sprint drop). Одинаковое переименование закрепило бы конфляцию; какое поле обязательно, решает тип — то самое, ради чего затевалась правка. Два новых обязательных раздела выросли из правил, которые были записаны и которые нечем было проверить. «Не воспроизводится — это research, а не fix» стояло в каноне: теперь есть раздел «Воспроизведение». Приёмка разведки — «записанный ответ, а не изменённый код» — тоже стояла, но sprint take требовал от research два-пять критериев с оракулами, и они писались ради проверки; вместо них «Вопрос» и «Куда ляжет ответ». Сортировка «по важности» из заметок не взята: она требует, чтобы кто-то важность поддерживал, а это приоритет, от которого отказалось правило 4. Взято только «сырьё в конец категории» — этот порядок выводится из типа и заполненности, а не назначается человеком, и потому проверяется машиной. TYPE_SCHEMA кормит и body_template, и schema_verdict: иначе add кладёт то, на чём sprint take потом откажет. check --fix мигрирует за один проход — kind:/[goal]/[idea] в поле «Тип», эмодзи в заголовок, «Секция» → «Категория», сырьё в конец. Тип, которого неоткуда взять, не угадывается: feature от chore машина не отличает, такие записи уходят в НЕОДНОЗНАЧНО поимённо. Попутно закрыт класс отказов в --fix: шагов, правящих мету, стало пять, и второй, перечитавший файл с диска, стирал правку первого. Общий stage() поверх отложенных правок; до этого корректность держалась на том, что шагов было мало. Устав на тип отдельным файлом — references/task-<тип>.md, пять штук: схема, алгоритм, что видит машина и что человек. Агент task-form получил правило «тип сходится с тем, что в записи написано» с проверяемыми расхождениями. Обкатано на демо-наборе из 13 записей: миграция за один проход, второй прогон даёт ноль починок; fix без «Воспроизведения» и сырьё в спринт не идут, годная feature берётся. DECISIONS тема 27 (ААББ–ЛЛММ, следствия 101–104). Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,63 @@
|
||||
# ✨ `feature` — снаружи появляется то, чего не было
|
||||
|
||||
Задача, после которой наблюдаемое поведение меняется в сторону новой
|
||||
возможности. Отвечает на **«что нужно сделать»** и пишется глаголом в
|
||||
неопределённой форме.
|
||||
|
||||
Общая форма записи (мета, слаг, строка индекса) — [task-format.md](task-format.md).
|
||||
Здесь только то, что у этого типа своё.
|
||||
|
||||
## Схема
|
||||
|
||||
| | |
|
||||
| --- | --- |
|
||||
| Заголовок отвечает на | что нужно сделать («Печатать поле одним куском кода») |
|
||||
| Обязательные разделы | `Затрагивает`, `Критерии приёмки` |
|
||||
| Допустимые сверх того | `Рамки`, `Вопросы` |
|
||||
| Поле места | **Категория** — полка домена беклога |
|
||||
| Цель (`goal:<слаг>`) | **обязательна** |
|
||||
| Индекс | `BACKLOG.md` → `SPRINT.md` |
|
||||
| Берётся в спринт | да |
|
||||
|
||||
**Цель обязательна, и это единственный тип, у которого так.** Новая возможность
|
||||
и есть содержание цели: подходящей нет — либо она заводится, либо перед тобой не
|
||||
`feature`. `sprint take` без цели откажет.
|
||||
|
||||
## Алгоритм
|
||||
|
||||
1. **Найти цель или завести её.** Задача без цели, названная функцией, — самый
|
||||
частый способ пронести в беклог работу, которой никто не заказывал.
|
||||
2. **Назвать границы** в разделе `Затрагивает`: эндпоинт или команда, таблица и
|
||||
миграция, формат на диске, публичный тип пакета, внешний сервис. Названы
|
||||
**границы, а не замысел**: «переписать хранилище на новый драйвер» — замысел,
|
||||
`таблица points и её миграция` — граница. Проверяется вопросом «это можно
|
||||
назвать до того, как решено *как* делать?».
|
||||
3. **Написать критерии приёмки** — 2–5 проверяемых утверждений списком, у
|
||||
каждого назван оракул. Не «работает корректно», а «повторный прогон даёт тот
|
||||
же отпечаток — оракул: команда сверки».
|
||||
4. **Сказать, какую строку «Завершения» цели задача двигает.** Одной строкой в
|
||||
теле. Это защита от задачи «отрефакторить X»: она проваливается не потому,
|
||||
что невидима снаружи, а потому, что не находит строки, к которой относится.
|
||||
5. **Проверить, что задача одна.** Отвечается всё, но задача не делается одним
|
||||
заходом и не мерджится целиком — это несколько задач под одной целью, дроби
|
||||
сразу ([split.md](split.md)). Промежуточного зонтика между целью и задачей
|
||||
нет.
|
||||
6. **Реализация** — дело пайплайна проекта, не этого скилла. Закрывается
|
||||
`close <слаг> --implemented`: файл и строка удаляются, суть переезжает в
|
||||
`openspec/specs/` и документацию.
|
||||
|
||||
## Что видит машина, а что человек
|
||||
|
||||
`check` и `sprint take` смотрят на **наличие непустого** раздела `Затрагивает`,
|
||||
на **число** критериев (меньше двух — отказ, больше пяти — замечание) и на цель.
|
||||
Наличие оракула проверяется **эвристикой** — словом «оракул» в пункте.
|
||||
|
||||
Полнота перечня границ машине не видна: границу, которую забыли назвать, она от
|
||||
отсутствующей не отличает. Настоящий оракул от слова «оракул» тоже не отличает.
|
||||
Поэтому в докладе это называется как есть: «проверено число пунктов и наличие
|
||||
границ, годность оракулов и полнота границ — глазами».
|
||||
|
||||
**Критерии — пол, но расхождение с ними есть дефект критериев.** Видишь, что
|
||||
критерии закрыты, а суть задачи не достигнута — **правь критерии и возвращай
|
||||
задачу**, а не держи невидимое сверх-требование: иначе исполнитель никогда не
|
||||
знает, закончил ли, и мотивирован занижать критерии заранее.
|
||||
Reference in New Issue
Block a user