# Alpine UI Integration Plan

## 1. Назначение документа

Этот документ фиксирует, как Alpine UI в `apps/ui` подключается к реальному backend.

Его задача:

- разложить UI по страницам;
- показать, что уже поддержано текущим backend;
- зафиксировать отсутствующие endpoint-ы и контрактные разрывы;
- определить порядок интеграции без хаотичных правок.

## 2. Текущее состояние

Сейчас `apps/ui` уже является основной Alpine.js UI-кодовой базой.

Важно:

- `apps/ui` является единственной рабочей UI-кодовой базой;
- новый UI пока опирается на `localStorage`, mock JSON и локальные сценарии;
- backend уже поддерживает `workspace`, `operations`, `agents`, `platform access`, `logs`, `usage`, но не все UI-flow закрыты полностью.

## 3. Принципы интеграции

- сначала подключаем страницы, уже совпадающие с текущим backend-контрактом;
- затем добавляем недостающие endpoint-ы под уже существующие UI-flow;
- только после этого убираем mock JSON и `localStorage`-костыли;
- если UI противоречит текущему backend, приоритет у целевой продуктовой модели, но конфликт должен быть разобран явно.

## 4. Page-by-page integration matrix

### 4.1. Operations catalog

UI-файлы:

- `apps/ui/index.html`
- `apps/ui/js/catalog.js`

Что UI хочет:

- список операций;
- фильтры по protocol/category/agent/status;
- карточки верхних метрик;
- переход в wizard create/edit;
- удаление/архивирование;
- отображение агентных привязок.

Что уже можно подключить:

- `GET /api/admin/workspaces/{workspace_id}/operations`
- `GET /api/admin/workspaces/{workspace_id}/agents`
- `GET /api/admin/workspaces/{workspace_id}/usage`
- `PATCH /api/admin/workspaces/{workspace_id}/operations/{operation_id}`
- `DELETE /api/admin/workspaces/{workspace_id}/operations/{operation_id}`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/archive`

Что еще не хватает:

- frontend data adapter, который заменит mock merge на реальные `items/page/page_size/total`;
- wiring server-side filters `protocol/category/agent/status/search`;
- переключение карточек верхних метрик с seeded summary на реальный usage payload.

Что убрать из UI после интеграции:

- `crank_ops_overrides` в `localStorage`
- merge поверх `data/operations.json`
- локальный tombstone/delete flow

Простой итог:

- эту страницу можно интегрировать первой;
- backend уже отдает server-side category, usage summary и agent refs;
- каталог уже может работать через реальные `list/delete/edit` вызовы;
- следующий шаг здесь только в server-side paging и остальных catalog actions; `target_url` и `target_action` теперь должны приходить из backend summary.

### 4.2. Wizard

UI-файлы:

- `apps/ui/html/wizard/index.html`
- `apps/ui/html/wizard/step*.html`
- `apps/ui/js/wizard.js`

Что UI хочет:

- create operation;
- edit operation;
- draft/save flow;
- test run;
- publish;
- загрузку samples;
- генерацию draft mapping;
- gRPC descriptor upload;
- import/export.

Что уже можно подключить:

- `POST /api/admin/workspaces/{workspace_id}/operations`
- `GET /api/admin/workspaces/{workspace_id}/operations/{operation_id}`
- `PATCH /api/admin/workspaces/{workspace_id}/operations/{operation_id}`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/versions`
- `GET /api/admin/workspaces/{workspace_id}/operations/{operation_id}/versions/{version}`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/archive`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/test-runs`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/samples/input-json`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/samples/output-json`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/drafts/generate`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/descriptors/proto`
- `POST /api/admin/workspaces/{workspace_id}/operations/{operation_id}/descriptors/descriptor-set`
- `GET /api/admin/workspaces/{workspace_id}/operations/{operation_id}/grpc/services`
- `GET /api/admin/workspaces/{workspace_id}/operations/{operation_id}/export`
- `POST /api/admin/workspaces/{workspace_id}/operations/import`

Что еще не хватает:

- дальнейший UX polish вокруг gRPC discovery, потому что server reflection сознательно заменен на descriptor-driven live flow;
- возможные smoke tests для `wizard`, чтобы закрепить уже подключенный live contract.

Что убрать из UI после интеграции:

- `sessionStorage`-передачу `wizard_edit`
- draft-overrides через `localStorage`
- локальное создание operation без backend

Простой итог:

- wizard почти готов для реального backend;
- текущий workspace для wizard уже приходит из auth session, а не только из client-side `localStorage`;
- это основной экран второй очереди после catalog;
- базовый create/edit draft flow уже можно посадить на live `create/get version/update` endpoints;
- следующий разрыв здесь - test/publish/import/export wiring и полноценный gRPC descriptor-set lifecycle.

### 4.3. Agents

UI-файлы:

- `apps/ui/html/agents.html`
- `apps/ui/js/agents.js`

Что UI хочет:

- список агентов;
- create/edit agent;
- выбор операций для агента;
- publish agent;
- MCP endpoint на агента;
- calls today / operation count / key count.

Что уже можно подключить:

