Skip to content

feat(devtools): секция токенов, разрешающихся в пустоту; пресет 0.14.1 - #12

Merged
efureev merged 2 commits into
mainfrom
feat/devtools-empty-tokens
Aug 28, 2026
Merged

feat(devtools): секция токенов, разрешающихся в пустоту; пресет 0.14.1#12
efureev merged 2 commits into
mainfrom
feat/devtools-empty-tokens

Conversation

@efureev

@efureev efureev commented Aug 28, 2026

Copy link
Copy Markdown
Owner

Панель — granularity-devtools 0.3.0

Новая секция на инспекторе компонента: --gr-*, который правило читает без запасного значения, а браузер отдаёт пустым. Такое объявление отбраковывается на этапе вычисления — компонент выходит без фона, без рамки, с прямыми углами, при зелёной сборке и валидном CSS.

Индекс стилей попутно собирает «класс → токены без запаса» тем же обходом, что и «классы без правил». Считаются только --gr-*: UnoCSS читает свои --un-* без запаса по всей утилитной раскладке, и на чистом стенде это три находки чужой механики.

Что компонент читает — четыре секции по владельцу

Обратная сторона секции объявленных токенов: own, from other components (с именем владельца — правка заденет и его), foundation (палитра, шкалы, тени, длительности) и unregistered (не объявлен ни одним реестром — опечатка). В строке значение и пометка has fallback.

Включения между множествами нет ни в одну сторону: объявленный токен может не потребляться, а потребляет компонент в основном чужое. Живой GrButton на стенде читает двенадцать токенов, своих из них два — и видно, откуда берётся цвет: --gr-button-primary-bg отдаёт #e546bd, потому что его запас --gr-primary перекрашен приложением.

Почему не хватило статики

Идея — из token-undefined, заведённой в granular doctor пресетом 0.14.0. Проверка слепа там, где приложения ошибаются чаще всего: themes.tokensFile заменяет tokens.css пакета, а доктор считает заданным объединение обоих файлов.

Замерено на apps/playground:

штатно с подменой tokensFile
theme-CSS 22 504 байт 15 703 байт
--gr-radius-control есть нет
doctor 17 находок 17 находок
панель 0 11

В 0.14.1 ту же дыру закрыли для themes.themeFiles, для tokensFile — нет.

Пресет 0.14.1 и гейт doctor

Новая диагностика роняла бы doctor --strict в семи пакетах. Разобрал все находки: на ядре их 33, и все до единой — токены, которые компонент выставляет себе сам инлайновым стилем (grAlertStyles.ts, grSegmentedStyles.ts, GrSwitch.vue).

Гейтом теперь служит scripts/granular-doctor.mjs: --strict минус token-undefined на токенах, объявленных tokens.json любого пакета монорепо. Токен, которого не объявляет никто, роняет гейт — это опечатка в имени. По дороге правило поймало --gr-floating-available-height, пока реестр читался только из components/*.

Проверено

  • doctor: 7 пакетов, exit 0
  • granularity: 4832 теста
  • granularity-devtools: 160 тестов (+31), линт и типы чисто
  • в браузере на стенде: пустых токенов 0 при штатном конфиге и 11 с подменой; на GrButton — 12 потребляемых, 8 строгих

fureev added 2 commits August 28, 2026 12:50
`--gr-*`, который правило компонента читает без запасного значения, а браузер
отдаёт пустым: объявление отбраковывается на этапе вычисления, и компонент
выходит без фона, без рамки, с прямыми углами — при зелёной сборке и валидном
CSS. Индекс стилей попутно собирает «класс → токены без запаса» тем же обходом,
что и «классы без правил»: `@media`/`@supports`/`@layer` внутрь, последний
`var()` цепочки запасных учитывается — пустой, он роняет объявление так же.

Считаются только `--gr-*`: UnoCSS читает свои `--un-shadow-inset`,
`--un-ring-inset`, `--un-space-y-reverse` без запаса по всей утилитной
раскладке, и на чистом стенде это три находки чужой внутренней механики.

Идея — из `token-undefined`, заведённой в `granular doctor` пресетом 0.14.0.
Статическая проверка слепа там, где приложения ошибаются чаще всего:
`themes.tokensFile` заменяет `tokens.css` пакета, а доктор считает заданным
объединение обоих файлов. Замерено на `apps/playground`: с подменой файла
theme-CSS падает с 22 504 до 15 703 байт и теряет `--gr-radius-control`,
доктор отчитывается теми же 17 находками, панель называет 11 пустых токенов
типографики и анимации. В 0.14.1 ту же дыру закрыли для `themes.themeFiles`,
для `tokensFile` — нет.

Пресет поднят до 0.14.1. Его новая диагностика роняла бы `doctor --strict` в
семи пакетах: на ядре 33 находки, и все до единой — токены, которые компонент
выставляет себе сам инлайновым стилем. Гейтом теперь служит
`scripts/granular-doctor.mjs`: `--strict` минус `token-undefined` на токенах,
объявленных `tokens.json` любого пакета монорепо. Токен, которого не объявляет
никто, роняет гейт — это опечатка в имени.
Обратная сторона секции объявленных токенов: что компонент потребляет на самом
деле — четырьмя группами по владельцу. `own` — объявлено им самим; `from other
components` — с именем владельца, чтобы было видно, кого заденет правка;
`foundation` — палитра, шкалы, тени, длительности; `unregistered` — не объявлен
ни одним реестром, почти всегда опечатка. В строке фактическое значение и
пометка `has fallback`.

Включения между двумя множествами нет ни в одну сторону: объявленный токен
может не потребляться, а потребляет компонент в основном чужое. Живой
`GrButton` на стенде читает двенадцать токенов, своих из них два. Отсюда виден
и путь значения: `--gr-button-primary-bg` отдаёт `#e546bd`, потому что его
запас — `--gr-primary`, перекрашенный приложением.

Индекс стилей теперь пишет потребление и с запасом тоже, помечая токен строгим,
если хоть одно чтение идёт без запаса. Секция пустых токенов отбирает по этому
флагу: чтение с запасом при пустом токене рисует запасным значением и находкой
быть не может.
@efureev
efureev merged commit 37e9396 into main Aug 28, 2026
45 checks passed
@efureev
efureev deleted the feat/devtools-empty-tokens branch August 28, 2026 10:09
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant