docs(frontend): sync frontend docs with current state

This commit is contained in:
Sergey Krylov 2026-06-24 07:49:30 +03:00
parent 41668ea452
commit afa0ec05e7
9 changed files with 60 additions and 97 deletions

1
.gitignore vendored
View File

@ -11,3 +11,4 @@ vite.config.js
apps/docs/.docusaurus/
apps/docs/build/
.idea
.playwright-mcp

View File

@ -13,7 +13,7 @@ npm run codegen -w apps/frontend
Выполняет:
```bash
openapi-typescript http://localhost:3000/api/docs-json -o src/api/types.ts
openapi-typescript http://localhost:3000/api/docs-json -o src/shared/api/types.ts
```
### Требования
@ -23,7 +23,7 @@ openapi-typescript http://localhost:3000/api/docs-json -o src/api/types.ts
### Результат
- `apps/frontend/src/api/types.ts` — сгенерированные типы `paths` и `operations`
- `apps/frontend/src/shared/api/types.ts` — сгенерированные типы `paths` и `operations`
- Live Swagger JSON на `http://localhost:3000/api/docs-json` остаётся источником OpenAPI-контракта
### Проверка артефактов
@ -39,4 +39,4 @@ npm run test -w apps/backend -- src/openapi-artifacts.spec.ts
### Ручные типы
Помимо codegen, используются рукописные типы в `apps/frontend/src/api/responses.ts`. Они не полностью соответствуют codegen'овым и поддерживаются вручную.
Помимо codegen, используются public DTO alias-ы в `apps/frontend/src/shared/api/index.ts`. Они не полностью соответствуют codegen'овым и поддерживаются вручную.

View File

@ -40,7 +40,7 @@
| `npm run dev -w apps/frontend` | `vite` |
| `npm run build -w apps/frontend` | `tsc -b && vite build` |
| `npm run preview -w apps/frontend` | `vite preview` |
| `npm run codegen -w apps/frontend` | `openapi-typescript` из Swagger → `src/api/types.ts` |
| `npm run codegen -w apps/frontend` | `openapi-typescript` из Swagger → `src/shared/api/types.ts` |
| `npm run lint -w apps/frontend` | ESLint для `src/**/*.{ts,tsx}` |
| `npm run test -w apps/frontend` | Frontend Vitest suite |

View File

