16 KiB
SPEC-REVIEW-640-r1
Скоуп ревью
Этап: ревью ТЗ (PROCESS.md §2.4), трек small. Заход r1, блокирующих циклов
израсходовано 0 из 2 (лимит цикла ревью ТЗ на лёгком треке — 2, §5).
Предмет: раздел ## ТЗ в теле issue #640 — точечная замена menu-иконки
категории dishwasher («Посудомоечная машина», группа «Техника») в палитре
мебели на рисунок из приложенного архива dishwasher.zip, без изменения
планового символа, публичного ID, размеров (60×60 см) и любых сохранённых
данных.
Материал ревью: тело issue #640 (раздел ## ТЗ) и оба комментария
(Оценка: ..., ТЗ добавлено ...) на момент чтения, working tree на
f234855e (HEAD detached), продуктовый код не менялся — подтверждено git status (clean) и текстом комментария автора.
Как проверялось
Продуктового диффа нет (только текст ТЗ в issue), поэтому дешёвые гейты
(typecheck/test/build) не запускались — репозиторий не тронут этой
задачей на этапе спецификации. Вместо гонки гейтов каждое фактическое
утверждение ТЗ сверено с текущим состоянием репозитория:
| Утверждение ТЗ | Проверка | Результат |
|---|---|---|
| «остальные 32 menu-иконки» | ls assets/furniture/houseplan-0.4.1/svg/menu |
33 файла всего, 33−1=32 — совпадает |
viewBox 110×110, безопасный menu-контракт (только svg/g/path, svg только viewBox,xmlns, path только d/fill/stroke/stroke-width/stroke-linecap/stroke-linejoin, fill=none, stroke=currentColor, круглые linecap/linejoin) |
прочитан scripts/generate-furniture-assets.mjs (svgArt(), парсер атрибутов) и текущий dishwasher.svg |
контракт существует буквально в описанном виде и уже применён к текущему файлу — ТЗ не изобретает требование |
группа «Техника», названия ru/en, размеры 60×60, menu_icon: dishwasher |
прочитан assets/furniture/houseplan-0.4.1/pack.json |
group: "appliance", name_ru: "Посудомоечная машина", width_cm/depth_cm: 60 — совпадает |
| «иконки редактора остаются в ленивом editor-графе» | прослежен путь decor-image-editor.ts → houseplan-editor-runtime.ts → houseplan-card.ts:720 await import(...) |
подтверждено: путь до GENERATED_FURNITURE_MENU целиком за динамическим import(), в стартовый граф не входит |
golden-сцена furniture-categories-light существует и показывает категории (не единственную) |
demo/golden/matrix.mjs:619 |
сцена есть, furniturePalette: 'categories' — показывает плитки категорий, а не один вариант |
| «новые скриншоты документации не нужны» | grep furniture demo/docs/screenshots.mjs — 0 совпадений; единственный сценарий с decor (07-background-editor.png) использует editorTray: 'decor-selection', а это трей выбора объекта декора (_decorSel), не палитра мебели |
подтверждено — палитра мебели ни в одном сценарии документации не фигурирует |
npm run furniture:generate / npm run furniture:check существуют |
package.json:46-47 |
оба скрипта определены как заявлено |
| существующий unit ленивой загрузки для AC3 | demo/smoke_furniture_lazy_art.mjs найден |
подтверждает наличие свидетеля, хотя ТЗ называет его «unit», а по факту это browser-smoke; см. находку Low ниже |
нет других мест в src/**, где рисуется/дублируется menu-иконка dishwasher (проверка «одно число — один источник» применительно к арту) |
grep -r dishwasher src/ |
только генерированные файлы и i18n-строки (названия, не геометрия); единственный потребитель generated menu-art — decor-image-editor.ts |
Дешёвые гейты typecheck/test/build не гонялись — на этапе ТЗ нет
продуктового диффа, гонять их не по чему. Ссылка на зелёный Validate из
контекста задачи (f234855e) относится к предыдущей задаче (#614) и здесь
не переиспользуется как доказательство: доказывать было нечего.
Проверка обязательных разделов (PROCESS.md §7.1)
Все обязательные разделы присутствуют и в правильном порядке (сценарий и «что человек увидит» — первыми):
- Сценарий — есть, называет персону (администратор,
docs/SCOPE.md), поверхность (редактор подложки, палитра мебели) и момент (перед добавлением предмета); - Что человек увидит до/после — есть, без терминов реализации;
- Проблема/скоуп/не-скоуп — есть, скоуп точен (один файл), не-скоуп явно перечисляет плановый SVG, ID, названия, размеры, сохранённые данные, остальные иконки, backend, i18n;
- Контракт и UX — есть, технически точен (сверено с кодом, см. таблицу выше);
- Данные/миграция/i18n/perf/touch — есть, единым абзацем, все пункты закрыты явным «не меняется»/«не нужна»;
- AC1…AC3 с указанием доказательства — есть, см. разбор ниже;
- План автотестов — есть;
- Риски и откат — есть;
- Release-артефакты — есть, требует правки обоих changelog;
- Блок принятых предположений — есть, оба пункта в границах технических решений автора, не продуктовых.
Дополнительно ТЗ содержит незаявленный процессом, но уместный раздел
«Происхождение и право использования» — фиксирует provenance приложенного
архива (сотрудник JustBusiness, право MIT-использования, ранее подтверждено
владельцем). Это не догадка: аналитический комментарий тем же автором
детализирует содержимое архива (SHA-256, viewBox, отсутствие активного
XML) — похоже на результат реального осмотра вложения владельцем, а не
предположение, выданное за факт.
Разбор критериев приёмки
- AC1 («новая menu-иконка», доказательство: unit + golden
furniture-categories-light+ ревью diff) — однозначен и проверяем: число «32» подтверждено подсчётом файлов, golden-сцена существует и показывает категории. Байтовое сравнение прочих 32 файлов — за автором на этапе кода, тестируемо unit-тестом (сравнение содержимого файлов). - AC2 («плановый контракт неизменен») — однозначен, перечисляет конкретные инварианты (файл, ID, группа/категория, ru/en названия, 60×60 см, рендер размещённых объектов), доказательство unit + diff — проверяемо чтением изменённых файлов на код-ревью.
- AC3 («генерация и загрузка корректны») — перечисляет команды
гейтов, существующие в
package.json(проверено), и «существующий unit ленивой загрузки» — по факту это browser-smokedemo/smoke_furniture_lazy_art.mjs, не unit-тест. Терминологическая неточность (см. находку Low), не блокирует проверяемость критерия.
Ни один AC не описывает поведение, зафиксированное только предположением автора: каждое числовое или структурное утверждение сверяется с реальным файлом кода или манифеста (см. таблицу выше), а не изобретается.
Находки
Low — AC3 называет browser-smoke «unit»-тестом
Файл: тело issue #640, раздел «Критерии приёмки», AC3.
Суть: «Доказательство: команды гейтов + существующий unit ленивой
загрузки» — свидетель, на который ссылается формулировка
(demo/smoke_furniture_lazy_art.mjs), является browser-smoke из
demo/smoke_*.mjs, а не test/*.test.mjs unit-тестом. Не искажает
проверяемость критерия (свидетель существует и годен), но при код-ревью
формулировка может увести к поиску несуществующего unit-теста.
Решение ревьюера: не блокирует, оставляю без правки автору — на
код-ревью проверяющий сверится с фактическим файлом, а не с текстом ТЗ;
исправление слова стоит дешевле, чем цикл ревью ради него.
Других находок нет. High- и Medium-находок в скоупе задачи — 0. Medium вне скоупа — 0, отдельный issue не заводится.
Что проверено и корректно
- Число прочих menu-иконок (32) и точный
viewBox/безопасный контракт SVG, включая цвет и толщину линии, — сверены с реальным генератором и текущим файлом, а не приняты на слово; - Соответствие группы/названий/размеров манифесту
pack.json; - Утверждение о ленивой загрузке menu-арта — прослежено по цепочке
импортов до динамического
import()вhouseplan-card.ts; - Существование golden-сцены и её охват (все категории, не одна плитка);
- Отсутствие влияния на скриншоты документации — палитра мебели не
фигурирует ни в одном сценарии
demo/docs/screenshots.mjs; - Отсутствие второго источника рисунка иконки в
src/**(единственный потребитель —decor-image-editor.tsчерезGENERATED_FURNITURE_MENU); - Существование обоих npm-скриптов (
furniture:generate,furniture:check), на которые ссылается AC3; - Полнота обязательных разделов ТЗ по §7.1 и корректность их порядка;
- Согласованность аналитического комментария (
Оценка: ...) с выбранным трекомsmall— все критерии §5 выполнены одновременно (сложность 2/10, одна поверхность, нет миграции/нового UX-контракта/ влияния на perf или touch), отказ отtrivialобоснован верно (тип — enhancement, не bug).
Чего не проверял
- Подлинность SVG-геометрии внутри приложенного
dishwasher.zip(не скачивал архив по внешней ссылке — это дело код-ревью: сверить итоговый path вsvg/menu/dishwasher.svgс содержимым архива по заявленному SHA-256, а не задача спек-ревью проверять содержимое ещё не реализованного изменения); - Юридический статус provenance (принадлежность аккаунта
nikitaevfz-commitsкомпании JustBusiness) — зафиксировано как решение владельца вне этого ревью, продуктовым вопросом не является; - Дешёвые гейты (
typecheck/test/build) — не гонялись, продуктового диффа для них нет на этапе ТЗ.
Материал раунда
- Issue: #640, заход r1.
- Тело issue (раздел
## ТЗ) прочитано целиком черезgh issue view 640 --json body. - Working tree: HEAD detached на
f234855e66ee7baba528b7c856c5ab79e9491156,git status— чисто, продуктовый код этой задачей не менялся.
Вердикт
Зелёный. ТЗ полно, каждый AC проверяем и подкреплён проверкой по реальному коду/манифесту/скриптам, продуктовых вопросов владельцу нет, единственная находка — Low (терминологическая неточность в AC3), не требует правки для перехода в «Готово к разработке».
Материал раунда
- Ветка:
issue/640-dishwasher-menu-icon, коммитf234855e66ee— ребейз его осиротит, и это нормально: ниже якоря, которые ребейз не меняет. - Дерево материала:
703233aee85cb3c3cbf101b84e288ec9dba3ce34git log --all --format='%H %T' | grep 703233aee85c - Тело issue:
1336c4649192ea657779f92aeaf1daff7c7f23c2b85316d89d401bcd9f06101f - Вердикт конвейера:
green· High 0