mirror of
https://github.com/Matysh/houseplan-card
synced 2026-09-30 11:49:16 +00:00
@@ -0,0 +1,159 @@
|
||||
# SPEC-REVIEW-43-r2
|
||||
|
||||
- Issue: https://github.com/Matysh/houseplan-card/issues/43
|
||||
- Ревьюер: Claude (роль «Ревьюер ТЗ», PROCESS.md §2.4)
|
||||
- Материал: `docs/specs/043-private-support-report.md` на коммите `e25aa302`
|
||||
(ветка `issue/43-help-feedback`), дельта против r1 (`docs diff
|
||||
00b68450..e25aa302 -- docs/specs/043-private-support-report.md`).
|
||||
- Заход: r2 · блокирующих циклов израсходовано 1 из 4.
|
||||
- Трек: полный (не изменился с r1).
|
||||
- Формат разбора: **по дельте** (PROCESS.md §2.9, issue #214) — обоснование
|
||||
ниже, в «Почему делаю по дельте, а не заново».
|
||||
|
||||
## Предыдущий раунд
|
||||
|
||||
- Вердикт r1: жёлтый · High 0 · Medium 1 (в скоупе) · Low 1 (снят без цикла).
|
||||
- Комментарий с вердиктом: issue #43, 2026-09-01T20:40:11Z.
|
||||
- Документ r1: `docs/reviews/SPEC-REVIEW-43-r1.md`, зафиксирован коммитом
|
||||
`4559b5cd`.
|
||||
- SHA, на котором получен вердикт r1: `755fa4cf` (упомянут в тексте вердикта
|
||||
и в шапке `SPEC-REVIEW-43-r1.md`). Этот SHA не резолвится в текущем дереве —
|
||||
автор пишет в хендоффе r2 «Ветка перебазирована на актуальный dev», и
|
||||
`git rebase` переписал хеши; коммит с тем же содержимым сегодня называется
|
||||
`00b68450` (`git diff 00b68450..HEAD` даёт содержательно тот самый и
|
||||
единственный дифф, который описывает хендофф r2).
|
||||
|
||||
## Почему делаю по дельте, а не заново
|
||||
|
||||
Формально это ребейз на ушедший вперёд `dev` — сценарий, для которого
|
||||
инструкция требует полного разбора, если ребейз действительно сделал это
|
||||
«другим кодом» (§7.2). Проверил, что это не тот случай:
|
||||
|
||||
- `git merge-base HEAD origin/dev` = `4fa670e8`; коммиты `dev` между старой и
|
||||
новой базой (`823fc316..4fa670e8`: пин растеризации скриншотов, измерение
|
||||
дрейфа кадра, гейт стабильности) не трогают ни `AGENTS.md`, ни
|
||||
`PROCESS.md`, ни `scripts/process-gate.mjs`, ни `docs/TOUCH-SUPPORT.md` —
|
||||
`git diff --stat` по этим путям в диапазоне пуст. Это ровно те четыре
|
||||
документа, на которые опирались обе находки r1.
|
||||
- `git diff 00b68450..HEAD --stat` показывает три файла: добавленный документ
|
||||
ревью `docs/reviews/SPEC-REVIEW-43-r1.md` (артефакт публикации, не правка
|
||||
автора), `docs/specs/README.md` (1 строка, не содержательная), и
|
||||
`docs/specs/043-private-support-report.md` — 24 изменённые строки, все три
|
||||
правки локализованы в §9.1, §11 и §18 и построчно соответствуют двум
|
||||
находкам r1.
|
||||
- Ни договор поведения (§4/§6–8), ни AC1–AC17 (§13), ни privacy allowlist
|
||||
(§7.2/7.3), ни UX-контракт (§6) дельта не задевает.
|
||||
|
||||
Поэтому разбор r2 ограничен: (а) доказать закрытие двух находок r1 построчно,
|
||||
(б) проверить, что дельта не сломала ничего в соседних разделах, (в)
|
||||
унаследовать всё остальное из r1 без повторной проверки.
|
||||
|
||||
## Закрытие раунда r1
|
||||
|
||||
| Находка r1 | Чем закрыта | Где это видно |
|
||||
|---|---|---|
|
||||
| **Medium.** `support-relay/**` как новый top-level каталог не попадает ни в класс A, ни в B `scripts/process-gate.mjs::classify()` → коммит, трогающий только этот каталог, проходит гейт без трейлера `Issue:` и без проверки статуса issue. | §9.1 переписан: relay переехал под `scripts/support-relay/**`, что совпадает с `CLASS_B` (`/^scripts\//` в `scripts/process-gate.mjs:59`) без каких-либо правок `AGENTS.md`/`PROCESS.md`/`process-gate.mjs`. §18 добавляет обязательство держать runtime/manifest/tests/README relay целиком в этом поддереве и завести process-gate regression fixture, доказывающую, что relay-only коммит классифицируется как B. | `docs/specs/043-private-support-report.md:404-412` (§9.1), `:621-623` (§18). Проверено запуском `node scripts/process-gate.mjs` на HEAD — «гейт пройден, предупреждений 0», путь `scripts/support-relay/` реально попадает в `CLASS_B` по regex `scripts/process-gate.mjs:59`. |
|
||||
| **Low.** §11 по содержанию реализует `Touch editor: supported`, но не содержит канонической фразы, которую требует `docs/TOUCH-SUPPORT.md`. | В §11 первой строкой добавлено `**Touch editor: supported.**` с уточнением, что диалог доступен из View и всех трёх редакторов с одинаковым touch-контрактом, а kiosk по-прежнему его скрывает. | `docs/specs/043-private-support-report.md:465-467`. Фраза дословно совпадает с канонической формой из `docs/TOUCH-SUPPORT.md:165` (`Touch editor: supported`). |
|
||||
|
||||
Обе находки закрыты текстом, а не заявлением: правка видна в дифф-контексте
|
||||
выше, а не только в комментарии автора.
|
||||
|
||||
## Проверка дельты (не унаследовано — перепроверено заново)
|
||||
|
||||
1. **Согласованность пути relay по всему документу.** `grep -n
|
||||
"support-relay" docs/specs/043-private-support-report.md` даёт ровно два
|
||||
совпадения (§9.1 заголовок и §18 release-артефакты) — оба уже указывают на
|
||||
`scripts/support-relay/**`, старого top-level упоминания `support-relay/`
|
||||
без префикса нигде не осталось. Более широкий `grep -n "relay"` (60+
|
||||
вхождений по всему файлу) показал, что остальные упоминания — это
|
||||
архитектурная роль сервиса («project-controlled relay», «relay secret»,
|
||||
«relay fixture» и т.д.), а не файловый путь, поэтому переезд каталога их
|
||||
не касается — переименование сделано полностью, частичной правки нет.
|
||||
2. **Не нарушает ли новое место relay границу HACS-пакета.** `hacs.json`
|
||||
(`zip_release: true`, `filename: houseplan.zip`) не перечисляет
|
||||
содержимое явно — упаковка определяется отдельным релизным шагом, не
|
||||
`process-gate.mjs`; `scripts/**` и раньше не попадал в
|
||||
`custom_components/houseplan/frontend/` (единственный источник
|
||||
HACS-фронтенда по `CLASS_D`). Утверждение «excluded from the HACS
|
||||
artifact» в §9.1 остаётся верным после переезда, это не новый риск,
|
||||
привнесённый дельтой.
|
||||
3. **Не конфликтует ли `scripts/support-relay/**` с существующей ролью
|
||||
`scripts/`.** `tsconfig.json` ограничивает typecheck `src/**/*.ts`;
|
||||
каталог `scripts/` уже состоит из `.mjs`/`.py`-скриптов вне зоны
|
||||
компиляции TS — новый relay-код в том же дереве не меняет эту границу и
|
||||
не требует правки `tsconfig*.json` (что и означало бы `A+B`, а не только
|
||||
`B`, в терминах самого §9.1).
|
||||
4. **Формулировка "a product commit that also changes `src/**` remains A+B и
|
||||
follows the stricter class-A flow"** (§9.1) сверена с
|
||||
`scripts/process-gate.mjs:137` (`classes: new Set(files.map(classify))`) и
|
||||
условиями `classes.has('A') || classes.has('B')` для строгих проверок —
|
||||
описание корректно: набор классов коммита — это множество классов всех
|
||||
его файлов, а не единственная метка.
|
||||
5. **Трейлеры коммита дельты.** `git show e25aa302 -s` → `Issue: #43`,
|
||||
`User-Visible: no` — верно для docs-only правки без видимого поведения.
|
||||
6. **Гейты на этой дельте.** Дифф `00b68450..e25aa302` строго класса C
|
||||
(только `docs/specs/043-private-support-report.md`). Прогнал:
|
||||
- `node scripts/process-gate.mjs` → «диапазон origin/dev..HEAD, коммитов
|
||||
3; гейт пройден, предупреждений 0» (офлайн, без `--issues`);
|
||||
- Validate CI на `e25aa302` зелёный (см. ссылку в хендоффе автора и в
|
||||
инструкции ревью) — покрывает `tsc --noEmit`/`npm test`/`npm run
|
||||
build`, предмета для которых у docs-only дельты и так нет.
|
||||
`check-docs.mjs`, browser-смоки, `model-invariants`, `pytest
|
||||
tests_backend`, golden — не прогонял: `src/**`, `custom_components/**` и
|
||||
геометрия/`layout` дельтой не тронуты, у этих гейтов нет предмета
|
||||
проверки на чисто документном коммите (то же обоснование, что в r1).
|
||||
|
||||
## Унаследовано из r1 (без повторной проверки)
|
||||
|
||||
Документ: `docs/reviews/SPEC-REVIEW-43-r1.md`, зафиксирован на `4559b5cd`,
|
||||
разбирал ТЗ на `00b68450` (тогда назывался `755fa4cf` до ребейза).
|
||||
Дельта r1→r2 не задевает ни один из пунктов ниже, поэтому принимаю выводы r1
|
||||
без повторной проверки:
|
||||
|
||||
- Обязательные разделы §7.1 (сценарий, до/после, проблема, скоуп, контракт
|
||||
поведения, UX, модель данных/миграция, i18n, AC1–AC17, план автотестов,
|
||||
риски, откат, release-артефакты) — все на месте и однозначны.
|
||||
- Продуктовые вопросы Q1–Q5 корректно отделены от технических и закрыты
|
||||
владельцем в issue дословно, без додумывания.
|
||||
- Пять утверждений §3 о текущем состоянии кода проверены построчно по
|
||||
`src/houseplan-card.ts`, `src/houseplan-editor-runtime.ts`,
|
||||
`custom_components/houseplan/{websocket_api,import_export,repairs}.py`,
|
||||
`src/i18n/*.json` — расхождений не найдено.
|
||||
- Privacy allowlist/exclusion §7.2/7.3 внутренне непротиворечивы; точная
|
||||
геометрия включена осознанно как продуктовое решение (Q2), а не побочный
|
||||
эффект.
|
||||
- «Одно число — один источник» для preview/download/submit спроектировано
|
||||
контрактом (кешированный TTL-токен + mutation-gate §6.4/7.1/8.1/AC5/AC10 +
|
||||
§14.4), а не оставлено на волю реализации.
|
||||
- Технические допущения промаркированы в §20 как «assumed, change freely».
|
||||
- i18n RU/EN/DE/FR соответствует уже существующим локалям, список языков не
|
||||
расширяется произвольно.
|
||||
- Cross-links issue↔ТЗ↔`docs/specs/README.md` на месте.
|
||||
- DoR-зависимости §17 (relay deployment, mailbox, staging) корректно вынесены
|
||||
как внешние операционные факты с явным `blocked`-путём, а не спрятаны как
|
||||
допущения.
|
||||
|
||||
## Чего не проверял (r2)
|
||||
|
||||
- Полные `npm test`/`npm run build`/browser-смоки/`model-invariants`/`pytest
|
||||
tests_backend` — не прогонял отдельно: Validate CI зелёный на этом самом
|
||||
SHA (`e25aa302`), а дельта и так docs-only без предмета для этих гейтов.
|
||||
- Реальная развёртываемость relay, секреты, содержимое ещё не написанного
|
||||
`scripts/support-relay/**` — кода ещё нет, это заявленная DoR-зависимость
|
||||
§17/§18, появится на этапе реализации и code-review.
|
||||
- Golden/скриншоты, performance-профили — не относятся к докс-only дельте.
|
||||
- Process-gate regression fixture, которую §18 требует для доказательства
|
||||
классификации relay-only коммита как B — она появится вместе с кодом;
|
||||
на этапе ТЗ можно проверить только текст требования (проверено, есть).
|
||||
|
||||
## Вывод
|
||||
|
||||
Обе находки r1 закрыты предметно, построчно и без побочных повреждений
|
||||
соседних разделов: relay-код явно и полностью перенесён в уже
|
||||
классифицированный класс-B каталог `scripts/support-relay/**` (подтверждено
|
||||
чтением `scripts/process-gate.mjs` и живым прогоном гейта), а §11 получил
|
||||
каноническую фразу `Touch editor: supported`, дословно совпадающую с
|
||||
требованием `docs/TOUCH-SUPPORT.md`. Ребейз на актуальный `dev` не изменил
|
||||
существа рассмотрения: коммиты `dev`, вошедшие в диапазон, не трогают ни один
|
||||
документ, на который опирались находки r1. Новых находок в дельте нет.
|
||||
Rec: **зелёный**, готово к переводу в `S5-ready`.
|
||||
Reference in New Issue
Block a user