feat(tradein/v2): CacheView history + PDF + quota + address autocomplete (FE-5) #2052

Merged
lekss361 merged 1 commit from feat/tradein-v2-fe5-cache into main 2026-06-28 13:15:18 +00:00
Owner

Closes #2042 · завершает FE-wiring /trade-in/v2 (#2036). Тот же mappers-паттерн.

Что

  • Предыдущие оценки (CacheView): новый useEstimateHistory (GET /history) → mapCache → список оценок (адрес/время/статус по 24h-TTL) + KPI FE-дерайв из /history (всего / средняя цена / повторные адреса %), НЕ из глобального /cache-stats.
  • PDF (HeroBar): «СКАЧАТЬ PDF-ОТЧЁТ» → /estimate/{id}/pdf; href UUID-gated + safeUrl scheme-check; disabled когда нет оценки.
  • Квота (TopNav): «Мои отчёты» ← useQuota.used (reused hook), fallback 0 (не фабрикованное 128).
  • Автокомплит адреса (ParamsPanel): debounced useGeocodeSuggest (GET /geocode/suggest?q=, ЕКБ viewbox) → дропдаун; выбор подставляет адрес + захватывает lat/lon в submit (сбрасывается при ручной правке). Без useEffect-for-HTTP (таймер + TanStack enabled>=3).
  • page.tsx: invalidate history+quota после новой оценки; hydration-safe PDF-линк за mounted-флагом (urlId SSR-null / client-uuid). FE-1..4 не тронуты.

Verify

  • next build зелёный (/v2 39.6 kB).
  • tsx-харнесс прогнал mapCache против реального /history (10 оценок): ВСЕГО 10 / СРЕДНЯЯ 8,85 млн / ПОВТОРНЫЕ 50%, статусы свежий/устарел, null→graceful.
  • code-reviewer: ⚠️ после 2 фиксов (hydration mismatch на restore-by-id + fallback счётчика отчётов).
  • Бэкенд-shape сверены live: /history (median_price, area_m2 string), /geocode/suggest ({items:[{label,full_address,lat,lon,kind}]}).
  • Визуальная проверка дропдауна автокомплита/PDF — за QA-окном (Playwright CDP-браузер недоступен в сессии).

TODO BE-1 (#2043): колонка «ИСТОЧНИКОВ N/7» в CacheView (нет sources_used в /history).

Closes #2042 · завершает FE-wiring `/trade-in/v2` (#2036). Тот же mappers-паттерн. ## Что - **Предыдущие оценки** (`CacheView`): новый `useEstimateHistory` (GET `/history`) → `mapCache` → список оценок (адрес/время/статус по 24h-TTL) + KPI **FE-дерайв из /history** (всего / средняя цена / повторные адреса %), НЕ из глобального `/cache-stats`. - **PDF** (`HeroBar`): «СКАЧАТЬ PDF-ОТЧЁТ» → `/estimate/{id}/pdf`; href **UUID-gated + safeUrl** scheme-check; disabled когда нет оценки. - **Квота** (`TopNav`): «Мои отчёты» ← `useQuota.used` (reused hook), fallback `0` (не фабрикованное 128). - **Автокомплит адреса** (`ParamsPanel`): debounced `useGeocodeSuggest` (GET `/geocode/suggest?q=`, ЕКБ viewbox) → дропдаун; выбор подставляет адрес + захватывает `lat/lon` в submit (сбрасывается при ручной правке). Без `useEffect`-for-HTTP (таймер + TanStack `enabled>=3`). - `page.tsx`: invalidate history+quota после новой оценки; **hydration-safe** PDF-линк за `mounted`-флагом (urlId SSR-null / client-uuid). FE-1..4 не тронуты. ## Verify - `next build` зелёный (/v2 39.6 kB). - tsx-харнесс прогнал `mapCache` против реального `/history` (10 оценок): ВСЕГО 10 / СРЕДНЯЯ 8,85 млн / ПОВТОРНЫЕ 50%, статусы свежий/устарел, `null`→graceful. - `code-reviewer`: ⚠️→✅ после 2 фиксов (hydration mismatch на restore-by-id + fallback счётчика отчётов). - Бэкенд-shape сверены live: `/history` (`median_price`, `area_m2` string), `/geocode/suggest` (`{items:[{label,full_address,lat,lon,kind}]}`). - Визуальная проверка дропдауна автокомплита/PDF — за QA-окном (Playwright CDP-браузер недоступен в сессии). TODO BE-1 (#2043): колонка «ИСТОЧНИКОВ N/7» в CacheView (нет `sources_used` в `/history`).
lekss361 added 1 commit 2026-06-28 13:15:09 +00:00
feat(tradein/v2): CacheView history + PDF link + quota + address autocomplete (#2042)
All checks were successful
CI / changes (pull_request) Successful in 7s
CI / backend-tests (pull_request) Has been skipped
CI / frontend-tests (pull_request) Has been skipped
CI / openapi-codegen-check (pull_request) Has been skipped
81ae21ada9
FE-5, last FE wiring on the mappers pattern. Closes #2042.
- New hooks (lib/trade-in-api.ts): useEstimateHistory (GET /history), useGeocodeSuggest
  (GET /geocode/suggest?q=&limit=, debounced, enabled>=3 chars); useQuota reused.
- types/trade-in.ts: EstimateHistoryItem (area_m2 string, median_price), GeocodeSuggestion.
- mappers.ts: mapCache(history) -> {rows: CacheRow[], kpis: CacheKpi[]} — per-row status
  by 24h TTL; KPIs FE-derived from /history (всего/средняя цена/повторные %), NOT the
  global /cache-stats.
- CacheView: real previous-estimates list. ParamsPanel: address autocomplete dropdown →
  captures lat/lon into submit (cleared on manual edit). HeroBar: «Скачать PDF» → /estimate/
  {id}/pdf, UUID-gated + safeUrl scheme check + disabled when no estimate. TopNav: «Мои
  отчёты» from quota.used/history. page.tsx: invalidate history+quota on new estimate.
- Hydration-safe: PDF link gated behind a mounted flag (urlId is SSR-null/client-uuid).
- FE-1..4 untouched.

Verified: next build green (/v2 39.6 kB); tsx harness ran mapCache vs real /history (10
items: ВСЕГО 10 / СРЕДНЯЯ 8,85 млн / ПОВТОРНЫЕ 50%, statuses, null graceful).
code-reviewer APPROVE after hydration + reports-fallback fixes.
lekss361 merged commit a100f03aa7 into main 2026-06-28 13:15:18 +00:00
lekss361 deleted branch feat/tradein-v2-fe5-cache 2026-06-28 13:15:18 +00:00
Sign in to join this conversation.
No reviewers
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference: lekss361/gendesign#2052
No description provided.