Commit Graph

372 Commits

Author SHA1 Message Date
Александр Зимин 5365170de2 Merge branch 'fix/topbar-restore-search-single-x' into 'main'
fix(ui): restore TopBar search + notifications bell + theme to sidebar

See merge request 2-6/2-6-4/terravault/ordinis!91
2026-05-11 19:09:15 +00:00
Zimin A.N. 7f3241686c fix(ui): remove TopBar search (final) + add clear X to catalog input
User clarification after MR !91:
- "Search из TopBar убран — все верно" — TopBar search должен быть удалён.
- "TopBar search вернулся. убери его" — MR !91 ошибочно его вернул.
- "два крестика баг в топбаре был а ты и в таблице убрал его" — двойной X
  was в TopBar (native + custom); в catalog был только custom X на
  старом input. После refactor catalog input получился без X совсем —
  fix: добавил кастомный clear button когда q непустой.

Changes:
- TopBar: removed form + SearchInput + handlers (handleSearchInput /
  Submit / Clear / inputRef / useState). Removed useEffect ⌘K shortcut
  (без search input nothing to focus). Right cluster: Docs +
  VersionBadge + NotificationsBell. ml-auto на right cluster чтобы
  push'ить вправо без search в центре.
- Catalog input: добавлен absolute-positioned X (✕) справа input'а
  когда `search.q` непустой. `pr-7` на input чтобы текст не наезжал.
  Clear → `setSearch({ q: undefined })`. Single X confirmed visually.
2026-05-11 22:07:00 +03:00
Zimin A.N. 7e44df3493 fix(ui): restore TopBar search + add notifications bell + theme to sidebar
Follow-up к MR !90 per user feedback iterations:

1) "в поиске по справочникам два крестика" — fixed в SearchInput:
   `type="search"` (native browser X) → `type="text"`. Custom onClear X
   остаётся единственным. Catalog input тоже type="text".

2) "блин два крестика было на топбар поиске а тут норм все. верни" —
   restore TopBar search input. Context-aware behavior сохранён:
   - На /dictionaries → live filter каталога через URL ?q=
   - На остальных routes → submit (Enter) → /search records search
   Single X confirmed by visual test.

3) "свитч темы можно тоже в профиль перенести" — ThemeSwitch переехал в
   Sidebar footer (рядом с RU/EN button). Right row в footer: lang button
   слева, theme switch (3 icons sun/moon/monitor) справа через ml-auto.

4) "руководство и версию оставить в топбар чтобы подсвечивать новинки" —
   Docs + VersionBadge stays in TopBar. Туда же добавлена
   NotificationsBell (placeholder Bell icon) — broadcast slot для
   webhook errors / draft reviews / system notices когда backend
   notifications stream появится.
2026-05-11 22:03:12 +03:00
semantic-release-bot ffdf942344 chore(release): v1.6.0 [skip ci]
## [1.6.0](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/compare/v1.5.0...v1.6.0) (2026-05-11)

###  Features

* **ui:** batch UI polish — auth/lang to sidebar, search h-7, info overflow, graph zoom ([d9df2fc](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/d9df2fc359856dedc7a4f6a0aea8728dc508a706))
2026-05-11 19:01:38 +00:00
Александр Зимин ce2768d1d9 Merge branch 'feat/ui-polish-batch' into 'main'
feat(ui): batch UI polish — auth/lang to sidebar, search h-7, info overflow, graph zoom

See merge request 2-6/2-6-4/terravault/ordinis!90
2026-05-11 18:55:48 +00:00
Zimin A.N. d9df2fc359 feat(ui): batch UI polish — auth/lang to sidebar, search h-7, info overflow, graph zoom
User feedback batch — multiple iterations of UX refinement.

Layout shifts:
- TopBar right cluster: AuthBadge + LanguageSwitch переехали в Sidebar
  footer per user ("вход в сайдбар перенесем", "ru/en тоже в сайд баре").
  TopBar теперь: breadcrumb + search + Docs + VersionBadge + ThemeSwitch
  only. Освобождает место + concentrates user/lang controls в одном месте.
- Sidebar footer: новая структура — Lang toggle (Язык [RU/EN]) + Auth block
  (avatar+name+logout authed, Sign-in CTA anonymous) + collapse button.
  Refactored из inline JSX в named subcomponents (AuthedUserBlock,
  SignInCta, SidebarFooter).

Sizing / spacing:
- TopBar SearchInput: h-9 → h-7 to match LangSwitch/ThemeSwitch (+ Sign-in
  кнопка). User: "поиск по справочникам высоту выровняй". Override via
  `!h-7 text-cell` className на SearchInput.
- TopBar: h-14 → h-11 (slimmer). Sidebar logo block matches h-11.

Catalog search:
- Catalog page input в toolbar — restored для on-page filter ("Catalog
  search никак не работает" → проверил, работает; добавил TopBar context-
  aware behavior где TopBar input на /dictionaries route синхронизируется
  с URL ?q= live).
- TopBar search context-aware: catalog mode = live filter; else = submit
  → /search (records JSONB search).

InfoPanel:
- Description: `text-body text-ink-2 leading-relaxed` → +
  `break-words overflow-hidden`. Long slash-separated values
  (LZW/Deflate/JPEG2000/ZSTD/LERC) теперь wrap'ятся внутри panel вместо
  overflow за границы (user: "описание убежало за границы панели").
- Container: + `min-w-0 overflow-hidden` для proper flex shrinking.

Graph:
- Zoom controls overlay (+/-/1:1/N%) + mouse wheel zoom toward cursor +
  drag pan по empty space. Per user: "Граф связей еще не зумируется".

WorkflowBanner:
- Moved в InfoPanel banner slot (compact flex-col layout) — free
  horizontal space выше editor + concentrates status info в left rail.

Auth:
- AuthBadge: primary Button → compact h-7 outline button. Matches
  TopBar toolbar control style.
- RequireAuth: убран visible amber error banner "Авторизация недоступна:
  Failed to fetch" — silent fall-through к anonymous mode (user feedback).
- routes/index.tsx: beforeLoad skip redirect если есть `?code=` в URL
  (OIDC callback fix). HomeIndex компонент рендерит null + redirect на
  /dictionaries после auth complete.

LanguageSwitch:
- h-8 + items-stretch + inner items-center — matches ThemeSwitch height.
- Later moved entirely в Sidebar footer (h-7 button only) per user.
2026-05-11 21:50:21 +03:00
semantic-release-bot 1bee41e2cf chore(release): v1.5.0 [skip ci]
## [1.5.0](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/compare/v1.4.0...v1.5.0) (2026-05-11)

###  Features

* **editor:** restore 3-col HubView + hide AOI on non-geo dicts ([b0e1995](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/b0e19951b30773545fdaf296e398ffe3ec4b5cae))
2026-05-11 17:55:39 +00:00
Александр Зимин 4b14749ec0 Merge branch 'feat/restore-hub-view-hide-aoi-non-geo' into 'main'
feat(editor): restore 3-col HubView + hide AOI on non-geo dicts

