docs: review document for #727

Issue: #727
User-Visible: no
This commit is contained in:
claude[bot]
2026-10-01 00:18:39 +00:00
parent 499c0860df
commit fc835cb97d
2 changed files with 170 additions and 1 deletions
+2 -1
View File
@@ -1,6 +1,6 @@
# Индекс ревью
Генерируется `node scripts/reviews-index.mjs` (#635) — не редактировать руками. Документов: 218, issue: 109. Вердикт: 🟢 зелёный · 🟡 жёлтый · 🔴 красный · ⚪ не распознан (свободная форма старых документов). H/M — число High/Medium по строке вердикта или заголовкам находок. Файлы — пути, названные в находках; ищите по имени файла: `grep form-kit INDEX.md`.
Генерируется `node scripts/reviews-index.mjs` (#635) — не редактировать руками. Документов: 219, issue: 109. Вердикт: 🟢 зелёный · 🟡 жёлтый · 🔴 красный · ⚪ не распознан (свободная форма старых документов). H/M — число High/Medium по строке вердикта или заголовкам находок. Файлы — пути, названные в находках; ищите по имени файла: `grep form-kit INDEX.md`.
| Issue | Документ | Этап · раунд | Вердикт | H | M | Находки | Файлы |
|---|---|---|---|---:|---:|---|---|
@@ -8,6 +8,7 @@
| #732 | [CODE-REVIEW-732-r1.md](CODE-REVIEW-732-r1.md) | code · r1 | 🟢 зелёный | 0 | 0 | — | — |
| #728 | [SPEC-REVIEW-728-r1.md](SPEC-REVIEW-728-r1.md) | spec · r1 | 🟡 жёлтый | 1 | 0 | 1. АС3/К3: заявленное различение причин validate-red и conflict «на текстах из констант…; 2. АС8: заявленное доказательство правки process-metrics.yml (fetch-depth: 0, timeout-m… | `wait-verdict.mjs` `review-doc-guard.mjs` `scripts/wait-verdict.mjs` `.github/workflows/_process.yml` `_process.yml` `_process-metrics.yml` `test/process-metrics.test.mjs` |
| #727 | [SPEC-REVIEW-727-r1.md](SPEC-REVIEW-727-r1.md) | spec · r1 | 🟡 жёлтый | 0 | 1 | К7/AC7: архивирование ночного документа с базой-стабильным-тегом не имеет ни одного про… | `scripts/reviews-archive.mjs` |
| #727 | [SPEC-REVIEW-727-r2.md](SPEC-REVIEW-727-r2.md) | spec · r2 | 🟢 зелёный | 0 | 0 | — | — |
| #726 | [SPEC-REVIEW-726-r1.md](SPEC-REVIEW-726-r1.md) | spec · r1 | 🟢 зелёный | 0 | 0 | — | — |
| #725 | [SPEC-REVIEW-725-r1.md](SPEC-REVIEW-725-r1.md) | spec · r1 | 🟢 зелёный | 0 | 0 | устаревший номер строки в «Проблема» п.3 / «Не-скоуп» | `src/iso-scene-render.ts` `src/houseplan-card.ts` `houseplan-card.ts` `header-menu.ts` `iso-scene-render.ts` |
| #724 | [CODE-REVIEW-724-r1.md](CODE-REVIEW-724-r1.md) | code · r1 | 🟢 зелёный | 0 | 0 | — | — |
+168
View File
@@ -0,0 +1,168 @@
# SPEC-REVIEW-727-r2
Issue: #727 · этап: spec · трек: ask · заход: r2 · блокирующих циклов израсходовано (после этого раунда): 1/4
## Скоуп
#727 — первая из двух независимых частей, выделенных из #707 п.3: ночное
пакетное ship-ревью на `dev` и переиспользование его результата в гейте беты
(`ship-review.mjs check`). Контракт не изменился с r1: К1 (патч-набор по
`git patch-id --stable`), К2 (ночной режим `tag=nightly`, имя документа
`SHIP-REVIEW-<база>-dev-<sha12>.md`), К3 (`shipCoverage`:
`clean`/`high`/`stale`/`none`), К4 (гейт `check` по покрытию), К5 (дельта
беты), К6 (job в `_nightly.yml`), К7 (индекс и архив узнают ночное имя), К8
(комментарий в задачу при High), К9 (канон). Красная ночь — отдельный issue E,
не входит. Продуктового кода нет, `User-Visible: no`, трек `ask` обоснован
(см. r1 и подтверждение ниже).
Этот раунд — правка автора по единственной находке r1 (Medium, К7/АС7): К7
переписан, в АС7 добавлены четыре конкретных примера вход→выход. Комментарий
автора 2026-10-01T00:13:45Z («ТЗ исправлено по ревью r1 ... Возвращаю на
ревью ТЗ») и пометка в ТЗ («Правка по ревью r1 сверена с `a49f7095`: файлы,
которые называет ТЗ, между этими коммитами не менялись») задают материал
раунда. Разбор — по дельте (§2.10): объём сопоставим с одной находкой,
ребейза, смены контракта или новой подсистемы нет — сокращаю объём разбора,
не строгость.
## Как проверялось
1. **Закрытие находки r1** — построчное сравнение текста К7/АС7 r1 (квоты в
`docs/reviews/SPEC-REVIEW-727-r1.md`) с текущим телом issue + текст
комментария автора, описывающий правку.
2. **Проверка новой логики по коду на материале ревью** (`HEAD` рабочей копии
`a49f7095ce77def25cc1ec4d48b390ec62d84bfd`, совпадает с материалом, названным
в задаче): прочитан целиком `scripts/reviews-archive.mjs` (`archivePlan`,
`compareStable`, `stableTagsThrough`), `scripts/reviews-index.mjs`
(`parseDocName`, `SHIP_DOC_NAME`), `test/ship-review.test.mjs` (тест #696,
строка 79-93) — каждый новый технический пример АС7 (а/б/в/г) проверен на
реализуемость существующими примитивами.
3. **Локальность дельты**: `git diff 40607aa37f13..HEAD --stat` и точечный
`git diff` по файлам, которые называет ТЗ (`scripts/ship-review.mjs`,
`scripts/reviews-index.mjs`, `scripts/reviews-archive.mjs`,
`.github/workflows/_nightly.yml`, `.github/workflows/_ship-review.yml`,
`.github/workflows/ship-review.yml`, `test/ship-review.test.mjs`,
`test/nightly-workflow.test.mjs`, `test/process-digests.test.mjs`,
`PROCESS.md`, `docs/process/REVIEWER.md`) — пусто: материал r1 не устарел.
4. Сверка текущего §11.7 PROCESS.md с формулировкой «публичного контракта» в
обосновании трека `ask`.
5. Гейты: `npx tsc --noEmit` (узел не содержит `node_modules`, зависимости на
этапе spec не ставились — #696, ожидаемо и не блокирует), мутант и
`entry-cost` проверены точечным чтением/запуском (ниже).
## Закрытие раунда r1
| Находка r1 | Чем закрыта | Где это видно |
|---|---|---|
| Medium (К7/АС7): правило «база — стабильный тег → первая архивируемая линия новее базы» не реализуемо точным совпадением `archivePlan`, и АС7 не даёт для этой ветки ни одного примера вход→выход | К7 переписан: явно разделены две ветки архивации (база-бета — точное совпадение, как сегодня; база-стабильный тег — «наименьшая архивируемая линия строго новее базы», `compareStable`, названа как новая логика). АС7 получил четыре конкретных примера (а: база-бета → `v1.79.0`; б: `[v1.78.0, v1.79.0]`, база `v1.78.0` → `v1.79.0`; в: `[v1.78.0, v1.78.1, v1.79.0]` → `v1.78.1`, ближайшая, не последняя; г: линии новее нет → `kept` с новой причиной) | Тело issue #727, раздел «Контракт поведения» → К7 (три подпункта: база-бета / база-стабильный тег / подходящей линии нет); таблица «Критерии приёмки» → АС7 (все 4 примера); раздел «Граничные случаи» (окно между релизом и бетой) и «Чем краснеет» (два новых отрицательных случая, явно привязанных к АС7 б/г) |
Проверка покрытия по существующему коду:
- `compareStable` (`scripts/reviews-archive.mjs:46-50`) и `stableTagsThrough` (`:53-57`) уже существуют и реализуют именно сравнение, которое нужно для «наименьшая линия строго новее базы» — К7 корректно называет существующий примитив, а не выдумывает его.
- Сегодняшняя ветка `stage === 'ship'` (`scripts/reviews-archive.mjs:91-97`) действительно ищет точное совпадение (`tags.has(line)`) и не умеет искать «следующий по порядку» тег — ровно тот пробел, который r1 называл находкой; К7 теперь явно описывает его как новую логику, а не как уже работающую.
- Пример (б) и (в) оба реализуемы одной и той же операцией: `ordered.filter(l => compareStable(l.tag, base) > 0)[0]` (где `ordered` — уже отсортированный по возрастанию массив строк кода) — даёт «ближайшую, не последнюю» линию без дополнительных допущений.
- Пример (а) — существующая ветка, не меняется; тест `#696` (`test/ship-review.test.mjs:78-93`) продолжает работать как сегодня, АС7 это прямо фиксирует («`deepEqual` теста `#696` не меняется») — проверено построчным чтением теста, сигнатура `assert.deepEqual(parseDocName('SHIP-REVIEW-v1.79.0-beta.1.md'), { stage: 'ship', issue: null, round: null, suffix: null, tag: 'v1.79.0-beta.1' })` не содержит поля `nightly` — реализация обязана добавлять `nightly: true` только условно (для ночных имён), что соответствует формулировке АС7 («`nightly: true`» называется только для нового примера, не для старого) и не противоречит незыблемости старого теста.
Находка закрыта полно: ветка, для которой АС7 не имел примера, теперь имеет все четыре требуемых случая (положительный×3 с различием «одна линия / несколько линий / ближайшая vs последняя», отрицательный), и реализуемость каждого подтверждена существующими примитивами, а не только декларацией.
## Унаследовано из r1
Без повторной проверки принято всё, что r1 зафиксировал в разделе «Что
проверено и корректно» (`docs/reviews/SPEC-REVIEW-727-r1.md`, материал —
`origin/dev` `40607aa37f13819c9db37a392a1d99f30382b3c0`), поскольку дельта его
не касается и диапазон `40607aa3..a49f7095` не трогает ни один из файлов,
которые называет ТЗ (проверено `git diff --stat` в этом раунде, см. «Как
проверялось» п.3):
- существование и сигнатуры `readCandidateHistory`, `issueTrailers`,
`shipReviewDocPath`, `isShipIssue`, `specSection`, `shipIssuesInRange`,
`renderShipBrief`, `anchorBlock`, `parseAnchorBlock`, `shipReviewProblems`,
`readShipDoc`;
- `RELEASE_TAG_RE`, текущий машинный блок документа беты и его поля;
- реальность тега `v1.79.0-beta.1`, документа `SHIP-REVIEW-v1.79.0-beta.1.md`,
коммита `dca0fd28` с трейлерами `Issue:`/`Release:`;
- `SHIP_DOC_NAME`/`parseDocName` сегодня не знают ночной суффикс;
- содержимое `_nightly.yml` (job `dispatch`, ожидание до 3 минут, токен
`github.token`), входы и права тонких файлов `ship-review.yml`;
- `HP_PROCESS_TOKEN` как существующий секрет публикации;
- мутант `ship-review-ignores-merge-marker` (`scripts/mutation-registry.mjs`),
команда `node scripts/entry-cost.mjs --check`;
- существование `test/process-digests.test.mjs`, `test/ship-review.test.mjs`,
`test/nightly-workflow.test.mjs`;
- обязательные разделы §7.1 присутствуют и в правильном порядке;
- обоснование трека `ask` (сложность/риск >3, публичный контракт §11.7).
Точечно переподтверждено в этом раунде (не просто унаследовано): §11.7
PROCESS.md прочитан заново (строки 1555-1583) — формулировка «документ обязан
лежать в кандидате или в `dev`, покрывать их все и не нести High» совпадает
дословно с тем, что обоснование трека `ask` называет «сегодняшним» правилом.
## Что проверено и корректно (этот раунд)
- К7/АС7 — полностью, см. «Закрытие раунда r1» выше.
- «Принято предположительно» — пункт 7 (новый): «Линия ночного документа со
стабильной базой — ближайшая архивируемая линия новее базы, а не линия по
трейлерам его задач» — корректно резюмирует именно то решение, что описано
в К7, не вводит противоречия с остальными 6 пунктами (не изменились).
- «Чем краснеет» — два новых отрицательных случая («ночной документ со
стабильной базой не уходит в каталог самой базы (АС7 б)», «без более новой
линии остаётся на месте (АС7 г)») точно соответствуют новым примерам АС7, не
дублируют и не противоречат трём прежним пунктам.
- «Затронутые файлы» — уточнение «(`archivePlan`: новая ветка для ночного
документа со стабильной базой)» верно называет функцию, которую правка
действительно трогает (проверено чтением `scripts/reviews-archive.mjs`, не
исполнением — продуктового кода задачи ещё нет).
- Материал не устарел: файлы ТЗ не менялись между `40607aa3` и `a49f7095`
(гейт «материал ревью не запушен/не устарел» выполнен).
## Чего не проверял
- Гейты (`npx tsc --noEmit`, `npm test`, `npm run build`) не прогонял по
существу — `node_modules` не установлены (зависимости на этапе spec не
ставятся, #696), а задача не меняет ни одного файла репозитория на этом
этапе: показывать «зелёный»/«красный» тестов, которых ещё нет, не на чем.
Обязательны на `S7-code-review`.
- Не проверял, что `ordered.filter(...)` (конкретная реализация «ближайшей
линии новее базы», которую я предложил как пример реализуемости) —
единственно возможная или будущая реализация автора; это право
реализатора, спецификация фиксирует только вход/выход АС7.
- Golden/смоки/бэкенд-pytest/инварианты модели — не относится: задача класса A
не содержит, геометрии и визуала не касается.
- Не проверял повторно всё, что уже подтверждено в r1 (список — раздел
«Унаследовано из r1»); точечно перепроверено только §11.7 PROCESS.md.
- Не проверял реальный прогон `git patch-id --stable` и `workflow_dispatch`
между workflow-файлами — та же причина, что в r1 (документированное
поведение инструментов, не специфика этого кода); дельта этого раунда их не
касается.
## Вердикт
Единственная находка r1 (Medium, К7/АС7) закрыта: правило архивации для
ночного документа со стабильной базой теперь описано отдельной веткой с
названным существующим примитивом (`compareStable`), и АС7 содержит четыре
конкретных примера вход→выход, включая отрицательный случай — реализуемость
каждого подтверждена чтением существующего кода, а не только текстом ТЗ.
Новых находок в дельте нет. Материал не устарел (файлы ТЗ не менялись между
`40607aa3` и `a49f7095`). Трек `ask` обоснован с r1 без изменений.
**Вердикт: зелёный · заход r2 · блокирующих циклов 1/4 · High: 0 · Medium: 0**
## Материал раунда
- Этап: spec. Материал — тело issue #727 на момент комментария Matysh
2026-10-01T00:13:45Z («ТЗ исправлено по ревью r1 ... Возвращаю на ревью
ТЗ»).
- Кода/ветки продукта не существует (инфраструктурная задача до реализации);
факты сверены с рабочей копией на `HEAD` = `a49f7095ce77def25cc1ec4d48b390ec62d84bfd`.
---
<!-- material-anchors: сгенерировано конвейером (#414) -->
## Материал раунда
- Ветка: `dev`, коммит `a49f7095ce77` — ребейз его осиротит, и это нормально: ниже якоря, которые ребейз не меняет.
- Дерево материала: `b65ac0114507ee69bdb435b2ba9f006de09b4e26`
```
git log --all --format='%H %T' | grep b65ac0114507
```
- Тело issue: `8ce2942ca915bc938c8c5b4a720bb71d5a06d18c13db0692ee802f6a55662b7a`
- Вердикт конвейера: `green` · High 0