docs(specs): archive api contract resilience remediation
This commit is contained in:
@@ -0,0 +1,36 @@
|
||||
# frontend-data-resilience Specification
|
||||
|
||||
## Purpose
|
||||
|
||||
Определяет, когда frontend сохраняет последний успешный ответ на экране и как
|
||||
сообщает пользователю о неудачном фоновом обновлении без искажения доменных
|
||||
состояний Portfolio.
|
||||
|
||||
## Requirements
|
||||
|
||||
### Requirement: Client Cached Snapshot остаётся доступным при обновлении Accounts и Portfolio
|
||||
Frontend MUST сохранять Client Cached Snapshot списка Brokerage Accounts или
|
||||
Portfolio на экране, если для этого же набора данных уже был успешно получен
|
||||
ответ. Начальная загрузка без такого ответа может показывать блокирующее
|
||||
состояние загрузки. Client Cached Snapshot MUST оставаться видимым во время
|
||||
фонового обновления и после его ошибки; он не является server-side fallback и MUST NOT
|
||||
изменять или интерпретировать поле `Portfolio.isStale`.
|
||||
|
||||
#### Scenario: Список Brokerage Accounts обновляется в фоне
|
||||
- **WHEN** экран Accounts уже показывает Client Cached Snapshot и начинается
|
||||
фоновое обновление того же списка
|
||||
- **THEN** frontend оставляет список видимым и показывает только
|
||||
неблокирующий индикатор обновления
|
||||
|
||||
#### Scenario: Обновление Portfolio завершается ошибкой после успешного ответа
|
||||
- **WHEN** экран Brokerage Account уже показывает Client Cached Snapshot
|
||||
Portfolio, а последующее обновление этого же Portfolio завершается ошибкой
|
||||
- **THEN** frontend сохраняет Portfolio видимым, показывает локализованное
|
||||
неблокирующее предупреждение о показе последних полученных данных и
|
||||
предоставляет повторную попытку обновления
|
||||
|
||||
#### Scenario: Server-side fallback и client cached snapshot различаются
|
||||
- **WHEN** backend возвращает Portfolio с `isStale` либо фоновое обновление
|
||||
Client Cached Snapshot завершается ошибкой
|
||||
- **THEN** frontend отображает соответствующее server-side либо client-side
|
||||
предупреждение независимо, не представляя один вид состояния другим
|
||||
@@ -123,3 +123,40 @@
|
||||
#### Scenario: Выход из настроек
|
||||
- **WHEN** пользователь нажимает logout на `/settings`
|
||||
- **THEN** клиент очищает локальную сессию и cache и направляет пользователя на `/login` независимо от результата сетевого запроса
|
||||
|
||||
### Requirement: Единый HTTP contract успешных auth endpoints
|
||||
Успешные `POST /api/v1/auth/register`, `POST /api/v1/auth/login` и
|
||||
`POST /api/v1/auth/refresh` MUST отвечать HTTP `200`; опубликованный
|
||||
OpenAPI-документ, зафиксированный frontend snapshot и сгенерированные
|
||||
transport types MUST описывать этот же status. Каждая операция сохраняет свои
|
||||
существующие payload, refresh-cookie и session semantics. Logout MUST
|
||||
продолжать отвечать `204`.
|
||||
|
||||
#### Scenario: Успешная регистрация возвращает контрактный status
|
||||
- **WHEN** пользователь отправляет новую валидную регистрацию
|
||||
- **THEN** система устанавливает refresh-cookie, возвращает профиль и access
|
||||
token с HTTP `200`
|
||||
|
||||
#### Scenario: Успешный login или refresh возвращает контрактный status
|
||||
- **WHEN** пользователь успешно входит либо восстанавливает Session
|
||||
- **THEN** система устанавливает или заменяет refresh-cookie, возвращает
|
||||
профиль и access token с HTTP `200`
|
||||
|
||||
### Requirement: Клиент контролируемо завершает неуспешный refresh
|
||||
Frontend MUST обрабатывать HTTP и транспортную ошибку общего refresh flow без
|
||||
необработанного отклонения Promise. При неуспешном cold-start refresh frontend
|
||||
MUST завершить инициализацию как неавторизованный, не сохраняя access token
|
||||
или профиль. При неуспешном refresh после защищённого запроса frontend MUST
|
||||
очистить in-memory session и query cache перед existing navigation to login.
|
||||
|
||||
#### Scenario: Cold-start refresh завершается транспортной ошибкой
|
||||
- **WHEN** приложение запускается без access token и refresh запрос не может
|
||||
получить транспортный response
|
||||
- **THEN** frontend завершается в готовом неавторизованном состоянии без
|
||||
необработанного отклонения Promise и показывает обычный public/login flow
|
||||
|
||||
#### Scenario: Повторный refresh после protected 401 завершается транспортной ошибкой
|
||||
- **WHEN** защищённый API отвечает `401`, а единственный serialised refresh
|
||||
завершается транспортной ошибкой
|
||||
- **THEN** frontend очищает in-memory session и query cache и направляет User
|
||||
в существующий login flow без необработанного отклонения Promise
|
||||
|
||||
Reference in New Issue
Block a user