- `GET /api/admin/workspaces/{workspace_id}/agents`
- `POST /api/admin/workspaces/{workspace_id}/agents`
- `GET /api/admin/workspaces/{workspace_id}/agents/{agent_id}`
- `PATCH /api/admin/workspaces/{workspace_id}/agents/{agent_id}`
- `DELETE /api/admin/workspaces/{workspace_id}/agents/{agent_id}`
- `POST /api/admin/workspaces/{workspace_id}/agents/{agent_id}/bindings`
- `POST /api/admin/workspaces/{workspace_id}/agents/{agent_id}/publish`
- `POST /api/admin/workspaces/{workspace_id}/agents/{agent_id}/unpublish`
- `POST /api/admin/workspaces/{workspace_id}/agents/{agent_id}/archive`
- `GET /api/admin/workspaces/{workspace_id}/usage`

Что еще не хватает:

- `POST /api/admin/workspaces/{workspace_id}/agents/{agent_id}/versions`
- `DELETE /api/admin/workspaces/{workspace_id}/agents/{agent_id}/bindings/{operation_id}`

Отдельный конфликт:

- UI считает, что агент можно редактировать прямо как рабочую сущность;
- backend пока ближе к publish-модели с version snapshot;
- нужно решить, edit агента мутирует draft напрямую или всегда создает новую version.

Простой итог:

- базовый live flow уже закрыт: list/create/edit/delete/bind/publish/unpublish/archive работают через backend;
- `GET /agents` уже отдает `calls_today`, `key_count`, `operation_count`, `operation_ids` и `mcp_endpoint`;
- следующий реальный разрыв здесь уже не в CRUD, а в richer version lifecycle поверх этих состояний.

### 4.4. API Keys

UI-файлы:

- `apps/ui/html/api-keys.html`
- `apps/ui/js/api-keys.js`

Что UI хочет:

- список platform API keys;
- create;
- one-time reveal;
- revoke;
- delete;
- scopes.

Что уже можно подключить:

- `GET /api/admin/workspaces/{workspace_id}/platform-api-keys`
- `POST /api/admin/workspaces/{workspace_id}/platform-api-keys`
- `POST /api/admin/workspaces/{workspace_id}/platform-api-keys/{key_id}/revoke`
- `DELETE /api/admin/workspaces/{workspace_id}/platform-api-keys/{key_id}`

Что еще не хватает:

- если захотим richer UX, можно добавить server-side pagination и фильтрацию по статусу.

Отдельный конфликт:

- одноразовый `secret` доступен только в create-response, а list endpoint возвращает только metadata;
- это уже совпадает с backend, но UX нельзя случайно перевести в режим “показывать ключ повторно”.

Простой итог:

- страница уже сажается на текущий backend без новых ручек;
- live `list/create/revoke/delete` можно считать закрытым;
- `last_used_at` теперь обновляется через успешную machine-auth аутентификацию в `mcp-server`;
- следующий реальный шаг здесь только в polishing вокруг audit trail и richer filtering.

### 4.5. Logs

UI-файлы:

- `apps/ui/html/logs.html`
- `apps/ui/js/logs.js`

Что UI хочет:

- список invocation logs;
- фильтры;
- detail row expansion;
- live refresh;
- status/error/duration.

Что уже можно подключить:

- `GET /api/admin/workspaces/{workspace_id}/logs`
- `GET /api/admin/workspaces/{workspace_id}/logs/{log_id}`

Что еще не хватает:

- optional pagination и server-driven cursor, если логи начнут расти;
- отдельный streaming endpoint, если polling перестанет устраивать;
- richer detail metadata, если захотим показывать trace/request ids отдельными виджетами

Простой итог:

- страница уже подключена к live `logs` API;
- текущий `live mode` реализован через polling и этого достаточно для текущего этапа.

### 4.6. Usage

UI-файлы:

- `apps/ui/html/usage.html`
- `apps/ui/js/usage.js`

Что UI хочет:

- верхние summary cards;
- timeline;
- breakdown по operations;
- p50/p95/p99;
- breakdown по agents;
- CSV export.

Что уже можно подключить:

- `GET /api/admin/workspaces/{workspace_id}/usage`
- `GET /api/admin/workspaces/{workspace_id}/usage/operations/{operation_id}`
- `GET /api/admin/workspaces/{workspace_id}/usage/agents/{agent_id}`

Что еще не хватает:

- если понадобится agent-specific usage drilldown, для него нужен отдельный экран или таб;
- если понадобится server-side export, можно добавить отдельный CSV endpoint позже;
- quota/limits пока не являются частью backend модели, поэтому страница честно показывает traffic share

Простой итог:

- usage page уже подключена к live `usage` API;
- CSV export сейчас делается на клиенте и этого достаточно для текущего этапа.

### 4.7. Workspace setup

UI-файлы:

- `apps/ui/html/workspace-setup.html`
- `apps/ui/js/workspace-setup.js`
- `apps/ui/js/workspace.js`

Что UI хочет:

- create workspace;
- edit workspace;
- список участников;
- приглашения;
- смену текущего workspace.

