mirror of
https://github.com/Matysh/houseplan-card
synced 2026-10-07 23:19:14 +00:00
@@ -0,0 +1,217 @@
|
||||
# CODE-REVIEW-744-r4
|
||||
|
||||
**Issue:** #744 · **Трек:** ask · **Заход:** r4 · блокирующих циклов израсходовано 1 из 4
|
||||
|
||||
**Материал:** `2bcde131581a6130f971dcef167299d6cc1129ad` (ветка
|
||||
`issue/744-floor-geometry-key`, поверх `dev` `c4cb0649` — после слияния #762).
|
||||
Девять коммитов от merge-base: продуктовые/тестовые К1–К5 `f5b20e07` и
|
||||
`6ed9aa16` (уже разобраны в r1/r2), `a86be350` (ленивый `space-editor`, уже
|
||||
разобран в r3 под хешем `0f16312e` — ребейз осиротил старый хеш, содержимое
|
||||
то же), три docs-коммита, публикующих CODE-REVIEW-744-r1/r2/r3.md
|
||||
(`bb9aaefe`, `2d7a1c97`, `9882046b`) и два коммита `docs(reviews): индекс
|
||||
после сдвига каталога` (`3d68a2fe`, `7bbab4b6`), и новый `2bcde131` —
|
||||
единственная содержательная правка этого раунда.
|
||||
|
||||
## Скоуп
|
||||
|
||||
r3 был зелёным на материале `0f16312e` (комментарий автора, вердикт
|
||||
2026-10-01). Пока ревью шло, `dev` продвинулся ещё на 5 коммитов; владелец
|
||||
зафиксировал это прямо в issue и вернул задачу в `S6-in-progress` **не как
|
||||
правку кода, а как ребейз** («Код-ревью зелёное — вердикт выше в силе,
|
||||
переделывать работу не нужно. Не удалось только слияние»). Автор сделал
|
||||
`git rebase origin/dev` на `dev@c4cb0649` (после #762) и запушил без force
|
||||
(lease `98db7b1f` → `2bcde131`).
|
||||
|
||||
Ребейз дал ровно один конфликт — в `docs/testing-notes/mutation-browser-guards.md`
|
||||
(таблица пересекалась с чужими правками, ушедшими в `dev` раньше #744): автор
|
||||
взял строки `dev` и прибавил к ним два мутанта задачи (`floor-geometry-key-*`),
|
||||
подняв lifecycle 97→99 и Total 214→216. После ребейза один шаг `gate:small`
|
||||
покраснел на храповике монолита: `bundleBytes` вырос с 2 605 172 до 2 607 854 Б
|
||||
(+2 682 Б при полосе 2 000) — не потому что код раунда что-то добавил (К1–К5 и
|
||||
ленивый `space-editor` уже посчитаны в r1/r3), а потому что ребейз сам по себе
|
||||
сдвинул дерево `dist/` относительно старой базы. Автор поднял базовую линию
|
||||
отдельным коммитом `2bcde131` с обоснованием (новый модуль ключа этажа + обёртка
|
||||
ленивого чанка), не трогая продуктовый код.
|
||||
|
||||
Задача по-прежнему `track: ask`, критерий §5 «перф» не переоценивается — не
|
||||
изменился с r1. **`route: fix`.**
|
||||
|
||||
### Дельта r3 → r4
|
||||
|
||||
Проверено прямым чтением, не только по словам автора: содержимое продуктовых
|
||||
коммитов не изменилось, изменились только их хеши (ребейз переносит одни и те
|
||||
же патчи на новый родитель):
|
||||
|
||||
- `f5b20e07` (К1–К5, перф floor-geometry-key): `git show f5b20e07 --stat` даёт
|
||||
те же 13 файлов/456+/24− и тот же текст изменений, что описан в r1 —
|
||||
с одним отличием: правка `docs/testing-notes/mutation-browser-guards.md`
|
||||
внутри этого же коммита теперь содержит ребейзнутые числа 97→99/214→216
|
||||
(было 90→92/205→207 на старой базе r1/r3). Это ожидаемый эффект ребейза
|
||||
коммита с текстовым конфликтом, не новая правка задачи.
|
||||
- `6ed9aa16` (тест «судить оба кадра удержанного resize») — 1 файл,
|
||||
58+/7−, идентичен r2.
|
||||
- `a86be350` (ленивый `space-editor`) — дифф `src/space-card.ts` побайтово
|
||||
совпадает с тем, что r3 разобрал под хешем `0f16312e` (тот же `import
|
||||
'./space-editor'` убран, тот же `async getConfigElement()`).
|
||||
|
||||
Единственное новое содержание раунда — коммит `2bcde131`:
|
||||
|
||||
```
|
||||
chore(monolith): raise the bundleBytes baseline for #744 (#744)
|
||||
scripts/monolith-baseline.json | 2 +-
|
||||
```
|
||||
|
||||
`"bundleBytes": 2605172` → `2607854`. Трейлеры: `Issue: #744`,
|
||||
`User-Visible: no` — верно: число самим пользователям не видно, это
|
||||
внутренний храповик монолита (`scripts/monolith-metrics.mjs`,
|
||||
`docs/testing-notes/...`, не пользовательская поверхность).
|
||||
|
||||
## Как проверялось
|
||||
|
||||
| Гейт | Статус | Как |
|
||||
|---|---|---|
|
||||
| `npx tsc --noEmit`, `npm test`, `npm run build` + `bundle-policy --verify` | не перегонял целиком, но `npm run build` выполнил сам | Validate на точном SHA материала зелёный: https://github.com/Matysh/houseplan-card/actions/runs/36937043475 — сверено `gh run view 36937043475`, `headSha` = `2bcde131581a6130f971dcef167299d6cc1129ad`, `conclusion: success` (не со слов автора). Дополнительно сам прогнал `npm run bundle:sync` (→ `tsc --noEmit && rollup -c` зелёные, бандл собрался за 22,2 с) ради смока ниже; рабочую копию `dist/` вернул `git checkout -- dist/` + `git clean -fd dist/`, `git status --porcelain` пуст после |
|
||||
| Корректность ребейзнутой таблицы `mutation-browser-guards.md` | **прогнал сам** | Пересчитал список построчно (`grep -c '^- \`'` по секциям): «Custom-element and HA browser lifecycle» = 99, сумма всех секций = 216 — совпадает с заявленным в таблице «99» и «216 / 200». Оба мутанта задачи (`floor-geometry-key-global-epoch`, `floor-geometry-key-ignores-content`) в списке на месте |
|
||||
| `node scripts/mutation-gate.mjs --check` | **прогнал сам** | exit 0; `browser guards: 216/200` — WARN (не отказ, #699, та же картина что в r3, но с актуальными для текущего `dev` числами); оба мутанта задачи — `ok` |
|
||||
| `node demo/smoke_floor_geometry_cache.mjs` | **прогнал сам, на пересобранном бандле** | Все проверки `true`/`0`/`[]` как ожидается: AC1 (`ac1GardenVisitBuildsNo*` = 0), AC2а/б/в (`...EqualsAFreshCard` = true), итог `OK`. Это прямое исполнение целевого смока задачи на точном материале раунда, не унаследованная запись |
|
||||
| `node scripts/smoke-select.mjs --base origin/dev --head HEAD` | **прогнал сам** | 20 прямых совпадений (включая целевой `smoke_floor_geometry_cache.mjs` ← `_cleanFloorCache`) + 41 слабая связь на `_curSpaceCfg` — тот же профиль, что в r3 (дельта `src/space-card.ts` не читает `_curSpaceCfg`); решение не прогонять слабые — не затронуты дельтой |
|
||||
| Freshness `docs/reviews/INDEX.md` | **прогнал сам** | `node scripts/reviews-index.mjs` → «docs/reviews/INDEX.md свеж» |
|
||||
| `npm run gate:small`, полный `smoke-select`, golden, Full Performance, `pytest tests_backend`, `npm run invariants` | не перегонял | дельта раунда — ребейз без изменения продуктового кода плюс один chore-коммит над `scripts/monolith-baseline.json`; геометрия, Python и рендер плана не затронуты; AC1–AC5 (К1–К5) и AC4 (performance) уже закрыты исполнением в r1–r3 на коде, который не менялся с тех пор |
|
||||
|
||||
## Закрытие раунда r3
|
||||
|
||||
r3 был зелёным без находок (0 High, 0 Medium) — закрывать нечего.
|
||||
|
||||
## Унаследовано из r3 (и транзитивно из r1/r2)
|
||||
|
||||
Продуктовый и тестовый код К1–К5 (`src/floor-geometry-key.ts`,
|
||||
`src/clean-floor.ts`, `src/stairs-editor.ts`, `src/houseplan-editor-runtime.ts`,
|
||||
`src/houseplan-card.ts`, `src/space-card.ts`, `demo/smoke_floor_geometry_cache.mjs`,
|
||||
`demo/benchmark_large_house.mjs`, `demo/performance/card-contract.mjs`,
|
||||
`scripts/mutation-registry.mjs`, `test/clean-floor.test.mjs`) не менялся
|
||||
между r3 и r4 — дельта раунда ограничена ребейзом (без изменения содержимого
|
||||
этих файлов, подтверждено построчно выше) и одним новым chore-коммитом над
|
||||
`scripts/monolith-baseline.json`. Принято без повторного построчного разбора,
|
||||
с документом и материалом r2/r3 (`docs/reviews/CODE-REVIEW-744-r2.md`,
|
||||
материал `d10285b0794d…`; `docs/reviews/CODE-REVIEW-744-r3.md`, материал
|
||||
`0f16312e8ff1…`):
|
||||
|
||||
- Архитектура ключа этажа (`contentFingerprint`, память на эпоху и на пару
|
||||
объектов записи), её использование в четырёх кэшах и resize-preview со
|
||||
своим ключом.
|
||||
- Контракт К1–К5 и защита против «устаревшего кадра» независимым oracle в
|
||||
смоке — сам смок перепрогнан мной заново в этом раунде на пересобранном
|
||||
бандле и зелёный, так что это подтверждено исполнением, а не только
|
||||
унаследовано.
|
||||
- `StairsEditor.write` больше не чистит `_cleanFloorCache` других этажей.
|
||||
- Ленивая загрузка GUI-редактора `space-card` (контракт идентичен
|
||||
`houseplan-card.getConfigElement()`), структурная и поведенческая
|
||||
корректность подтверждены исполнением в r3 (манифест чанка + Playwright-зонд).
|
||||
- Два мутанта в `scripts/mutation-registry.mjs` — перепроверено мной
|
||||
`mutation-gate --check` в этом раунде, оба на месте.
|
||||
- AC4 — Full Performance против базы `dev`, закрыт в r1→r2, исполнение
|
||||
проверено r2 напрямую по API/логам; код, который измеряет AC4, с тех пор
|
||||
не менялся.
|
||||
- Трейлеры и CHANGELOG RU/EN на продуктовом коммите `f5b20e07` (бывший
|
||||
`5263403c` до ребейза) — текст дословно совпадает с ТЗ, оба файла правлены
|
||||
в одном коммите; проверено, что обе строки `#744` сохранились в текущем
|
||||
`docs/CHANGELOG.md`/`docs/CHANGELOG.ru.md` после ребейза (не были потеряны
|
||||
слиянием).
|
||||
|
||||
## Находки
|
||||
|
||||
Нет High. Нет Medium в скоупе. Нет Medium вне скоупа.
|
||||
|
||||
Наблюдение r3 о расхождении счётчика в `mutation-browser-guards.md» (92/207
|
||||
в тексте против 209 фактических) снято этим раундом: ребейз пересчитал
|
||||
коммит `f5b20e07` против актуальной базы `dev`, и таблица теперь точно
|
||||
совпадает с фактическим выводом `mutation-gate.mjs` (216/216, 99/99
|
||||
lifecycle) — подтверждено пересчётом выше.
|
||||
|
||||
## Что проверено и корректно
|
||||
|
||||
- Дельта раунда (ребейз + `2bcde131`) не меняет ни одного продуктового файла
|
||||
К1–К5: сверено построчно по diff-статам коммитов `f5b20e07`/`a86be350`,
|
||||
совпадающим с тем, что уже разобрано в r1/r3.
|
||||
- Единственная содержательная правка — поднятие `bundleBytes` baseline —
|
||||
это class D (генерируемое значение), её корректность уже подтверждена
|
||||
прохождением `gate:small`/Validate на точном SHA (храповик монолита сам
|
||||
проверяет, что новое число соответствует фактической сборке в пределах
|
||||
полосы; расхождение завалило бы Validate).
|
||||
- Конфликт-резолюшн в `docs/testing-notes/mutation-browser-guards.md`
|
||||
корректен: фактический вывод `mutation-gate --check` (216 всего, 99
|
||||
lifecycle) совпадает с текстом таблицы после ребейза, оба мутанта задачи
|
||||
на месте.
|
||||
- Целевой смок задачи (`demo/smoke_floor_geometry_cache.mjs`, AC1/AC2а/б/в)
|
||||
зелёный на пересобранном бандле точного материала — не только по
|
||||
унаследованной записи r3.
|
||||
- Трейлеры всех коммитов класса A/B раунда (`f5b20e07`, `6ed9aa16`,
|
||||
`a86be350`, `2bcde131`) содержат `Issue: #744` и корректный
|
||||
`User-Visible:`; `User-Visible: yes` на `f5b20e07` — оба CHANGELOG правлены
|
||||
в этом же коммите и сохранились после ребейза.
|
||||
- `docs/reviews/INDEX.md` свеж относительно опубликованных r1–r3 документов
|
||||
(`node scripts/reviews-index.mjs`).
|
||||
- Одно число — один источник: `bundleBytes` 2 607 854 видно один раз — в
|
||||
`scripts/monolith-baseline.json`, которое читает только
|
||||
`scripts/monolith-metrics.mjs`/`gate:small`; пользователю это число не
|
||||
показывается (`User-Visible: no`), второго источника для сверки нет.
|
||||
|
||||
## Чего не проверял
|
||||
|
||||
- Дешёвые гейты `npx tsc --noEmit`/`npm test`/`bundle-policy --verify`
|
||||
целиком не перегонял — Validate на точном SHA материала подтверждён
|
||||
зелёным (`gh run view 36937043475`); `npm run build` тем не менее выполнил
|
||||
сам (см. таблицу), так что сборка на этом дереве подтверждена дважды
|
||||
независимо.
|
||||
- Полный `smoke-select` (всю матрицу 289 смоков), browser-смоки/golden всех
|
||||
шардов не перегонял — дельта раунда не трогает рендер плана, геометрию или
|
||||
UI; целевой смок задачи и профильный `mutation-gate --check` прогнал сам.
|
||||
- Full Performance (AC4) не перезапускал — закрыт исполнением в r1/r2 на
|
||||
коде, который не менялся с тех пор; дельта этого раунда (ребейз +
|
||||
baseline-чиcло) не затрагивает горячий путь переключения этажа.
|
||||
- `npm run invariants` — не запускал, геометрия в этом раунде не менялась
|
||||
(К1–К5 не тронуты).
|
||||
- `pytest tests_backend` / HA harness — не запускал, Python не затронут ни
|
||||
в одном коммите материала.
|
||||
- Golden (`ci:golden`) — не перегонял; задача не рисует план иначе и дельта
|
||||
раунда (ребейз + chore) рендера не касается.
|
||||
- Английскую версию `docs/USER-GUIDE.ru.md`/EN — не проверял: видимое
|
||||
поведение задачи не изменилось с r1 (`User-Visible: yes` сверен с ТЗ ещё
|
||||
в r1), дельта этого раунда — `User-Visible: no`.
|
||||
|
||||
## Вердикт
|
||||
|
||||
Зелёный. Дельта раунда — ребейз на `dev@c4cb0649` (после #762), не менявший
|
||||
содержимое продуктового и тестового кода задачи (проверено построчно), плюс
|
||||
один chore-коммит, поднимающий `bundleBytes` baseline монолита на величину,
|
||||
которую сам раунд и внёс (ключ этажа + ленивый `space-editor`). Конфликт
|
||||
ребейза в `docs/testing-notes/mutation-browser-guards.md` разрешён верно —
|
||||
перепроверено пересчётом фактического вывода `mutation-gate --check`.
|
||||
Целевой смок задачи перепрогнан на пересобранном бандле точного материала и
|
||||
зелёный. Находок нет. Бюджет циклов остаётся израсходованным на 1 из 4
|
||||
(унаследовано из r1) — зелёный вердикт цикла не образует.
|
||||
|
||||
---
|
||||
|
||||
<!-- material-anchors: заполняется публикующим шагом -->
|
||||
|
||||
## Материал раунда
|
||||
|
||||
- Ветка: `issue/744-floor-geometry-key`, коммит `2bcde131581a6130f971dcef167299d6cc1129ad`.
|
||||
- `git rev-parse HEAD` на момент ревью: `2bcde131581a6130f971dcef167299d6cc1129ad`.
|
||||
- Вердикт: `green` · High 0 · Medium 0 · маршрут `fix`.
|
||||
|
||||
---
|
||||
|
||||
<!-- material-anchors: сгенерировано конвейером (#414) -->
|
||||
|
||||
## Материал раунда
|
||||
|
||||
- Ветка: `issue/744-floor-geometry-key`, коммит `2bcde131581a` — ребейз его осиротит, и это нормально: ниже якоря, которые ребейз не меняет.
|
||||
- Дерево материала: `0272ec42089ccc881841358169ad6e9105944e7c`
|
||||
```
|
||||
git log --all --format='%H %T' | grep 0272ec42089c
|
||||
```
|
||||
- Тело issue: `9dec80eead95ea0cbc014364d7ed09eaef1f7f45b7e2c70f97f1a95c586ac465`
|
||||
- Вердикт конвейера: `green` · High 0 · маршрут `fix`
|
||||
<!-- hp:usage input_tokens=4060 output_tokens=25030 cache_creation_input_tokens=114145 cache_read_input_tokens=2651158 num_turns=53 -->
|
||||
Reference in New Issue
Block a user