build 043: finalize Quotes Feed architecture verification
This commit is contained in:
287
docs/migrations/build_042.md
Normal file
287
docs/migrations/build_042.md
Normal file
@@ -0,0 +1,287 @@
|
||||
# Build 042 — Удаление MarketPriceCache
|
||||
|
||||
## Статус
|
||||
|
||||
**Завершён**
|
||||
|
||||
---
|
||||
|
||||
## 1. Цель Build 042
|
||||
|
||||
Целью Build 042 было провести аудит зависимостей legacy-компонента `MarketPriceCache`, определить безопасный способ его удаления и устранить compatibility facade без нарушения работы существующего Quotes Feed, REST fallback, WebSocket runtime и потребителей котировок.
|
||||
|
||||
Основное ограничение миграции:
|
||||
|
||||
> Legacy-компонент может быть удалён только после подтверждения, что его поведение полностью покрывается целевым `QuoteStore` и что все runtime-потребители переведены без изменения существующих контрактов.
|
||||
|
||||
---
|
||||
|
||||
## 2. Исходное состояние
|
||||
|
||||
До Build 042 в проекте существовал legacy-компонент:
|
||||
|
||||
```text
|
||||
src/integrations/exchange/market_cache.py
|
||||
```
|
||||
|
||||
с классом:
|
||||
|
||||
```text
|
||||
MarketPriceCache
|
||||
```
|
||||
|
||||
`MarketPriceCache` использовался как compatibility facade над:
|
||||
|
||||
```text
|
||||
src/storage/quote_store.py
|
||||
```
|
||||
|
||||
и внутренне содержал общий экземпляр `InMemoryQuoteStore`.
|
||||
|
||||
Основными потребителями были:
|
||||
|
||||
```text
|
||||
src/integrations/exchange/service.py
|
||||
src/integrations/exchange/market_stream.py
|
||||
src/integrations/exchange/market_data_runner.py
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 3. Результаты аудита
|
||||
|
||||
Аудит подтвердил, что `MarketPriceCache` не содержал самостоятельной бизнес-логики хранения котировок. Его обязанности ограничивались делегированием операций `set`, `get` и `clear` в `QuoteStore`, нормализацией `runtime_key`, использованием фиксированного `source_name` и предоставлением глобального shared store через class-level `_store`.
|
||||
|
||||
Фактическое хранение данных уже выполнялось через:
|
||||
|
||||
```text
|
||||
src/storage/quote_store.py
|
||||
```
|
||||
|
||||
Основные контракты:
|
||||
|
||||
```text
|
||||
QuoteStoreProtocol
|
||||
InMemoryQuoteStore
|
||||
```
|
||||
|
||||
Таким образом, `MarketPriceCache` являлся промежуточным compatibility facade и не был необходим как самостоятельный архитектурный слой.
|
||||
|
||||
---
|
||||
|
||||
## 4. Критические семантики, сохранённые при удалении
|
||||
|
||||
### 4.1. Общий shared Quote Store
|
||||
|
||||
Все основные производители и потребители котировок продолжают работать с одним общим экземпляром `QuoteStore`.
|
||||
|
||||
```text
|
||||
WebSocket / REST
|
||||
↓
|
||||
Quote model
|
||||
↓
|
||||
shared QuoteStore
|
||||
↓
|
||||
ExchangeService / runtime consumers
|
||||
```
|
||||
|
||||
### 4.2. Изоляция по runtime_key
|
||||
|
||||
Сохранена изоляция котировок между runtime-контекстами, включая:
|
||||
|
||||
```text
|
||||
auto
|
||||
debug_auto
|
||||
default
|
||||
```
|
||||
|
||||
Ключ хранения остаётся логически эквивалентным:
|
||||
|
||||
```text
|
||||
(source_name, runtime_key, symbol)
|
||||
```
|
||||
|
||||
### 4.3. Нормализация runtime_key
|
||||
|
||||
Сохранена нормализация:
|
||||
|
||||
```text
|
||||
" AUTO " → "auto"
|
||||
" Debug_Auto " → "debug_auto"
|
||||
```
|
||||
|
||||
### 4.4. Нормализация symbol
|
||||
|
||||
Сохранена нормализация символов при операциях чтения, записи и очистки.
|
||||
|
||||
```text
|
||||
" btc/usd_leverage " → "BTC/USD_LEVERAGE"
|
||||
```
|
||||
|
||||
### 4.5. Семантика clear()
|
||||
|
||||
Сохранена возможность точечной и общей очистки `QuoteStore` по `source_name`, `runtime_key`, `symbol`, комбинации фильтров и полной очистке store.
|
||||
|
||||
### 4.6. REST fallback
|
||||
|
||||
Удаление `MarketPriceCache` не нарушило восстановленный в Build 040 REST fallback. Если свежая котировка отсутствует в shared `QuoteStore`, `ExchangeService` сохраняет возможность загрузить котировку через новый Quotes Feed acquisition pipeline и сохранить полученный `Quote` в общий store.
|
||||
|
||||
---
|
||||
|
||||
## 5. Выполненные изменения
|
||||
|
||||
В рамках Build 042:
|
||||
|
||||
- удалён compatibility facade `MarketPriceCache`;
|
||||
- удалён файл `src/integrations/exchange/market_cache.py`;
|
||||
- удалён legacy-набор тестов `tests/unit/integrations/exchange/test_market_cache.py`;
|
||||
- `ExchangeService` переведён на прямую работу с shared `QuoteStore`;
|
||||
- `MarketDataRunner` переведён на прямую работу с shared `QuoteStore`;
|
||||
- `market_stream` переведён на прямую работу с shared `QuoteStore`;
|
||||
- сохранена runtime isolation;
|
||||
- сохранена нормализация символов и runtime keys;
|
||||
- сохранена семантика очистки;
|
||||
- сохранён REST fallback;
|
||||
- сохранены существующие публичные контракты получения котировок.
|
||||
|
||||
---
|
||||
|
||||
## 6. Архитектурный результат
|
||||
|
||||
До Build 042:
|
||||
|
||||
```text
|
||||
WebSocket / REST
|
||||
↓
|
||||
Quote
|
||||
↓
|
||||
MarketPriceCache
|
||||
↓
|
||||
InMemoryQuoteStore
|
||||
```
|
||||
|
||||
После Build 042:
|
||||
|
||||
```text
|
||||
WebSocket / REST
|
||||
↓
|
||||
Quote
|
||||
↓
|
||||
shared QuoteStore
|
||||
↓
|
||||
ExchangeService / runtime consumers
|
||||
```
|
||||
|
||||
Удалён лишний промежуточный слой `MarketPriceCache`. `QuoteStore` теперь является непосредственным storage-контрактом для канонических моделей `Quote`.
|
||||
|
||||
---
|
||||
|
||||
## 7. Проверка тестами
|
||||
|
||||
### Quote Store
|
||||
|
||||
```text
|
||||
python -m pytest -q tests/unit/storage/test_quote_store.py
|
||||
```
|
||||
|
||||
Результат:
|
||||
|
||||
```text
|
||||
64 passed in 0.04s
|
||||
```
|
||||
|
||||
### ExchangeService quote contracts
|
||||
|
||||
```text
|
||||
python -m pytest -q tests/unit/integrations/exchange/test_service_quote.py tests/unit/integrations/exchange/test_service_execution_quote.py
|
||||
```
|
||||
|
||||
Результат:
|
||||
|
||||
```text
|
||||
11 passed in 0.11s
|
||||
```
|
||||
|
||||
### Market runtime
|
||||
|
||||
```text
|
||||
python -m pytest -q tests/unit/integrations/exchange/test_market_data_runner.py tests/unit/integrations/exchange/test_market_stream.py
|
||||
```
|
||||
|
||||
Результат:
|
||||
|
||||
```text
|
||||
15 passed in 0.09s
|
||||
```
|
||||
|
||||
### Полный regression suite
|
||||
|
||||
```text
|
||||
python -m pytest -q
|
||||
```
|
||||
|
||||
Результат:
|
||||
|
||||
```text
|
||||
613 passed in 2.37s
|
||||
```
|
||||
|
||||
Уменьшение общего количества тестов с `614` до `613` является ожидаемым результатом удаления legacy-файла:
|
||||
|
||||
```text
|
||||
tests/unit/integrations/exchange/test_market_cache.py
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 8. Контроль отсутствия legacy-зависимостей
|
||||
|
||||
Выполнена финальная проверка:
|
||||
|
||||
```text
|
||||
grep -RIn --exclude-dir="__pycache__" --exclude="*.pyc" -E "\bMarketPriceCache\b|integrations\.exchange\.market_cache|market_cache" src tests
|
||||
```
|
||||
|
||||
Результат:
|
||||
|
||||
```text
|
||||
пусто
|
||||
```
|
||||
|
||||
Это подтверждает отсутствие оставшихся ссылок на `MarketPriceCache`, `src.integrations.exchange.market_cache` и `market_cache`.
|
||||
|
||||
---
|
||||
|
||||
## 9. Итог Build 042
|
||||
|
||||
Build 042 завершён успешно.
|
||||
|
||||
Подтверждено:
|
||||
|
||||
- legacy `MarketPriceCache` полностью удалён;
|
||||
- прямые зависимости от `market_cache.py` отсутствуют;
|
||||
- shared `QuoteStore` стал непосредственным storage-механизмом котировок;
|
||||
- WebSocket и REST пути используют каноническую модель `Quote`;
|
||||
- runtime isolation сохранена;
|
||||
- REST fallback сохранён;
|
||||
- полный regression suite проходит без ошибок;
|
||||
- архитектура готова к финальной проверке Quotes Feed.
|
||||
|
||||
---
|
||||
|
||||
## 10. Следующий этап
|
||||
|
||||
```text
|
||||
Build 043 — Финальная архитектурная проверка Quotes Feed
|
||||
```
|
||||
|
||||
Цель Build 043:
|
||||
|
||||
- проверить целостность всей архитектурной цепочки Quotes Feed;
|
||||
- подтвердить отсутствие legacy quote parsing;
|
||||
- подтвердить отсутствие legacy quote cache facade;
|
||||
- проверить REST и WebSocket пути получения котировок;
|
||||
- проверить единый canonical `Quote`;
|
||||
- проверить Feed → Handler → Adapter → Validation → Mapper → Storage → Consumer flow;
|
||||
- проверить границы ответственности модулей;
|
||||
- подтвердить готовность Quotes Feed к завершению миграции.
|
||||
Reference in New Issue
Block a user