Что уже можно подключить:

- `GET /api/admin/workspaces`
- `POST /api/admin/workspaces`
- `GET /api/admin/workspaces/{workspace_id}`
- `PATCH /api/admin/workspaces/{workspace_id}`
- `GET /api/admin/workspaces/{workspace_id}/members`
- `PATCH /api/admin/workspaces/{workspace_id}/members/{user_id}`
- `DELETE /api/admin/workspaces/{workspace_id}/members/{user_id}`
- `GET /api/admin/workspaces/{workspace_id}/invitations`
- `POST /api/admin/workspaces/{workspace_id}/invitations`
- `DELETE /api/admin/workspaces/{workspace_id}/invitations/{invitation_id}`
- `GET /api/admin/workspaces/{workspace_id}/export`
- `DELETE /api/admin/workspaces/{workspace_id}`

Что еще не хватает:

- finer-grained permission matrix beyond current `owner/admin` management rules.

Отдельный конфликт:

- memberships, role-management и invitations уже live;
- `settings` page не должна дублировать этот flow, пока у нее нет своего backend-контракта

Простой итог:

- `workspace-setup` уже подключен к live backend;
- create/edit workspace, memberships, invitations, export и delete работают;
- текущий workspace уже синхронизируется через auth session и используется всеми live страницами.

### 4.8. Settings

UI-файлы:

- `apps/ui/html/settings.html`
- `apps/ui/js/settings.js`

Что UI хочет:

- профиль пользователя;
- security/preferences;
- workspace settings;
- language switcher.

Что уже можно подключить:

- `GET /api/auth/session`
- `GET /api/auth/profile`
- `PATCH /api/auth/profile`
- `POST /api/auth/current-workspace`
- `POST /api/auth/password`
- workspace block через `GET /api/admin/workspaces/{workspace_id}`
- `PATCH /api/admin/workspaces/{workspace_id}`

Что еще не хватает:

- preferences endpoint;
- полноценный advanced security model (`2FA`, passkeys, session inventory).

Отдельный конфликт:

- UI исторически притворялся, что `2FA`, passkeys и active sessions уже реализованы;
- backend пока дает только live `profile` и `password change`, без advanced security lifecycle;
- поэтому страница должна честно разделять:
  - live `profile`;
  - live `password change`;
  - read-only/security roadmap блоки без fake data.

Простой итог:

- workspace block уже live;
- profile и password change уже live;
- notifications остаются локальным placeholder;
- страницу теперь можно считать частично интегрированной без ложных mock-сценариев.

### 4.9. Login

UI-файлы:

- `apps/ui/html/login.html`
- `apps/ui/js/login.js`

Что UI хочет:

- app-level sign in;
- mock SSO button;
- user session.

Что уже есть реально:

- login screen и mock redirect flow

Что уже есть:

- session auth backend;
- `POST /api/auth/login`;
- `POST /api/auth/logout`;
- `GET /api/auth/session`;
- protected page guard через backend session.

Простой итог:

- login уже перешел на live backend flow;
- защищенные страницы проверяют server-side session;
- `localStorage` больше не должен быть source of truth для auth.

## 5. Отдельные UI-vs-backend конфликты

### 5.1. Login vs Basic Auth

Конфликт закрыт. UI использует встроенный login, backend перешел на app-level session auth.

Решение:

- использовать `POST /api/auth/login`, `POST /api/auth/logout`, `GET /api/auth/session`;
- хранить auth state в `HttpOnly` cookie;
- использовать `localStorage` только как UI mirror для display state и не считать его source of truth.

### 5.2. Agent draft/edit lifecycle

UI редактирует агента напрямую, backend идет к version/publish модели.

Решение:

- зафиксировать draft agent как редактируемую сущность;
- publish должен фиксировать snapshot;
- UI не должен скрывать разницу между draft и published.

### 5.3. API key scopes

UI вводит scope `deploy`, backend пока не отражает полноценную deploy-подсистему.

Решение:

- либо урезать scope-тексты;
- либо позже расширять platform access под реальный deploy scope.

### 5.4. Workspace switching

UI хранит current workspace в auth session и использует `localStorage` только как cache/fallback.

Решение:

- backend хранит `current_workspace_id` в user session;
- `POST /api/auth/current-workspace` переключает активный workspace;
- клиент использует `localStorage` только как cache/fallback для shell state.

## 6. Порядок интеграции

### Wave 1

- `Operations catalog` — completed
- `Wizard` — completed

### Wave 2

- `Agents` — completed
- `API Keys` — completed

### Wave 3

- `Logs` — completed
- `Usage` — completed

### Wave 4

- `Workspace setup` — completed
- частичный `Settings` — completed

### Wave 5

- `Login` — completed
- полноценный session/auth layer — completed

## 7. Ближайший практический шаг

Следующий рабочий этап:

- добить live `Settings` без заглушек для profile/security;
- закрыть `workspace access` lifecycle (`roles`, `member removal`, `delete/export workspace`);
- пройти stabilization pass по Alpine UI и убрать оставшиеся client-side fallback patterns.