@ -1,8 +1,8 @@
# API client
## Клиент (`api/client.ts`)
## Клиент (`shared/api/kyClient.ts`)
Использует нативный `fetch` с единой обёрткой `request<T>`.
Использует `ky` с единой обёрткой `request<T>`.
```typescript
async function request<T>(
@ -13,9 +13,14 @@ async function request<T>(
```
- Формирует URL из `path` + query params
- Парсит JSON-ответ в `ApiEnvelope<{ data: T, meta: ApiResponseMeta }>`
- Парсит JSON-ответ и нормализует envelope через `normalizeEnvelope()`
- Выбрасывает `Error` при HTTP-ошибке
## Public API (`shared/api/index.ts`)
Публичная точка входа для frontend API — `shared/api/index.ts`. Оттуда экспортируются `request`,
`configureKyAuth`, `getHealth` и DTO alias-ы.
## API functions
| Function | Method | Path |
@ -50,7 +55,7 @@ async function request<T>(
## Типы
Ручные типы ответов в `api/responses.ts`:
Публичные DTO alias-ы в `shared/api/index.ts`:
- `ApiResponseMeta``{ cachedAt, fromCache }`
- `ApiEnvelope<T>``{ data: T, meta: ApiResponseMeta }`
@ -62,4 +67,4 @@ async function request<T>(
- `Portfolio`, `PortfolioDetail`, `Position`, `PortfolioSummary`, `AnalyticsResponse`
- `ScreenerItem`, `ScreenerResult`
Codegen-типы из OpenAPI в `api/types.ts` (генерируются через `npm run codegen`).
Codegen-типы из OpenAPI в `shared/api/types.ts` (генерируются через `npm run codegen -w apps/frontend`).

View File

@ -24,6 +24,11 @@
- broker-event hooks: `entities/broker-event/index.ts`
- session hooks: `entities/session/index.ts`
## Test helpers
- `renderWithProviders``shared/lib/test/test-utils.tsx`
- `TestSessionProvider``shared/lib/test/TestSessionProvider.tsx`
## Конфигурация Query
```typescript
@ -40,9 +45,9 @@ const queryClient = new QueryClient({
## Паттерн hook
1. Хук вызывает domain API helper из `entities/*/api/` или `shared/api/client`
1. Хук вызывает domain API helper из `entities/*/api/` или `shared/api`
2. Извлекает `res.data` (ответ API обёрнут в `{ data, meta }`)
3. Типизируется через response types из `shared/api/responses.ts`
3. Типизируется через response types из `shared/api`
```typescript
export function useStock(secid: string) {

View File

@ -5,10 +5,10 @@ React SPA, собранная с Vite.
## Технологический стек
- React 18
- react-router-dom v6
- @tanstack/react-router
- TanStack Query v5
- lightweight-charts v4
- openapi-fetch (с рукописными типами `responses.ts`)
- ky + OpenAPI-generated types
- Vitest + Testing Library + MSW
- Vite 5
@ -21,14 +21,15 @@ Published-структура ниже описывает primary FSD entrypoints
apps/frontend/src/
├── main.tsx # Точка входа
├── app/ # FSD app layer
│ ├── App.tsx # BrowserRouter → AppRoutes
│ ├── App.tsx # RouterProvider → router
│ ├── index.ts # barrel
│ ├── providers/
│ │ ├── AppProviders.tsx # QueryClientProvider + SessionProvider
│ │ ├── SessionProvider.tsx
│ │ └── index.ts
│ ├── routing/
│ │ ├── AppRoutes.tsx # Все маршруты
│ │ ├── routeTree.tsx # TanStack Router tree
│ │ ├── router.ts # router export
│ │ ├── ProtectedRoute.tsx
│ │ └── index.ts
│ └── layouts/
@ -37,7 +38,10 @@ apps/frontend/src/
├── features/ # FSD features
│ └── screener/ # Скринер ценных бумаг (api, model, ui)
├── shared/
│ ├── api/ # shared API client, response types, generated OpenAPI types
│ ├── api/ # shared API client, public API aliases, generated OpenAPI types
│ ├── config/ # env config
│ ├── lib/
│ │ └── test/ # shared test helpers
│ └── ui/ # shared UI primitives without domain logic
├── entities/ # FSD business entities
│ ├── session/ # Auth/session (api, model)
@ -79,13 +83,6 @@ apps/frontend/src/
│ ├── broker-events/ # FSD: page entrypoint
│ ├── broker-positions/ # FSD: page entrypoint
│ └── broker-operations/ # FSD: page entrypoint
├── test/
│ ├── factories.ts # Фабрики тестовых данных
│ ├── handlers.ts # MSW handlers
│ ├── server.ts # MSW server
│ ├── test-utils.tsx # Обёртка рендера
│ ├── setup.ts # Настройка jsdom
│ └── README.md
└── styles.css
```
@ -96,9 +93,9 @@ apps/frontend/src/
Создан `app/` слой FSD, в который перенесены инфраструктурные модули:
- `app/providers/` — композиция провайдеров (SessionProvider, QueryClientProvider)
- `app/routing/`маршруты и ProtectedRoute
- `app/routing/`route tree и guard'ы
- `app/layouts/` — AppLayout (шапка + Outlet)
- `app/App.tsx`BrowserRouter → AppRoutes
- `app/App.tsx`RouterProvider → router
### entities
@ -106,7 +103,7 @@ apps/frontend/src/
| Сущность | api | model | ui |
|----------|-----|-------|----|
| `session` | login, register, refresh, logout, getMe, updateProfile | SessionContext, useSession | — |
| `session` | login, register, refresh, logout, getMe, updateProfile | useSession, useSessionStore | — |
| `stock` | getStock, getStockCandles, getStockDividends | useStock, useStockCandles, useStockDividends | — |
| `bond` | getBond, getBondCandles | useBond, useBondCandles | — |
| `portfolio` | CRUD портфелей и позиций, аналитика | usePortfolio, usePortfolios, usePortfolioAnalytics, usePortfolioMutations, usePositionMutations | — |
@ -130,6 +127,13 @@ apps/frontend/src/
- `portfolio-card`, `portfolio-form`, `portfolio-summary`, `portfolio-analytics` — UI портфелей
- `share-positions-table`, `bond-positions-table` — таблицы позиций
### test helpers
- `shared/lib/test/test-utils.tsx``renderWithProviders`
- `shared/lib/test/handlers.ts` — MSW handlers для тестов
- `shared/lib/test/server.ts` — MSW server
- `shared/lib/test/factories.ts` — тестовые фабрики
### pages
- `pages/home`, `pages/stock`, `pages/bond` — FSD page entrypoints для market pages

View File

@ -1,21 +1,21 @@
# Маршруты
Source of truth для маршрутов: `apps/frontend/src/app/routing/AppRoutes.tsx`.
Source of truth для маршрутов: `apps/frontend/src/app/routing/routeTree.tsx`.
| Path | Component | Доступ | Описание |
|---|---|---|---|
| `/` | `HomePage` from `pages/home` | Public | Главная страница |
| `/stocks/:secid` | `StockPage` from `pages/stock` | Public | Страница акции |
| `/bonds/:secid` | `BondPage` from `pages/bond` | Public | Страница облигации |
| `/stocks/$secid` | `StockPage` from `pages/stock` | Public | Страница акции |
| `/bonds/$secid` | `BondPage` from `pages/bond` | Public | Страница облигации |
| `/screener` | `ScreenerPage` | Public | Скринер ценных бумаг |
| `/login` | `LoginPage` | Public | Вход |
| `/register` | `RegisterPage` | Public | Регистрация |
| `/profile` | `ProfilePage` | Protected | Профиль текущего пользователя |
| `/portfolios` | `PortfoliosListPage` | Protected | Список портфелей |
| `/portfolios/:id` | `PortfolioDetailPage` | Protected | Детальная страница портфеля |
| `/portfolios/$id` | `PortfolioDetailPage` | Protected | Детальная страница портфеля |
| `/broker` | `BrokerAccountsPage` from `pages/broker-accounts` | Protected | Список брокерских счетов |
| `/broker/:accountId` | `BrokerAccountLayout` + nested pages | Protected | Детальная область брокерского счёта |
| `/broker/:accountId/events` | `BrokerEventsPage` from `pages/broker-events` | Protected | Календарь событий и выплат |
| `/broker/$accountId` | `BrokerAccountLayout` + nested pages | Protected | Детальная область брокерского счёта |
| `/broker/$accountId/events` | `BrokerEventsPage` from `pages/broker-events` | Protected | Календарь событий и выплат |
Все page entrypoints живут в FSD-слоях:
@ -37,67 +37,12 @@ Source of truth для маршрутов: `apps/frontend/src/app/routing/AppRou
## Структура маршрутов
```tsx
<Routes>
<Route element={<AppLayout />}>
<Route path="/" element={<HomePage />} />
<Route path="/stocks/:secid" element={<StockPage />} />
<Route path="/bonds/:secid" element={<BondPage />} />
<Route path="/screener" element={<ScreenerPage />} />
<Route path="/login" element={<LoginPage />} />
<Route path="/register" element={<RegisterPage />} />
<Route
path="/profile"
element={
<ProtectedRoute>
<ProfilePage />
</ProtectedRoute>
}
/>
<Route
path="/portfolios"
element={
<ProtectedRoute>
<PortfoliosListPage />
</ProtectedRoute>
}
/>
<Route
path="/portfolios/:id"
element={
<ProtectedRoute>
<PortfolioDetailPage />
</ProtectedRoute>
}
/>
<Route
path="/broker"
element={
<ProtectedRoute>
<BrokerAccountsPage />
</ProtectedRoute>
}
/>
<Route
path="/broker/:accountId"
element={
<ProtectedRoute>
<BrokerAccountLayout />
</ProtectedRoute>
}
>
<Route index element={<BrokerAccountOverviewPage />} />
<Route path="shares" element={<BrokerPositionsPage type="share" title="Акции" />} />
<Route path="bonds" element={<BrokerPositionsPage type="bond" title="Облигации" />} />
<Route path="operations" element={<BrokerOperationsPage />} />
<Route path="events" element={<BrokerEventsPage />} />
</Route>
</Route>
</Routes>
Маршруты собираются через TanStack Router в `routeTree.tsx`.
```
## Композиция страницы событий
Страница `/broker/:accountId/events` собирается из FSD-слоёв:
Страница `/broker/$accountId/events` собирается из FSD-слоёв:
```mermaid
flowchart TB

View File

@ -202,6 +202,13 @@ cash flow, бюджеты, аналитика, прогнозы и автома
состояние и приоритеты.
- Эпик для этой декомпозиции: `Frontend Debt Backlog`.
### Синхронизировать frontend docs
- Привести frontend docs к текущему состоянию после TanStack Router migration, ky-based API client и
shared/lib/test helpers.
- Удалить устаревшие ссылки на `AppRoutes.tsx`, `api/client.ts`, `api/responses.ts` и `src/api/types.ts`.
- Считать `docs/features/frontend-docs-sync` рабочей фичей-синхронизацией, а не исследовательской идеей.
### Исследовать Backend-Driven UI
- Рассматривать BDUI как исследовательскую гипотезу, а не выбранную целевую архитектуру.

View File

@ -83,16 +83,12 @@ Roadmap отражает порядок продуктовой работы, н
## Кандидаты следующих фич
- [ ] [Frontend docs sync](features/frontend-docs-sync/spec.md) — синхронизация frontend docs с текущим состоянием кода.
- [ ] [Frontend infrastructure hardening](features/frontend-infrastructure-hardening/spec.md) — завершение infrastructure/tooling debt.
- [ ] [Frontend shared boundary cleanup](features/frontend-shared-boundary-cleanup/spec.md) — сужение shared/public API и границ слоёв.
- [ ] [Frontend test hygiene](features/frontend-test-hygiene/spec.md) — упрощение и нормализация frontend test infrastructure.
- [ ] [Frontend debt audit and backlog](features/frontend-debt-audit/spec.md) — audit текущего
frontend-техдолга, разделение open items на follow-up фичи, синхронизация inbox/roadmap.
- [ ] [Frontend docs sync](features/frontend-docs-sync/spec.md) — синхронизация inbox/roadmap и
устаревшей frontend-документации.
- [ ] [Frontend infrastructure hardening](features/frontend-infrastructure-hardening/spec.md) —
завершение infrastructure/tooling debt.
- [ ] [Frontend shared boundary cleanup](features/frontend-shared-boundary-cleanup/spec.md) —
сужение shared/public API и границ слоёв.
- [ ] [Frontend test hygiene](features/frontend-test-hygiene/spec.md) — упрощение и нормализация
frontend test infrastructure.
- [ ] [Миграция таблиц на дизайн-систему](features/table-migration/spec.md) — перевести legacy-таблицы
на `DataTable` поверх `TanStack Table`.
- [ ] Аналитика портфеля Phases 23 — дивидендный доход, сравнение с target allocation.