See merge request 2-6/2-6-4/terravault/ordinis!89
2026-05-11 17:49:44 +00:00
semantic-release-bot c3ae1a7ecc chore(release): v1.4.0 [skip ci]
## [1.4.0](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/compare/v1.3.0...v1.4.0) (2026-05-11)

###  Features

* **catalog:** scope-colored row stripes + filter pills + chips ([bc73782](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/bc737820d6a74755494987bf7c45cc2674ab2365))
* **catalog:** toolbar layout per redesign prototype ([ad7c51d](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/ad7c51d93fe73c8af4c91464637992ef758d9b48))
* **editor:** Fields / Events / History tabs match redesign prototype ([cbe21db](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/cbe21dbc52026998ceb91205a491b531f201c0c1))
* **editor:** scope-colored InfoPanel badge + Time-travel label ([e580a04](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/e580a04007e2a0658b3cfcedc73f240bd81978ac))
* **editor:** wrap InfoPanel + main content in bordered panels per prototype ([ce1f40c](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/ce1f40c5d1771166a7ba59785d8b2a4623c0ed9a))
* **editor:** Связи tab 2-col split per redesign prototype ([180a592](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/180a5920fe79b2144396bc3fb6ff6a90337e3a3e))
* **layout:** catalog relative time + chevron + flat sidebar per redesign (4) ([7e33456](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/7e33456d70875ad70e8748517cb668b0abd6fec2)), closes [#faf9f5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/faf9f5)
* **record:** conflict diff modal на 409 save (handoff line 444) ([16da694](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/16da694d8ca9acb1a3014f0d2947ea2421c57401))
* **records:** accent businessKey + remove redundant Export CSV from bulk bar ([3e4d789](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/3e4d78906d4ebb976ec9382defd6c7c502add794))
* **topbar:** match redesign prototype — breadcrumb back-arrow + cleaner right cluster ([ac1ca8d](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/ac1ca8d035d928bfd90ab36650cd38a196a73ebc))

### 🐛 Fixes

* **catalog:** title→TopBar + toolbar→tinted bar + table white + font fix ([d77f040](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/d77f040a5c2ba7b566cd94d50f1776d695988278))
* **table:** white row bg + stronger hover per user feedback ([a27e9ec](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/a27e9ec901d609afea150d1272c2be5b4bee8adb)), closes [#faf9f5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/faf9f5)
* **topbar:** restore full right cluster per user preference ([38f7dce](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/38f7dcee3ec7ba645ecbbaa8e278fb060f2b7c6c))
* **topbar:** revert ThemeSwitch to 3-icon original + shorten create button ([6627fd9](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/6627fd918d382f338bc4ee2667df70dfae604191))
2026-05-11 17:47:48 +00:00
Zimin A.N. b0e19951b3 feat(editor): restore 3-col HubView + hide AOI on non-geo dicts
Per user feedback:
- "hub view" — restore старый 3-col layout с central focused dict card +
  outgoing FK rail слева + refBy rail справа. Был simpler 2-col split,
  но user previously сказал "Связи и вкладка связи была удобнее" (старый
  hub более информативный + центральная карта показывает context).
  Revert к версии 5007e0f (pre-2-col-redesign).
- "aoi там где нет полей гео лишний" — InfoPanel AOI button теперь скрыт
  если schema dict не имеет geo properties. Heuristic: property name
  matches /geom|location|bbox|polygon|coordinates|geo/i OR format=geojson|wkt.
  Edge case: если active aoi уже set → button показывается чтобы clear.
2026-05-11 20:19:27 +03:00
Александр Зимин ff0a8b25cc Merge branch 'feat/business-key-accent-bulk-bar-export-removed' into 'main'
feat(records): accent businessKey + remove Export from bulk bar

See merge request 2-6/2-6-4/terravault/ordinis!88
2026-05-11 17:14:49 +00:00
Zimin A.N. 3e4d78906d feat(records): accent businessKey + remove redundant Export CSV from bulk bar
Per user feedback:
- "поле Бизнес-ключ выделен цветом" — businessKey column TableCell теперь
  `text-mono text-accent` (было plain text-mono). Matches prototype 03 где
  RES-P-1, KAN-V-3, SNT-1A показаны в accent orange — primary identifier
  для каждой row.
- "Экспорт CSV в bulk bar лишний как повтор Экспорт кнопки в InfoPanel" —
  убрал Export button из BulkSelectionToolbar. ExportModal pre-picks
  scope=selected когда selection.size > 0, поэтому workflow:
  select rows → click "↓ Экспорт..." в InfoPanel → modal с pre-selected
  scope. Бэк endpoint тот же, UX cleaner — один путь к export'у.
- Removed handleBulkExport callback + DownloadSimpleIcon import (теперь
  unused).
2026-05-11 20:14:43 +03:00
Александр Зимин 3da788c5da Merge branch 'feat/editor-bordered-panels' into 'main'
feat(editor): wrap InfoPanel + main content in bordered panels

See merge request 2-6/2-6-4/terravault/ordinis!87
2026-05-11 17:11:10 +00:00
Zimin A.N. ce1f40c5d1 feat(editor): wrap InfoPanel + main content in bordered panels per prototype
Per user feedback: "словари в своих панелях то как у нас было ранее".

Per redesign prototype editor view (Ordinis(4) compact.html):
- InfoPanel: was floating sidebar aside без borders → теперь
  `rounded-lg border border-line bg-surface p-4` — visible bordered card
  containing PUBLIC chip + meta + Связи + actions.
- Main editor area: tabs + toolbar + tab content (records/relations/
  fields/json/events/history) обёрнуты в `rounded-lg border border-line
  bg-surface overflow-hidden` panel.
- WorkflowBanner и AOI banner остаются outside panels (status chrome).

Visual containment отделяет editor chrome от page background, делает
очевидным где info ends / table starts. Matches prototype Screen 03-08.
2026-05-11 20:11:04 +03:00
Александр Зимин ea729dc901 Merge branch 'fix/catalog-toolbar-bar-topbar-count' into 'main'
fix(catalog): title→TopBar + toolbar→tinted bar + table white + font fix

See merge request 2-6/2-6-4/terravault/ordinis!86
2026-05-11 17:06:23 +00:00
Zimin A.N. d77f040a5c fix(catalog): title→TopBar + toolbar→tinted bar + table white + font fix
Per user feedback:
- "Справочники 37 шт. эта надпись в топбаре" — title с inline count
  переехал в TopBar breadcrumb (новый Crumb.caption field, text-cap mute).
  Catalog page больше не имеет h1 — start straight from toolbar.
- "фильтры и кнопки в баре таблицы. бар цветом" — toolbar (scope/bundle
  pills + counter + Граф + + Создать) обёрнут в tinted `bg-surface-2`
  rounded bar с border. Визуально отделяет controls от table chrome.
- "заголовки таблицы белый фон" — table thead was `bg-surface-2` (cream),
  сливалось с toolbar bar. Стало `bg-surface` (white) — clean visual
  separation toolbar (tinted) → table (white).
- "→ ссылается шрифт не тот" — InfoPanel section subhead "→ ссылается"
  / "← используют" был `text-cap` (Tektur uppercase 10.5px bold).
  Прототип использует regular body Inter lowercase mute. Заменил на
  `text-body text-mute`.

TopBar useBreadcrumb extended: для catalog route добавляет inline `caption`
field из useDictionaries() count. Editor route остаётся с mono `subtitle`
("name · v1.0.0"). Different fields rendered с different styles.
2026-05-11 20:06:18 +03:00
Александр Зимин d4348d4d26 Merge branch 'fix/table-rows-white-stronger-hover' into 'main'
fix(table): white row bg + stronger hover

See merge request 2-6/2-6-4/terravault/ordinis!85
2026-05-11 17:00:45 +00:00
Zimin A.N. a27e9ec901 fix(table): white row bg + stronger hover per user feedback
User: "строки таблиц белые / ховер на них более чёткий а то еле видно".

Прошлый hover был bg-surface-2/40 (40% opacity на cream/yellow page bg) —
почти неотличим от default. Под page bg #faf9f5 + 40% opacity surface-2
тёмное пятно еле проступало. На long тяжело отследить какая row под cursor.

Изменения:
- DictRow (catalog table): убран subtle scope-color bg tint (был
  warn-bg/30, pink-bg/30 — еле виден на page bg). Row всегда `bg-surface`
  (white). Scope visually conveyed через 3px left-stripe + colored SCOPE
  chip. Hover full strength `bg-surface-2` (no /40 opacity).
- FieldsTabContent + EventsTabContent rows: same change — bg-surface +
  hover:bg-surface-2.
- Shared TableRow component (ui/components/table.tsx): bg-surface +
  hover:bg-surface-2 — applies к records table, audit, и любым другим
  TableRow callsites.
2026-05-11 20:00:40 +03:00
Александр Зимин 1b382cb338 Merge branch 'fix/topbar-restore-full-cluster' into 'main'
fix(topbar): restore full right cluster (Docs/VersionBadge/LangSwitch)

See merge request 2-6/2-6-4/terravault/ordinis!84
2026-05-11 16:56:06 +00:00
Zimin A.N. 38f7dcee3e fix(topbar): restore full right cluster per user preference
User explicitly: "Руководство · dev · 19a3731b · ☀️🌙🖥 · RU EN · zimin.an · ↩
это оставь". Revert MR !81 cluster-minimization — diagnostic info нужна
для prod debugging.

Restored:
- Docs link (/docs/) — opens admin docs portal
- VersionBadge (channel + commit short SHA) — shows local/dev/v1.x.x · hash
- LanguageSwitch (dual RU | EN radio) — keeps both visible vs single-toggle
- (ThemeSwitch + AuthBadge остаются как были)
2026-05-11 19:55:52 +03:00
Zimin A.N. 6627fd918d fix(topbar): revert ThemeSwitch to 3-icon original + shorten create button
User explicitly: "ThemeSwitch не трогай". Реверт my 2-button Earth|Dark
переделку обратно на 3-icon Sun/Moon/Monitor segmented control (по
original 3bfa7ca).

Также:
- schema.action.create RU: "Создать справочник" → "Создать"
- schema.action.create EN: "Create dictionary" → "Create"
  (per prototype catalog button — короче чтобы не растягивать toolbar)
2026-05-11 19:50:41 +03:00
Александр Зимин 1102e7b8ec Merge branch 'feat/scope-badge-timetravel-label' into 'main'
feat(editor): scope-colored InfoPanel badge + Time-travel label

See merge request 2-6/2-6-4/terravault/ordinis!82
2026-05-11 16:46:52 +00:00
Zimin A.N. e580a04007 feat(editor): scope-colored InfoPanel badge + Time-travel label
Per redesign (4) prototype.

- InfoPanel scope badge: было `<Badge variant="info">` (generic light bg).
  Стало scope-color filled chip: PUBLIC→accent-bg, INTERNAL→warn-bg,
  RESTRICTED→pink-bg. Matches table SCOPE col + filter pills.
- i18n: timeTravel.button RU "Просмотр на дату" → "Time-travel…"; EN
  "View as of date" → "Time-travel…". User confirmed: "Time-travel label
  оставь" — единый label везде, без локализации (бренд-слово как редизайн).
2026-05-11 19:46:33 +03:00
Александр Зимин a9394ea363 Merge branch 'feat/topbar-cleanup-infopanel-order' into 'main'
feat(topbar): breadcrumb back-arrow + cleaner right cluster + InfoPanel order

See merge request 2-6/2-6-4/terravault/ordinis!81
2026-05-11 16:43:21 +00:00
Zimin A.N. ac1ca8d035 feat(topbar): match redesign prototype — breadcrumb back-arrow + cleaner right cluster
Per /Users/zimin/Downloads/Ordinis (4)/redesign/compact.html.

TopBar breadcrumb:
- Detail routes теперь показывают `← Справочники / Космические аппараты`
  с back-arrow prefix на parent crumb (caption text, mute). Bold title +
  inline mono subtitle "satellites · v1.0.0".
- Catalog route: simple "Dictionaries" title.

TopBar right cluster cleanup:
- Removed `Docs` link — diagnostic, не critical UX, моя кноп не нужна
  для UI flow.
- Removed `VersionBadge` (commit + tag) — был noise рядом с продакшн
  features. Build info всё ещё доступна в browser console / Docs.
- ThemeSwitch: tri-state (Light/Dark/System icons 3×24px) заменён на
  2-button `Earth | Dark` с text labels (per prototype). `system`
  preference остаётся в localStorage для existing users, но новый UI
  не выставляет.
- LanguageSwitch: dual radio `RU | EN` заменён на single toggle button —
  показывает текущий язык как label, click переключает на следующий.
  Saves ~60px горизонтально, matches prototype.

EditorInfoPanel order:
- Action buttons (Экспорт / Time-travel / AOI) переехали из середины
  panel (между metadata и Relations) в bottom (после Relations) —
  per prototype. Info → meta → relations → actions flow.
- Action order: Экспорт первым (frequent), затем Time-travel, AOI последним
  (rare для most dicts).
2026-05-11 19:43:05 +03:00
Александр Зимин 4219a6f96d Merge branch 'feat/catalog-scope-color-rows' into 'main'
feat(catalog): scope-colored row stripes + filter pills + chips

See merge request 2-6/2-6-4/terravault/ordinis!80
2026-05-11 16:35:57 +00:00
Zimin A.N. bc737820d6 feat(catalog): scope-colored row stripes + filter pills + chips
Per redesign prototype screenshot: каждая row имеет 3px цветной strip слева
по scope + filter chips заполняются scope-color когда active.

- DictRow: добавлен absolute-positioned `<span>` шириной 3px на левом краю
  первой td (relative wrapper), background = SCOPE_DOT (PUBLIC=accent,
  INTERNAL=warn, RESTRICTED=pink). pl-1 на контенте чтобы не наезжал.
- Row bg tint: для INTERNAL/RESTRICTED rows — subtle SCOPE_BG_TINT/30,
  PUBLIC = plain white (default).
- SCOPE col chip: использует SCOPE_BG_TINT + SCOPE_TEXT вместо generic
  Badge info — теперь PUBLIC chip orange, INTERNAL amber, RESTRICTED pink.
- Toolbar scope filter pills: active state = SCOPE_BG_TINT + SCOPE_TEXT +
  border-transparent (filled in scope color). Inactive = outline.
2026-05-11 19:35:43 +03:00
Zimin A.N. 180a5920fe feat(editor): Связи tab 2-col split per redesign prototype
Per /Users/zimin/Downloads/Ordinis (4)/redesign/screens/04-editor-links.png.

Replaced 3-col hub view (left rail + center dict card + right rail) с simple
2-col grid. Central dict card стал избыточен — все его info уже в InfoPanel
слева, дублирование тратило место и attention.

New layout:
┌────────────────────────────┬────────────────────────────┐
│ → ССЫЛАЕТСЯ НА (N)         │ ← ССЫЛАЮТСЯ НА НАС (M)     │
│ ┌──────────────────────┐   │ ┌──────────────────────┐   │
│ │ {target} {count}     │   │ │ {source} {count}     │   │
│ │ {req|opt} {.field}   │   │ │ {крит} {.field}      │   │
│ └──────────────────────┘   │ ├──────────────────────┤   │
│                            │ │ Warning N ссылок     │   │
│                            │ └──────────────────────┘   │
└────────────────────────────┴────────────────────────────┘

Each outgoing row: target_dict (link accent) | recordCount | required/optional
chip | source_field (mono right).
Each incoming row: source_dict (link) | activeRecordsInSourceDict | onClose
policy chip (BLOCK=критично pink, CASCADE=warn amber) | .source_field.

Footer warning в incoming panel когда totalDeps > 100 — "удаление сложно".
2026-05-11 19:29:37 +03:00
Александр Зимин 19a3731ba9 Merge branch 'feat/catalog-relative-time-flat-sidebar' into 'main'
feat(layout): catalog relative time + chevron + flat sidebar per redesign (4)

See merge request 2-6/2-6-4/terravault/ordinis!78
2026-05-11 16:27:18 +00:00
Zimin A.N. 7e33456d70 feat(layout): catalog relative time + chevron + flat sidebar per redesign (4)
Per /Users/zimin/Downloads/Ordinis (4)/redesign/compact.html (бэкграунд
прототипа уже #faf9f5 — match'ит наш neutral default).

Catalog table:
- ИЗМЕНЁН column показывает relative time: Xс / Xмин / Xч / Xд / Xмес / Xг.
  Прошлая абсолютная дата (05/06/2026) затирала scale ("5 минут vs 3 месяца —
  визуально одинаково далеко"). Прототип использует 2ч, 3д, 1мес.
- Chevron `›` column добавлен в конец каждой строки — affordance что row
  кликабелен (открывает editor).

Sidebar:
- Flatten: убраны section labels (workflow / admin). Все nav items в одном
  списке per redesign: Главная → Справочники → Мои черновики → На ревью →
  Outbox → Webhooks → Аудит → Поиск.
- /graph удалён из sidebar — теперь reachable только через catalog toolbar
  "Граф ⇄" button (single entry point, no duplication).
- Применено в обоих Sidebar (desktop) и MobileSidebar (drawer).

Cleanup: убран unused GitBranch icon import.
2026-05-11 19:26:56 +03:00
Александр Зимин b39e0500de Merge branch 'feat/editor-tabs-redesign' into 'main'
feat(editor): Fields / Events / History tabs match redesign prototype

See merge request 2-6/2-6-4/terravault/ordinis!77
2026-05-11 16:21:17 +00:00
Zimin A.N. cbe21dbc52 feat(editor): Fields / Events / History tabs match redesign prototype
Per redesign/screens/{05-fields,07-events,08-history}.png:

Fields tab (Поля):
- # numbered col (01, 02, ...) — mono mute, tabular-nums
- ПОЛЕ — bold accent (was plain mono)
- ТИП — inline FK render: `fk → target_dict`, array as `string[]`,
  date/date-time format names, enum, native types
- REQUIRED / UNIQUE / I18N / INDEX — checkmark (green) or — dash
- INDEX heuristic: x-unique || x-references → indexed (backend doesn't
  expose explicit flag yet)
- ОПИСАНИЕ truncate с max-w-[320px]

Events tab (События):
- Filter chips above table: все N / webhooks / publish / review / edit /
  export (только показываем те которые есть, кроме «все»)
- "Полный лог →" link справа в chips row
- Table cols: Время (5 sec precision) / Тип (colored chip) / Статус
  (● dot + ok/fail) / Куда·Кто (user) / Сообщение (businessKey · action)
- Type chips colored: webhook=accent, publish=green, review=warn,
  export=surface-2, edit=accent-bg/50

History tab (История):
- HEAD row: ● filled dot + v{version} + HEAD chip (dark) + change summary
  (+N ~0 −0 placeholder until backend changelog endpoint появится)
- Description + updatedAt date
- Backend-pending notice card: "/api/v1/dictionaries/{name}/changelog pending"

Plus: + import { cn } from '@/lib/utils' для новых tabs
2026-05-11 19:20:57 +03:00
Александр Зимин a0b10e50ec Merge branch 'feat/conflict-diff-modal' into 'main'
feat(record): conflict diff modal на 409 save

See merge request 2-6/2-6-4/terravault/ordinis!76
2026-05-11 16:13:57 +00:00
Zimin A.N. 16da694d8c feat(record): conflict diff modal на 409 save (handoff line 444)
Когда PUT /records/{key} возвращает 409 (optimistic-lock fail — другой
пользователь сохранил тот же record между нашим load и submit'ом),
открываем ConflictDiffModal.

Component:
- Header: 'Конфликт сохранения · {DICT}' + business key
- Diff body: refetch server state via useRecordRaw, иди по union ключей
  local + server, оставь только отличающиеся. Per-row: field name (mono)
  + ваше значение (accent-bg) + серверное (surface-2)
- Footer 3 actions:
  - Отмена: close, оставить editor open
  - Загрузить серверное: discard local, refetch records, close editor
  - Перезаписать: re-submit current payload (если опять 409 → новый diff)
- Backend-friendly: не требует server diff endpoint, client считает diff
  client-side через JSON.stringify equality

Route wiring:
- onError handler distinguishes generic 409 (open diff modal) от
  специальных кодов: x_references_blocked_by_dependents,
  x_references_cascade_required, draft_required — те идут в свои dialogs
- Conflict state ({payload, businessKey}) capture'ит local data чтобы
  показать в diff даже после reset формы
2026-05-11 19:13:30 +03:00
semantic-release-bot 258ba50d3e chore(release): v1.3.0 [skip ci]
## [1.3.0](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/compare/v1.2.2...v1.3.0) (2026-05-11)

###  Features

* **admin-ui:** editor 6-tab layout (Stage 3.4) ([640c890](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/640c890d0bb35117ee32420f11d4960c24aeabb8))
* **admin-ui:** editor 6-tab layout (Stage 3.4) ([0ddba87](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/0ddba871f7cbc62ac49a72144cfc9c98dfc861d4))
* **catalog:** row-based table per handoff prototype design/compact.html ([f43ce55](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/f43ce5563a7f6ddffb494b1879247c4c582b4567)), closes [#2](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/2)
* **drawer:** all-sections layout с chips strip per handoff prototype ([155c70e](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/155c70e23cc0e38deb10953c176ff3835712f415)), closes [#5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/5)
* **drawer:** sticky toolbar API per handoff Screen 3 line 279 ([d4000dd](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/d4000ddd3d93facfeb4f61270f132cf5fe16974c)), closes [#5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/5)
* **editor:** + Экспорт button в InfoPanel per redesign dark theme screenshot ([e15a391](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/e15a3916bfcd89f61cc63ea5f5472474bad98f9b))
* **editor:** ExportModal + TimeTravelModal + InfoPanel merge + fixes ([5a2220d](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/5a2220d77966efff26ddac12b2d408cdf5696f5f)), closes [#fbf8ee](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/fbf8ee) [#faf9f5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/faf9f5)
* **editor:** keyboard shortcuts j/k/Enter/n per handoff Screen 2 ([a09c411](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/a09c4113c1b8331590cc2e368dec680bcb4d1e04))
* **editor:** left info panel + 3-col layout per handoff prototype ([a57cf52](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/a57cf520a428b5d72966818967327fa714f05728))
* **editor:** match redesign prototype layout — TopBar title + tab counts + InfoPanel actions ([ec99010](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/ec99010697e8a2687d99ee01e2dc4751a62a8346))
* **editor:** Stage 3.4 polish — Events embedded + JSON syntax highlight ([f0392af](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/f0392af0e37a06f784cb18558f8fb79c1b8bce24))
* **handoff:** WorkflowBanner + table a11y + responsive + toast styling ([0acba4c](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/0acba4c073507951b9dbdd191ff0a4ad0ed8252a))
* **mobile:** Sidebar drawer <1024px + Modal/Sheet fullscreen <880px ([7a3b31b](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/7a3b31b9578ef280e25c88f2657a62bf7272f216))
* **record:** RecordDrawer slide-over per Stage 3.5 handoff (Phase A) ([750395d](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/750395da09dc11a4048744417933864df147708d)), closes [#5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/5)
* **sidebar:** desktop collapse mode 220px → 56px per handoff prototype ([69a86b2](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/69a86b238c3baa2c6cf44f8d6b9a15bcc59664b5))
* **theme:** sync color tokens с redesign ui-kit + add claude-light theme ([42dab24](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/42dab24d964533d6ce600e5d5c73f6ff2b8e87ce)), closes [#fbf8ee](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/fbf8ee) [#d4a07a](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/d4a07a) [#faf9f5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/faf9f5) [#d97757](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/d97757)
* **ui:** drop @nstart/ui dependency (Stage 3.9) ([5007e0f](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/5007e0f4eb730454c9883942fa3c59c6416f0637))
* wire drawer toolbar filters + records table responsive hiding ([889207f](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/889207f62901820fcb3e908fd576cd0878013945))

### 🐛 Fixes

* **admin-ui:** sidebar font sizes per handoff spec ([f72aac6](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/f72aac63986e3ba30717139f852ebbf5fe26bc23))
* **admin-ui:** sidebar fonts per handoff ([0297745](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/0297745d139ae7ebb9076c61e83d6a2d53a6e275))
* **admin-ui:** UpdateBanner generic message ([dc0002f](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/dc0002f379f96e7d22746f3fc2b87e7b456475f5))
* **fonts:** align all text sizes to handoff spec via Tailwind theme overrides ([71432e9](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/71432e9ae7006bad3bc38cf89ce82c6596e07c81))
* **fonts:** explicit font-family on title utilities + cascade conflicts ([f0dbc20](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/f0dbc20f62c7b3b0c9f0150247fb3b14007f267d))
* **fonts:** semantic typography utilities per handoff (7 roles) ([b949127](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/b94912789f7d7be93def334aeb3377dd0dad409d))
* **release:** drop invalid tarballDir: [secure] config ([090bff5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/090bff56ce2aa9153617dc11a623005fa0c88918))
* **table+layout:** TableHead alias to THEAD wrapper + kill horizontal scroll ([787cea9](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/787cea9db172b3f111c357129af45183ce461efa))
* **theme:** de-saturate light bg — убрать жёлтый Earth-cream tone ([e5572d5](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/e5572d534640953f86fed7eecefe0210d49c3925)), closes [#fbf8ee](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/fbf8ee) [#fbf8ee](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/fbf8ee) [#fafaf8](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/fafaf8) [#f4eedc](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/f4eedc) [#f2f1ee](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/f2f1ee) [#e3dccb](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/e3dccb) [#e4e1dc](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/e4e1dc) [#efe9d8](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/efe9d8) [#ecebe7](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/ecebe7) [#b05a2e](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/b05a2e) [#3a2818](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/issues/3a2818)
* **ui:** 3 user-reported issues ([abdfaa8](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/abdfaa8fcc2da6fba8bab6d73f43498e4f77f5a5))
* **ui:** tailwind-merge стрипал text-body — buttons ушли в 16px inherited ([9e2d985](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/9e2d985485f60f8333ed5d81de7cd6bcd5009bad))
* **version:** bump to 1.3.1 and show 8-char commit hash ([780de70](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/780de70fc5cf91c3904a8dc417a09514e3ddf584))
* **version:** channel-based label, no semver fallback for branch builds ([3223a5c](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/3223a5ced74956efa85cf1a9d4be0d51a17b2297))
* **version:** detect CI build via CI_COMMIT_SHORT_SHA, not process.env.CI ([b6af155](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/b6af155da256a395db6757c911e1e3e3c50cac9a))
* **version:** read CI_COMMIT_TAG as source of truth, package.json as fallback ([e62633d](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/e62633d903c063540d521c4b063795aade1b6a14))

###  Reverts

* **timetravel:** keep 'Time-travel…' label ([36fb70f](https://git.nstart.cloud/2-6/2-6-4/terravault/ordinis/commit/36fb70fc00a62f93687142293c318b231b915a07))
2026-05-11 16:11:52 +00:00
Zimin A.N. ad7c51d93f feat(catalog): toolbar layout per redesign prototype
Match handoff screenshot:
- Title "Справочники" + inline "N шт." count caption (no description text)
- Remove page-level SearchInput (TopBar already has global search ⌘K)
- Reorder toolbar to single row:
  [scope pills PUBLIC|INTERNAL|RESTRICTED]
  | divider |
  [bundle pills все|cuod|geo|i18n|core]
  | spacer |
  N/M counter
  [Граф ⇄] (→ /graph)
  [+ Создать] (moved here from PageHeader actions)
- Scope/bundle pills are bordered chips с ring-1 для active state
- Drop deps-only toggle (not in redesign)
- Drop scopeCounts useMemo (counts moved out of chip labels per design)
2026-05-11 19:09:39 +03:00
Zimin A.N. 5a2220d779 feat(editor): ExportModal + TimeTravelModal + InfoPanel merge + fixes
UI redesign matching prototype (Ordinis (3) dump):
- ExportModal: format (CSV/JSON/Excel/SQL) + scope (all/filtered/selected) +
  column toggles + encoding/delimiter + preview filename per redesign line
  1059-1092. CSV uses backend mutation, JSON client-side from filtered rows,
  Excel/SQL disabled (backend pending).
- TimeTravelModal: full-page compare СЕЙЧАС vs ТОЧКА ВО ВРЕМЕНИ + quick
  presets (сейчас/неделя/месяц/год/при создании) + step toggle версия/день
  + slider + tabs (Что изменилось / Записи на момент / Структура и поля) +
  "Открыть как readonly" CTA. Replaces inline TimeTravelPicker.
- InfoPanel ← используют merge: rich rows с field path + active records
  count + onClose policy chip (BLOCK/WARN/CASCADE). Inline
  DictionaryDependentsPanel above records table removed (one source of truth).
- Sidebar logo: match redesign/ui-kit.html .brand SVG (outer ring + inner
  faded ring + orbit dot offset right cx=22.5). ORDINIS Tektur tracking 0.22em
  + MDM smaller mute 0.32em.
- Bg neutralized: #fbf8ee Earth cream → #faf9f5 warm neutral default
  (per user preference, Earth cream still described in comment как opt-in).
- WorkflowBanner: Case 1 Live (approvalRequired=false) returns null —
  permanent "Опубликовано" banner = noise, status already visible в
  InfoPanel scope/version/updatedAt. Banner показывается только когда
  есть actionable state.

Critical bug fixes:
- fix(CascadeConfirmDialog): infinite render loop "Maximum update depth
  exceeded". useEffect had cascadeMut (TanStack Query mutation wrapper) в
  deps — wrapper identity changes every render → effect fires → reset() →
  store update → render → loop. Extract stable `reset` reference перед
  useEffect. Симптомы у user: создание/редактирование записи не работали.
- fix(semantic-release): add missing peer dep
  conventional-changelog-conventionalcommits (9.3.1). semantic-release 22+
  больше не bundles preset. Без неё release job падал с
  "Cannot find module 'conventional-changelog-conventionalcommits'".
2026-05-11 19:01:57 +03:00
Zimin A.N. e15a3916bf feat(editor): + Экспорт button в InfoPanel per redesign dark theme screenshot
User dropped /Users/zimin/Downloads/Ordinis (3) — full project dump.
Dark theme editor screenshot (uploads/draw-4b771386...png) показывает
INFO PANEL c двумя buttons:
  - ↓ Экспорт…
  - ⟲ Time-travel…

У нас был Time-travel + AOI — добавил Экспорт как third button.

Implementation:
  - EditorInfoPanel.actions.onExport + exportPending props
  - DownloadSimpleIcon кнопка 'Экспорт…'
  - Wired к useBulkExportRecords mutation:
    * Selection не empty -> export selected
    * Selection empty -> export all filtered records
  - disabled когда mutation pending, label 'Экспорт…'

Project dump reviewed:
  - design_handoff_dictionary_catalog — старый handoff, всё уже реализовано
    (List view MR !62, Hub MR earlier, Graph earlier)
  - patches/ — @nstart/ui patches, moot (мы dropped @nstart/ui MR !52)
  - redesign/ — уже синхронизированы colors MR !71, layout MR !69
  - uploads/ — user-provided screenshots, main delta = Export button
2026-05-11 18:03:52 +03:00
Zimin A.N. 36fb70fc00 revert(timetravel): keep 'Time-travel…' label
User feedback: 'Time-travel label такое себе Time-travel… оставь'.
Reverting MR !70 part of rename ('Таймлайн' → 'Time-travel…').

Per handoff prototype line 299 это и был 'Time-travel…' изначально —
надо было не трогать.
2026-05-11 17:56:38 +03:00
Zimin A.N. 42dab24d96 feat(theme): sync color tokens с redesign ui-kit + add claude-light theme
Reverted MR !66 de-yellow — turns out redesign prototype intentionally
использует жёлтый Earth cream (#fbf8ee) как primary bg. User confusion
was с предыдущим build'ом до MR !66, в ui-kit все таки cream.

Added tokens per redesign/ui-kit.html prototype:

Scope tints:
  --bg-public, --bg-internal, --bg-tenant (для scope chip backgrounds)
Workflow states:
  --bg-draft, --bg-live, --bg-deprec (для workflow banner backgrounds)
Alert variants:
  --al-info-bg/bd, --al-warn-bg/bd, --al-err-bg/bd, --al-ok-bg/bd
Shadows:
  --shadow-l, --shadow-m, --shadow-toast, --shadow-drawer (consistent)
Toast cap color:
  --toast-cap #d4a07a (orange-cream per handoff Screen 4)
Avatars:
  --avt-pink-bg, --avt-green-bg (semantic state avatar backgrounds)
Purple:
  --color-purple для future use

New theme '[data-theme=claude-light]':
  Warm cream neutral (#faf9f5) — для users которые не любят saturated Earth.
  Accent navy → coral orange (#d97757) per Claude branding.
  Full token set включая scope/workflow/alert variants.

Dark theme получил те же дополнительные tokens (bg-public/internal/tenant,
al-info-bg/bd, shadows, toast-cap, avt-bg) — consistency с light tier.

User может через ThemeSwitch / manual data-theme attr выбрать:
  default     — Earth cream (handoff design intent)
  claude-light — neutral warm
  dark        — Claude-style dark

Bundle: +~1KB CSS. Tests: 116 pass.
2026-05-11 17:53:45 +03:00
Zimin A.N. abdfaa8fcc fix(ui): 3 user-reported issues
1) MODAL OFF-SCREEN (Schema/AOI/Confirm dialogs)
DialogContent had `inset-0 w-full h-full` + `min-[880px]:inset-auto`
конфликтовал — inset-0 winning по CSS specificity, modal приклеивался
к левому краю viewport вместо центра. User screenshot показал Schema edit
выходящим за левую границу экрана.

Fix: remove inset-0 fullscreen pattern. Use simple centered modal —
left-1/2 top-1/2 -translate-x-1/2 -translate-y-1/2 + w-[95vw] max-h-[95vh]
overflow-y-auto. На mobile <880px max-w из size variant даёт ширину 95vw
(natural fit). На desktop max-w ограничивает до 440/560/720/880/920px.

2) LOGO 'ORDINIS MDM' С CIRCLE ICON (per redesign prototype)
Sidebar logo: 'ORDINIS' → circle icon (accent orbit ring + dot) +
'ORDINIS' bold + 'MDM' mute subtitle (Tektur). SVG inline — нет external
dep.

Collapsed mode: только circle icon, no text (uses Tektur ORDINIS dropped).

3) TIMELINE BUTTON LABEL
InfoPanel button 'Time-travel…' → 'Таймлайн' (per user feedback). Behaviour
не меняется — клик открывает picker. Inline таймлайн visualization
отложен (большой refactor, нужен product decision).

Verified:
  - Dialog modal центрируется на десктоп
  - Logo рендерится с svg + text
  - Tests: 116 pass
2026-05-11 17:49:57 +03:00
Zimin A.N. ec99010697 feat(editor): match redesign prototype layout — TopBar title + tab counts + InfoPanel actions
Per /Users/zimin/Downloads/redesign/screens/03-editor-records.png редизайн
prototype editor layout отличается от current MVP:

1. TopBar absorbs editor title + version (was в PageHeader)
2. PageHeader удалён — title и breadcrumb теперь только в TopBar
3. Tab labels получили counts (Записи 127, Связи 6, Поля 12)
4. Action buttons распределены per role:
   - Time-travel + AOI → InfoPanel bottom (close к data context)
   - Schema edit + +Запись → tab toolbar right (close к tab actions)

Changes:

src/components/layout/TopBar.tsx
  - Breadcrumb получил subtitle slot — mono '<name> · v<version>'
  - useBreadcrumb fetches dict detail для editor route '/dictionaries/$name'
  - Render: '← Справочники / Космические аппараты satellites · v1.0.0'

src/api/queries.ts
  - useDictionaryDetail принимает name: string | undefined + enabled flag
  - Guard для editor breadcrumb когда route не matches dict

src/routes/dictionaries.$name.tsx
  - Removed <PageHeader> — title/breadcrumb теперь в TopBar
  - EditorInfoPanel получает actions prop:
    onTimeTravel + timeTravelActive + onAoi + aoiActive
  - EditorTabBar получает counts (per-tab badge) + actions slot
    (right-aligned Schema + +Запись buttons)
  - extractOutgoingFkCount helper для relations count

src/components/editor/EditorInfoPanel.tsx
  - actions prop с Time-travel + AOI buttons
  - Rendered в panel выше Relations section, между metadata и FK list
  - aria-pressed когда active (time-travel или AOI с filter)

src/components/editor/EditorTabBar (inline in route)
  - counts prop: Partial<Record<EditorTab, number>>
  - actions prop: ReactNode для right-aligned cluster
  - inline count badge — text-mono text-mute next to label

Tests: 116 pass. TS strict clean.
2026-05-11 17:45:06 +03:00
Zimin A.N. 69a86b238c feat(sidebar): desktop collapse mode 220px → 56px per handoff prototype
Handoff prototype показывает «‹ Свернуть» button внизу sidebar — toggle
desktop rail в icon-only 56px. Persists в localStorage ord-sidebar-collapsed.

Sidebar component:
  - State collapsed (localStorage 'ord-sidebar-collapsed' = '1')
  - <aside width> transitions между w-[220px] и w-[56px] (200ms ease)

SidebarContent (DRY с MobileSidebar) получил props:
  - collapsed?: boolean (default false)
  - onToggleCollapsed?: () => void (undefined hides button — mobile drawer)

Когда collapsed:
  - Logo: 'ORDINIS' → 'O' (single char, centered)
  - Section labels (text-cap headers) — hidden
  - Nav links: icon-only, centered, icon size 18px (vs 15px expanded);
    title attribute с label для hover tooltip
  - Badges (records count, pending) — hidden (нет места)
  - User block: avatar only, name/email hidden; title attribute с full name
  - Toggle button bottom: '‹ Свернуть' → '›' (icon-only)

Mobile (MobileSidebar Sheet) НЕ получает collapse — там Sheet даёт full
nav text всегда, close через × header.

A11y: aria-label / title для всех collapsed buttons. Click handler
sets localStorage + state — survives F5.

Tests: 116 pass. TS strict clean.
2026-05-11 17:13:06 +03:00
Zimin A.N. 889207f629 feat: wire drawer toolbar filters + records table responsive hiding
Closing 2 handoff gaps:

1) DRAWER TOOLBAR FILTERS (handoff Screen 3 line 279)
SchemaDrivenForm получил три new optional props:
  - searchFilter (string) — case-insensitive substring против field key + label
  - onlyFilled (boolean) — hide fields с empty data[key]
    (null/undefined/''/false/0/empty-array/empty-object)
  - onCounterChange (visible, total) — surface field counter parent'у

Filter применяется поверх bucketing — все три buckets (identity/description/
extra) фильтруются. UI рендерит filteredBuckets.X.map(...) вместо raw bucket'ов.

В sections layout (drawer use case) если section после filter empty —
sticky header не рендерится. Tabs layout backward-compat (filter применяется
но visually invisible если user в другом tab'е).

dictionaries.$name.tsx callsite:
  - State: drawerSearch, drawerOnlyFilled, drawerCount {visible, total}
  - Reset on drawer close
  - RecordDrawer.toolbar prop wired только в edit mode (create — все поля
    empty, 'только заполненные' даст 0/0)
  - SchemaDrivenForm receives все три filter props

Result: user может typing 'mass' в drawer search → видит только mass_kg /
data_mass / etc.; toggle 'только заполненные' → hide unused optional fields.

2) RECORDS TABLE RESPONSIVE COLUMN HIDING (handoff line 466)
Records table в dictionaries.$name.tsx применяет hideBelow API из MR !59:
  - businessKey: всегда visible
  - name/code: hideBelow='md' (768px)
  - extra schema columns: hideBelow='lg' (1024px)
  - scope badge: hideBelow='sm' (640px)
  - validFrom: hideBelow='lg'
  - actions: всегда visible

На mobile 375px только businessKey + actions visible — chrome остаётся
usable. Tablet 768+ adds name/scope. Desktop 1024+ adds schema columns.

Tests: 116 pass.
2026-05-11 17:10:26 +03:00
Zimin A.N. e5572d5346 fix(theme): de-saturate light bg — убрать жёлтый Earth-cream tone
Пользователь: 'этот желтый фон давай уберем'. Светлый bg #fbf8ee
выглядел слишком cream/yellow на staging — особенно на больших areas
страницы (список справочников, hover states).

Color token changes (light theme только; dark не трогаем):
  --color-bg:        #fbf8ee → #fafaf8  (off-white neutral)
  --color-surface-2: #f4eedc → #f2f1ee  (subtle warm grey hover/stripe)
  --color-line:      #e3dccb → #e4e1dc  (de-saturated border)
  --color-line-2:    #efe9d8 → #ecebe7  (subtle inner border)

Brand accents preserved:
  --color-accent: #b05a2e (warm orange-brown) — unchanged
  --color-navy:   #3a2818 (deep brown) — unchanged
  --color-warn / pink / green BG — unchanged (semantic states)

Result: cleaner light theme, professional reading surface. Accent
color по-прежнему даёт warmth для brand identity, но page bg
больше не tints всё жёлтым.
2026-05-11 17:01:54 +03:00
Zimin A.N. 090bff56ce fix(release): drop invalid tarballDir: false config
@semantic-release/npm падал с EINVALIDTARBALLDIR — tarballDir option
должен быть String OR omitted. У нас был false (boolean), что invalid.

Поскольку npmPublish: false (мы НЕ публикуем pkg в npm registry —
private repo), tarballDir не нужен вовсе. Удалили — default behavior
(npm pack идёт в temp dir после bump, но не used при npmPublish:false).

После этого fix semantic-release должен пройти normally:
  - analyze conventional commits с момента v1.2.2
  - bump version в admin-ui/package.json
  - generate CHANGELOG.md
  - commit + tag vX.Y.Z [skip ci]
  - create GitLab Release object

Минимум tag будет v1.3.0 (мы накопили 10+ feat: с момента v1.2.2).
2026-05-11 16:57:19 +03:00
Zimin A.N. 155c70e23c feat(drawer): all-sections layout с chips strip per handoff prototype
Handoff Screen 3 RecordDrawer показывает sections подряд с chips strip
для quick jump, не tabs (currently SchemaDrivenForm has 3 tabs).

SchemaDrivenForm:
  - New optional prop layout: 'tabs' (default, legacy) | 'sections'
  - В sections mode:
    * Section chips strip на верху (sticky top-0) вместо Tabs
    * Chip = bucket name + field count в Mono
    * Click chip → scrollIntoView к section
    * Все 3 buckets рендерятся подряд (visible одновременно)
    * Каждая section получает sticky h3 cap header + scroll-mt-12
    * z-indexed sticky: chips strip = 10, section headers = 5
  - В tabs mode: backward-compat без изменений

RecordDrawer callsite (dictionaries.$name.tsx):
  - Передаёт layout='sections' в SchemaDrivenForm (create + edit)
  - Существующий tabs API остаётся для test'ов которые используют default

Layout matches handoff Screen 3 prototype:
  [chips strip sticky]
  [section: Основное]
   field grid 2-col
  [section: Описание (i18n)]
   localized fields
  [section: Дополнительно]
   optional fields grid

Future Phase B refactor: backend x-section schema metadata (open question
#5) разблокирует per-property sections (вместо bucketing). Текущий
fallback bucketing (identity/description/extra) достаточен для MVP.

Tests: 116 pass (test использует default 'tabs' layout, не разломан).
2026-05-11 16:37:38 +03:00
Zimin A.N. a57cf520a4 feat(editor): left info panel + 3-col layout per handoff prototype
Handoff prototype design/compact.html показывает editor как 3-col layout:
[Sidebar 220 (global nav)] [InfoPanel 220 (dict metadata)] [main content].
Текущая implementation была 2-col (nav + everything).

NEW src/components/editor/EditorInfoPanel.tsx:
  - Scope badge (PUBLIC/INTERNAL/RESTRICTED) — top
  - ОПИСАНИЕ section — caption + dict.description body
  - Metadata 2x2 grid: Bundle / Версия / Записей / Локали
    (mono text-ink-2, cap labels)
  - СВЯЗИ section с двумя группами:
    → ссылается  outgoing FK list (name links к /dictionaries/$name)
    ← используют incoming refBy list (deduplicated sourceDict names)
  - sticky lg:top-2 self-start чтобы panel оставалась видна при scroll
  - lg:max-h-[calc(100vh-7rem)] overflow-y-auto если metadata высокий

src/routes/dictionaries.$name.tsx:
  - Обернул содержимое (banner + tabs + tab content) в:
    <div className='grid grid-cols-1 lg:grid-cols-[220px_1fr] gap-4 lg:gap-6'>
      <EditorInfoPanel ... />
      <div>{banner + tabs + content}</div>
    </div>
  - На <lg переключается в stacked (info above content) — single column
    благодаря grid-cols-1.

PageHeader остаётся выше grid (full-width breadcrumb + title + actions).
Action buttons (AOI / Time-travel / Schema edit / Создать) живут в
PageHeader.actions slot — handoff prototype показывает их в info panel,
но рядом с title лучше discoverable. Может уйти в info panel в future
refactor.

Tests: 116 pass. TS strict clean.
2026-05-11 16:33:40 +03:00
Zimin A.N. f43ce5563a feat(catalog): row-based table per handoff prototype design/compact.html
Refactor каталога с card grid → compact row table. Handoff README line
46 явно говорит 'clicking any dictionary row in the catalog' — наша cards
implementation diverged от прототипа.

What's new:
- DictionaryListTable — single flat table (bundle стал column, не группа)
- DictRow — compact tr с scope dot prefix + title + truncated desc
- 8 columns per prototype: name / id / bundle / scope / records / → / ← / updated
- Responsive column hiding via hideBelow-style breakpoints:
  - id: hidden <md
  - bundle: hidden <lg
  - scope: hidden <sm
  - records: hidden <md
  - → ←: hidden <lg
  - updated: hidden <xl
- На mobile <640px показано только name column (с inline scope dot и desc)
- Row click → navigate к editor; Enter/Space keyboard accessible (role=link)

Removed:
- DictCard component (card layout)
- FkChip component (FK chips на cards — теперь just counts)
- SCOPE_STRIP (vertical 3px strip — заменён на inline scope dot)
- groupByBundle usage (bundle стал column, не group section)
- MAX_REFBY_CHIPS const

Note: outgoing FK count (→) пока показывает '—' — требует schemaJson per-dict
fetch (40+ requests). Batch endpoint GET /dictionaries/graph (handoff open
question #2) разблокирует это. Текущий incoming refBy через useDictionary-
Dependents работает per row.

Tests: 116 pass. TS strict clean.
2026-05-11 16:30:31 +03:00
Zimin A.N. d4000ddd3d feat(drawer): sticky toolbar API per handoff Screen 3 line 279
RecordDrawer теперь принимает optional toolbar prop:
  - search (string) — field name filter
  - onlyFilled (boolean) — show only filled fields toggle
  - counterVisible/Total (number) — 'N / M полей' caption

Sticky position между header и body, h=44 per handoff style. Toolbar
rendered только если caller передал. SchemaDrivenForm callsite (записать
filter в каждое FieldRenderer) — separate follow-up, требует refactor
form internals (currently 3 buckets identity/description/extra).

Section anchor chips + wide-mode ToC rail — deferred до backend
x-section schema metadata (CEO open question #5 в handoff).
2026-05-11 16:02:11 +03:00