- отношение победы было нетранзитивным: полнота (частичный порядок) плюс тай-брейк (тотальный) в попарной свёртке давали цикл, из-за которого одна и та же доставка меняла содержимое объекта при каждой пересборке - надмножество побеждает только при совпадении значений общих содержательных ключей: иначе точка без единого измерения вытесняла измерение - Less стал тотальным, isEmpty не материализует значение, имя метрики в координате столкновения обрезается, отпечаток витрины включает units и sealed - на живом архиве строгий no-op: 1737 объектов, содержимое совпало побайтово
4.6 KiB
4.6 KiB
Why
Полнота точки при разрешении столкновения считается числом ключей с
непустым значением. Число сравнимо всегда, а сравнивать надо содержание: точка
с пятью полями, где значения 0, {} и [], выигрывает у настоящего
измерения с двумя полями и стирает его безвозвратно.
точка {"qty":0,"a":0,"b":0,"c":{},"d":[]} полнота 5 ← выигрывает сегодня
точка {"date":"…","qty":123.4} полнота 2 ← стирается
Замер по всем 99 доставкам (docs/local-research.md, находка 49) даёт основание для правильной формы правила: настоящих столкновений 2 897 из 444 256 координат (0.65%), из них наборы полей сравнимы в 981 случае, равны в 1 916 и несравнимы ни разу. То есть правило сводится к «побеждает надмножество», а самая дорогая часть — объединение полей из двух точек — на живом потоке не нужна вовсе.
What Changes
- Полнота точки перестаёт быть числом и становится множеством ключей с непустым значением. Побеждает строгое надмножество; равные множества уходят на прежний тай-брейк.
- Пустым значением считается не только
nullи"", но и0,{},[]: поле, не несущее содержания, не делает точку полнее отсутствующего поля. Это и есть та часть, из-за которой сегодняшний счётчик даёт неверный исход на приведённой выше паре.falseпустотой НЕ считается — для булева поля это одно из двух значений, а не отсутствие сведений. - Надмножество побеждает только при совпадении значений общих содержательных ключей: иначе точка без единого измерения вытесняла бы измерение.
- Несравнимые множества (ни одно не является надмножеством другого) не
объединяются, а считаются: счётчик в итоге слияния плюс
WARNс координатами объекта (метрика, слой, час), без значений. Победителя в этом случае выбирает тот же тай-брейк, что и при равной полноте. - Не меняется тай-брейк при равной полноте: он зависит от рода метрики,
а род измеряется сверкой слоёв (задача
rod-agregacii-i-katalog). Выбирать его сейчас — угадывать то, что скоро станет известно точно.
Capabilities
New Capabilities
Нет.
Modified Capabilities
storage: требование «Разрешение столкновений по полноте» переформулируется с числа значащих полей на множество ключей с непустым значением; добавляется наблюдаемость несравнимых множеств.
Impact
internal/canon—Completeness(число) заменяется сравнением множеств ключей; расширяется понятие пустого значения.internal/store/bucket.go—resolveиMergeStats(новый счётчик и координаты несравнимых случаев).internal/fold— новая ветвьWARNв единственном логирующем чекпоинте.openspec/specs/storage/spec.md— дельта-спека.- Витрина не мигрирует: правило меняет исход только там, где сегодня он
неверен. Проверяется прогоном
task verify:archiveна живом архиве — состояние обязано совпасть с прежним.