specs: define shared design system correction

This commit is contained in:
2026-09-08 07:09:08 +03:00
parent 0e4c491765
commit 61782885b5
6 changed files with 270 additions and 0 deletions
@@ -0,0 +1,2 @@
schema: wealth-ledger-sdd
created: 2026-09-08
@@ -0,0 +1,127 @@
## Context
Baseline: app/theme задаёт blue 0–9, primaryColor blue, defaultRadius md и
системный sans-serif; прочие шкалы разрешаются Mantine 9.5.1. App/styles задаёт
фон gray.2 и текст dark.7. StateView и LoadingSkeleton уже используются в shared/ui.
Каталог содержит 6 групп / 21 историю; preview импортирует тему из app.
Локальные card gradients, размеры, shadows и бизнес-цвета остаются у владельцев.
## Goals / Non-Goals
**Goals:** shared-владение темы и базовых стилей, явные шкалы и семантические
роли без копий значений, полезный общий набор и два блока Storybook.
**Non-Goals:** редизайн приложения, перенос всех CSS literals в tokens,
новые зависимости, смена Mantine, перенос AppShell/навигации, бизнес-реализаций
или auth в дизайн-систему, продуктовый пилот и правка исторических artifacts.
## Decisions
- `shared/theme` — FSD segment с public API `index.ts`: тема Mantine,
CSSVariablesResolver и семантические color roles. Базовые CSS импортируются
public entrypoint темы. App владеет MantineProvider; preview подключает свой
изолированный MantineProvider с тем же public API. Дублирующий app/theme удаляется.
- Blue palette и font family сохраняют исходные bytes. Шкалы spacing, radius,
fontSizes, lineHeights, headings, shadows, breakpoints и mono font явно
принимаются из DEFAULT_THEME, без повторения числовых значений. Primary shade
и focus behavior также сохраняют defaults. Это используемый Mantine contract,
а не отдельный token engine.
- Семантические CSS aliases `--wl-color-*` ссылаются на Mantine CSS variables:
canvas gray.2, surface white (body светлой схемы), subtle gray.0, text dark.7, muted gray.6 (dimmed),
border gray.3, primary filled, info blue.6, positive green.6, negative red.6,
warning yellow.6. Цвет не заменяет текстовый статус; warning не предназначен
для мелкого текста на белом. Глобальный фон/текст используют соответствующие
aliases; локальные роли можно принимать постепенно без массовой миграции.
- Общий набор — существующие StateView (empty/error, optional action) и
LoadingSkeleton (busy/status wrapper с caller-owned decorative shapes).
Они уже решают реальные задачи, не требуют новых wrappers. AppShell содержит
маршруты и не входит в заявленный общий каталог. Mantine Button показывается
напрямую в принятых конфигурациях primary/default/subtle/loading/disabled;
никаких WLButton и изменения глобальных defaults ради витрины.
- CSF stories остаются colocated. StateView и новые foundations/loading/buttons
относятся к Design System; пять существующих бизнес-групп — Product.
Theme foundations читают effective theme через useMantineTheme, labels роли
ссылаются на тот же alias map; значения не копируются в stories.
## UI/UX Applicability and Package
**Applicability and scope:** new/changed для каталога; приложение сохраняет
существующий UI, новый макет приложения не нужен.
**Package revision:** 1; пакет полностью inline Markdown, exports не нужны.
**Screens, states and interactions:**
| Блок / экран | Содержание и поведение |
| --- | --- |
| Design System / Foundations / Colors | Подписанные роли, образец цвета, фактическое значение; blue 0–9 и используемые neutral/status palettes. Цвет всегда сопровождается текстом. |
| Design System / Foundations / Typography | Семейства sans/mono, heading и body шкалы с размерами, весом, line-height и примерами. |
| Design System / Foundations / Layout | Spacing, radius, shadows, breakpoints из effective theme, default radius и правила применения. |
| Design System / Components / StateView | Сохраняются все 4 истории: empty/error с действием и без, error role alert, keyboard button и локальный callback. |
| Design System / Components / LoadingSkeleton | Нейтральные structural shapes; status/busy label, no focusable shapes. Форма страницы остаётся у page. |
| Design System / Components / Button | Реальный Mantine Button; primary/default/subtle, loading/disabled, доступное имя, keyboard focus и наблюдаемый local action. |
| Product | Все 17 исходных бизнес-историй: список счетов, позиции, события, обновление сохранённых сумм и loading страницы. Синтетические fixtures, локальные Actions и MemoryRouter, без API/auth runtime. |
Docs каждой группы задаёт назначение, правила применения и границы. Manager
явно сортирует Design System перед Product. Controls меняют поддерживаемые args,
reset/remount сохраняют штатную семантику Storybook.
**Responsive behavior:** foundations используют переносящиеся grids/stack,
длинные значения и labels не расширяют viewport 375px. Button variants переносятся;
StateView сохраняет доступную кнопку. Product сохраняет существующее responsive
поведение; проверяется узкий и desktop iframe, без нового breakpoint contract.
**Reused source and differences:** исходные реализации текущей baseline,
без ссылки на изменяемую витрину как authority и без reuse исторического пакета.
## Delivery Map
| Area | Status | Architectural outcome or N/A reason |
| --- | --- | --- |
| frontend | affected | Shared theme и базовые styles, общий набор, два блока каталога |
| backend | N/A | API, auth и хранение данных не меняются |
| specs | affected | Новый corrective contract и evidence в canonical store |
| docs | affected | As-built foundation ownership, coverage и использование каталога |
### Contract Gate Decision
| Gate | Status | Reason |
| --- | --- | --- |
| runtime-openapi | N/A | Ни одна сторона API contract не меняется |
## Solution Assessment
Mantine 9.5.1 уже предоставляет зрелые тему, типы, CSS variables, scales,
компоненты и focus/loading/disabled semantics. Его native theme сохраняет
совместимость и не увеличивает operating cost. Storybook 10.6.0 уже установлен,
CSF/autodocs достаточно для двух блоков. Отдельный token framework либо новая
UI-библиотека дублировали бы ownership, увеличили зависимости и стоимость
миграции без нужного поведения. Выбран текущий stack; custom code ограничен
семантическим map и демонстрацией effective scales, без runtime интеграций.
## Risks / Trade-offs
- DEFAULT_THEME — источник встроенных шкал: обновление Mantine требует проверки
foundations и приложения, а не скрытого сохранения старой копии defaults.
- Перенос CSS может повлиять на cascade; сохраняются content/order и сравниваются
computed styles и снимки до/после. Не заявляется exhaustiveness визуальной проверки.
- Новые story IDs меняют прямые ссылки; документация использует новые пути.
- Изоляция подтверждается существующим transitive runtime graph guard;
browser проверяет доступность и взаимодействия, не API recovery.
## Migration Plan
Зафиксировать baseline, перенести ownership темы и styles, подключить оба
provider, оформить общий набор и foundations, классифицировать Product,
обновить документацию. После проверок — независимый read-only review и canonical
completion mechanics только при актуальном PASS. Исторические archives и чужие
changes/state исключены из записи. Прямое разрешение владельца в запросе
заменяет промежуточные session/approval stops для этого bounded corrective scope;
независимость review сохраняется.
### Rollback Contract
| Field | Decision |
| --- | --- |
| Status | N/A |
| Reason | Обратимый перенос frontend-владения и каталог, без данных, auth или public API изменений; возврат delivery diff восстанавливает исходную структуру |
@@ -0,0 +1,38 @@
## Why
Поставленный каталог реальных компонентов не даёт явно оформленного общего
визуального фундамента и не разделяет общие решения и продуктовые композиции.
Это corrective change поверх текущей baseline после integrate-ui-ux-design-workflow;
исторические artifacts и evidence двух архивированных changes остаются неизменными.
## What Changes
- Единая визуальная основа с определёнными шкалами и семантическими ролями,
общая для приложения и каталога, с сохранением текущего вида и поведения.
- Минимальный полезный набор используемых общих компонентов без бизнес-знаний.
- Два содержательных блока Design System и Product: foundations, общие
компоненты, реальные продуктовые композиции, состояния и правила применения.
- Проверяемые границы покрытия, изоляции и as-built описание результата.
Non-goals: массовый редизайн, замена всех локальных значений, полный каталог
библиотеки или приложения, новый продуктовый пилот, изменение backend/API,
переписывание архивов и чужого state. По прямому разрешению владельца planning
и implementation выполняются в одном контексте без sdd-session/session records.
## Capabilities
### New Capabilities
- `frontend-design-system`: `specs/frontend-design-system/spec.md` — общий
визуальный фундамент и независимые от домена общие компоненты.
### Modified Capabilities
- `frontend-ui-catalog`: `specs/frontend-ui-catalog/spec.md` — обязательные
содержательные блоки Design System и Product и критерии готовности.
## Impact
Frontend и участники разработки получают переиспользуемую визуальную основу
и каталог с явными границами. Specs фиксирует corrective contract; docs —
фактически поставленный результат. Backend и данные пользователей не затронуты.
@@ -0,0 +1,55 @@
## Purpose
Определяет единый визуальный фундамент WealthLedger и переиспользуемые общие
компоненты, чтобы приложение и каталог сохраняли согласованное представление.
## ADDED Requirements
### Requirement: Приложение и каталог используют единый визуальный фундамент
Приложение и каталог SHALL использовать один источник темы и токенов: цвета
с семантическими ролями, типографику, интервалы, радиусы, тени и применимые
адаптивные параметры. Общий фундамент MUST быть независим от бизнес-сущностей
и уровня приложения; подключение провайдеров принадлежит приложению и runtime
каталога. Параллельные копии значений MUST NOT создаваться там, где существующий
механизм темы уже владеет шкалой. Выделение фундамента MUST сохранять текущий
внешний вид, светлую схему и поведение приложения без массовой замены локальных
значений оформления.
#### Scenario: Компонент отображается в приложении и каталоге
- **WHEN** один компонент с одинаковыми props отображается в обоих runtime
- **THEN** он получает одинаковые тему, токены и общие визуальные правила
#### Scenario: Участник выбирает токен
- **WHEN** участник изучает фундамент дизайн-системы
- **THEN** доступны используемые шкалы, их значения, семантические роли и правила
применения без необходимости обращаться к данным приложения
#### Scenario: Владение темой перенесено
- **WHEN** приложение использует выделенный общий фундамент
- **THEN** исходные эффективные значения и внешний вид остаются прежними,
включая встроенные шкалы, глобальные стили и локальное оформление
### Requirement: Общие компоненты независимы от предметной области
Дизайн-система SHALL предоставлять минимальный набор реально используемых
общих компонентов с описанием назначения, вариантов, состояний и доступности.
Они MUST NOT знать о счетах, позициях, API или authentication. Существующие
компоненты SHALL переиспользоваться, если удовлетворяют этой границе; новые
обёртки MUST NOT вводиться только ради имени или покрытия каждого примитива.
Принятые конфигурации библиотечных компонентов MAY демонстрироваться напрямую.
#### Scenario: Требуется общее состояние интерфейса
- **WHEN** разработчик выбирает общее empty/error или loading представление
- **THEN** он получает используемый приложением компонент с доступной семантикой,
необязательными действиями там, где они применимы, без бизнес-зависимостей
#### Scenario: Композиция имеет бизнес-смысл
- **WHEN** композиция представляет счёт, позицию или продуктовый запросный экран
- **THEN** она остаётся у продуктового владельца и не становится общей только
ради классификации каталога
@@ -0,0 +1,31 @@
## ADDED Requirements
### Requirement: Каталог разделяет Design System и Product
Каталог SHALL иметь два явно различимых содержательных блока: Design System
и Product. Design System SHALL показывать foundations из действующей общей темы,
семантические роли, используемые шкалы и общие компоненты, их варианты, состояния,
доступность и правила применения. Product SHALL содержать реальные бизнес-компоненты
и композиции приложения с полезными существующими историями, классифицированными
по ответственности без перемещения бизнес-реализаций в общий слой. Оба блока
MUST сохранять общую тему и изоляцию от application API, auth и данных пользователя.
#### Scenario: Участник открывает Design System
- **WHEN** выбран блок Design System
- **THEN** доступны наглядные foundations с актуальными значениями токенов,
общие empty/error и loading компоненты, а также принятые конфигурации примитивов
с правилами использования и применимыми интерактивными состояниями
#### Scenario: Участник открывает Product
- **WHEN** выбран блок Product
- **THEN** доступны существующие примеры списка счетов, карточек позиций, событий,
обновления сохранённых сумм и skeleton страницы с их вариантами и ограничениями
#### Scenario: Оценивается готовность каталога
- **WHEN** каталог представлен как поставленный результат
- **THEN** существуют общий фундамент и оба содержательных блока, проверены
отображение и применимые взаимодействия, явно описаны границы покрытия;
сборка и наличие stories сами по себе не доказывают полноту или продуктовый пилот
@@ -0,0 +1,17 @@
## 1. Общий фундамент и каталог
- [x] 1.1 [frontend] Перенести тему и базовые styles в shared/theme, явно определить шкалы и семантические роли через native Mantine, подключить оба provider к public API.
- **Covers:** `frontend-design-system` — `Приложение и каталог используют единый визуальный фундамент`
- **Verification:** Сравнить effective theme, computed styles и browser снимки до/после; проверить public imports и отсутствие дублирующих values.
- [x] 1.2 [frontend] Оформить используемые StateView и LoadingSkeleton в Design System, foundations и принятые конфигурации Button; классифицировать все существующие бизнес-истории как Product.
- **Covers:** `frontend-design-system` — `Общие компоненты независимы от предметной области`; `frontend-ui-catalog` — `Каталог разделяет Design System и Product`
- **Verification:** npm run verify после npm ci под .nvmrc; browser обеих групп, foundations, empty/error/loading/disabled, keyboard/local callbacks, 375px и desktop; deps и deps:storybook.
## 2. Спецификации и as-built
- [x] 2.1 [specs] Согласованно оформить corrective Proposal, Delta Specs, Design revision 1 и Tasks в wealth-ledger-specs без session records и изменения архивов.
- **Covers:** `frontend-design-system` — `Приложение и каталог используют единый визуальный фундамент`; `frontend-design-system` — `Общие компоненты независимы от предметной области`; `frontend-ui-catalog` — `Каталог разделяет Design System и Product`
- **Verification:** openspec schema validate wealth-ledger-sdd --verbose; openspec validate complete-shared-design-system --type change --strict --store wealth-ledger-specs; openspec validate --specs --strict --store wealth-ledger-specs; semantic review относительно текущей baseline.
- [x] 2.2 [docs] Обновить as-built описание общего фундамента, FSD ownership, обоих блоков, coverage и ограничений без заявления о пройденном продуктовом пилоте.
- **Covers:** `frontend-design-system` — `Приложение и каталог используют единый визуальный фундамент`; `frontend-design-system` — `Общие компоненты независимы от предметной области`; `frontend-ui-catalog` — `Каталог разделяет Design System и Product`
- **Verification:** npm ci и npm run verify под docs .nvmrc; scoped local link review, соответствие путей и состава фактическому каталогу.