build 039: complete Quotes Feed migration foundation
This commit is contained in:
@@ -0,0 +1,341 @@
|
||||
# Stream Research Protocol — marketData.subscribe
|
||||
|
||||
## Контроль документа
|
||||
|
||||
| Свойство | Значение |
|
||||
|----------|----------|
|
||||
| Документ | Stream Research Protocol — marketData.subscribe |
|
||||
| Тип документа | Research Protocol |
|
||||
| Версия | 2.0 |
|
||||
| Статус | Draft |
|
||||
| Проект | Dzentra |
|
||||
| Подсистема | Market Intelligence |
|
||||
| Биржа | Dzengi |
|
||||
| Endpoint | `marketData.subscribe` |
|
||||
| Транспорт | WebSocket Stream |
|
||||
| Основан на | Market Intelligence Stream Research Standard |
|
||||
| Язык | Русский |
|
||||
|
||||
---
|
||||
|
||||
# 1. Исследование подключения
|
||||
|
||||
## 1.1 Подключение
|
||||
|
||||
### 1.1.1 Корректность подключения
|
||||
|
||||
- [x] корректность подключения — подтверждена.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
Получено успешное подключение к WebSocket API Dzengi.
|
||||
|
||||
Получено подтверждение подписки.
|
||||
|
||||
После подтверждения подписки начинают поступать сообщения `internal.quote`.
|
||||
|
||||
---
|
||||
|
||||
### 1.1.2 Требования к соединению
|
||||
|
||||
- [x] URL подключения — соответствует документации.
|
||||
- [x] используемый транспорт (WS/WSS) — соответствует документации.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
**URL подключения**
|
||||
|
||||
Production: `wss://api-adapter.dzengi.com/connect`
|
||||
Demo: `wss://demo-api-adapter.dzengi.com/connect`
|
||||
|
||||
**Используемый транспорт**
|
||||
|
||||
`WSS (WebSocket Secure)`
|
||||
|
||||
---
|
||||
|
||||
### 1.1.3 Требования к авторизации
|
||||
|
||||
- [x] требуется ли авторизация — соответствует документации.
|
||||
- [x] механизм авторизации — соответствует документации.
|
||||
- [x] обязательные заголовки авторизации — соответствует документации.
|
||||
- [x] возможность работы без авторизации — соответствует документации.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
Публичный поток `marketData.subscribe` доступен без передачи данных авторизации.
|
||||
|
||||
---
|
||||
|
||||
### 1.2 Подписка
|
||||
|
||||
- [x] формат подписки — частично соответствует документации;
|
||||
- [x] подтверждение подписки — соответствует документации;
|
||||
- [x] сообщения об ошибках — определено экспериментально;
|
||||
- [х] повторная подписка — определено экспериментально;
|
||||
- [x] подписка на несколько инструментов — определено экспериментально.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
**Формат подписки**
|
||||
|
||||
Документация описывает только содержимое `payload`:
|
||||
|
||||
```
|
||||
{
|
||||
"symbols": [
|
||||
"string"
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
Фактический формат сообщения, передаваемого через WebSocket /connect:
|
||||
|
||||
```
|
||||
{
|
||||
"correlationId": "...",
|
||||
"destination": "marketData.subscribe",
|
||||
"payload": {
|
||||
"symbols": [
|
||||
"BTC/USD_LEVERAGE"
|
||||
]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Подтверждение подписки**
|
||||
|
||||
```
|
||||
{
|
||||
"destination": "marketData.subscribe",
|
||||
"status": "OK",
|
||||
"payload": {
|
||||
"subscriptions": {
|
||||
"BTC/USD_LEVERAGE": "PROCESSED"
|
||||
}
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Сообщения об ошибках**
|
||||
|
||||
Экспериментально зафиксированы варианты ошибок:
|
||||
|
||||
- `INVALID/SYMBOL` возвращает `status = OK`, но в `payload.subscriptions` указывается `ERROR: INVALID/SYMBOL not found`.
|
||||
- пустой `symbols` возвращает `status = ERROR`, `code = -1128`.
|
||||
- отсутствующий `symbols` возвращает `status = ERROR`, `code = -1128`.
|
||||
- отсутствующий `payload` возвращает `status = ERROR`, `code = -1128`.
|
||||
- неверный `destination` возвращает `status = ERROR`, `errorCode = BAD_REQUEST`.
|
||||
|
||||
**Повторная подписка**
|
||||
|
||||
- первая подписка получает статус `PROCESSED`;
|
||||
- повторные подписки получают статус `ALREADY_SUBSCRIBED`;
|
||||
- сообщения об ошибке не формируются;
|
||||
- повторная подписка работает без предварительной отмены;
|
||||
- в проведенных экспериментах признаков дублирования сообщений `internal.quote` не обнаружено.
|
||||
|
||||
**Подписка на несколько инструментов**
|
||||
|
||||
Экспериментально установлено:
|
||||
|
||||
- команда `marketData.subscribe` принимает несколько торговых инструментов;
|
||||
- подтверждение подписки содержит отдельный статус для каждого инструмента;
|
||||
- поток `internal.quote` передает сообщения для всех подписанных инструментов через одно WebSocket-соединение;
|
||||
- принадлежность сообщения к инструменту определяется полем `payload.symbolName`.
|
||||
|
||||
---
|
||||
|
||||
# 2. Исследование структуры потока
|
||||
|
||||
## 2.1 Типы сообщений
|
||||
|
||||
- [ ] назначение;
|
||||
- [ ] содержит ли рыночную информацию;
|
||||
- [ ] содержит ли служебную информацию;
|
||||
- [ ] содержит ли ошибки;
|
||||
- [ ] содержит ли подтверждение подписки;
|
||||
- [ ] содержит ли подтверждение отписки.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
## 2.2 Структура сообщений
|
||||
|
||||
- [ ] обязательные поля;
|
||||
- [ ] необязательные поля;
|
||||
- [ ] тип каждого поля;
|
||||
- [ ] допустимые значения;
|
||||
- [ ] диапазоны значений;
|
||||
- [ ] ограничения.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
# 3. Классификация сообщений
|
||||
|
||||
- [ ] рыночное сообщение;
|
||||
- [ ] служебное сообщение;
|
||||
- [ ] сообщение управления;
|
||||
- [ ] сообщение об ошибке;
|
||||
- [ ] сообщение подтверждения.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
# 4. Исследование семантики полей
|
||||
|
||||
- [ ] фактическое назначение;
|
||||
- [ ] источник происхождения;
|
||||
- [ ] обязательность;
|
||||
- [ ] изменяемость;
|
||||
- [ ] диапазон допустимых значений;
|
||||
- [ ] взаимосвязь с другими полями;
|
||||
- [ ] ограничения использования;
|
||||
- [ ] степень подтверждения семантики.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
# 5. Исследование информационных фактов
|
||||
|
||||
- [ ] какие информационные факты содержит сообщение;
|
||||
- [ ] какие информационные факты могут быть вычислены непосредственно из сообщения;
|
||||
- [ ] какие информационные факты отсутствуют;
|
||||
- [ ] какие информационные факты являются первичными;
|
||||
- [ ] какие информационные факты являются производными.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
## 5.1 Первичные информационные факты
|
||||
|
||||
- [ ] источник происхождения;
|
||||
- [ ] поле сообщения;
|
||||
- [ ] степень подтверждения;
|
||||
- [ ] ограничения использования.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
## 5.2 Производные информационные факты
|
||||
|
||||
- [ ] формула вычисления;
|
||||
- [ ] необходимые исходные данные;
|
||||
- [ ] ограничения вычисления;
|
||||
- [ ] степень достоверности.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
# 6. Исследование поведения потока
|
||||
|
||||
## 6.1 Частота сообщений
|
||||
|
||||
- [ ] минимальная частота;
|
||||
- [ ] максимальная частота;
|
||||
- [ ] средняя частота;
|
||||
- [ ] пиковая частота;
|
||||
- [ ] условия изменения частоты.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
## 6.2 Последовательность сообщений
|
||||
|
||||
- [ ] порядок поступления сообщений;
|
||||
- [ ] последовательность timestamp;
|
||||
- [ ] наличие пропусков;
|
||||
- [ ] наличие повторяющихся сообщений;
|
||||
- [ ] возможность нарушения порядка.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
## 6.3 Полнота сообщений
|
||||
|
||||
- [ ] полный снимок состояния;
|
||||
- [ ] инкрементальные изменения;
|
||||
- [ ] смешанный режим передачи;
|
||||
- [ ] обязательность всех полей;
|
||||
- [ ] возможность частичных обновлений.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
# 7. Исследование поведения данных
|
||||
|
||||
- [ ] условия появления;
|
||||
- [ ] условия изменения;
|
||||
- [ ] условия исчезновения;
|
||||
- [ ] частота изменения;
|
||||
- [ ] взаимосвязь с другими фактами.
|
||||
|
||||
---
|
||||
|
||||
## Дополнительно определить
|
||||
|
||||
- [ ] какие факты изменяются одновременно;
|
||||
- [ ] какие факты никогда не изменяются одновременно;
|
||||
- [ ] какие факты являются независимыми;
|
||||
- [ ] какие факты являются производными от других.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
# 8. Проверка эквивалентности
|
||||
|
||||
- [ ] существует ли аналогичный источник;
|
||||
- [ ] полностью ли совпадает значение;
|
||||
- [ ] совпадает ли семантика;
|
||||
- [ ] совпадает ли точность;
|
||||
- [ ] совпадает ли момент обновления;
|
||||
- [ ] имеются ли расхождения.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
## 8.1 Альтернативные источники
|
||||
|
||||
- [ ] REST endpoint;
|
||||
- [ ] WebSocket Request;
|
||||
- [ ] другие Stream;
|
||||
- [ ] внутренние вычисления.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
## 8.2 Приоритет источников
|
||||
|
||||
- [ ] основной источник;
|
||||
- [ ] резервный источник;
|
||||
- [ ] допустимые альтернативы;
|
||||
- [ ] причины выбора приоритетного источника.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
---
|
||||
|
||||
# 9. Исследование производительности
|
||||
|
||||
- [ ] средний размер сообщения;
|
||||
- [ ] максимальный размер сообщения;
|
||||
- [ ] средняя скорость передачи;
|
||||
- [ ] максимальная скорость передачи;
|
||||
- [ ] объём данных в минуту;
|
||||
- [ ] объём данных в час.
|
||||
|
||||
#### Журнал исследования
|
||||
@@ -0,0 +1,46 @@
|
||||
### 1.1.4 Дополнительные требования клиента
|
||||
|
||||
- [x] обязательный формат сообщений — частично соответствует документации;
|
||||
- [ ] поддержание соединения;
|
||||
- [x] heartbeat / keepalive / ping-pong — определено экспериментально;
|
||||
- [ ] автоматическое закрытие соединения;
|
||||
- [ ] idle timeout;
|
||||
- [ ] требования к кодировке;
|
||||
- [ ] другие обязательные требования.
|
||||
|
||||
#### Журнал исследования
|
||||
|
||||
**Обязательный формат сообщений**
|
||||
|
||||
Документация указывает формат payload (json):
|
||||
|
||||
```
|
||||
{
|
||||
"symbols": [
|
||||
"string"
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
Фактический формат сообщения через WebSocket /connect:
|
||||
|
||||
```
|
||||
{
|
||||
"correlationId": "...",
|
||||
"destination": "marketData.subscribe",
|
||||
"payload": {
|
||||
"symbols": ["BTC/USD_LEVERAGE"]
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
**Поддержание соединения**
|
||||
|
||||
Документация требований не содержит.
|
||||
|
||||
За время наблюдения получены сообщения только следующих типов:
|
||||
|
||||
- `marketData.subscribe`
|
||||
- `internal.quote`
|
||||
|
||||
Специальные сообщения heartbeat / keepalive / ping / pong не обнаружены.
|
||||
@@ -0,0 +1,269 @@
|
||||
# Dzengi API Endpoint Research — marketData.subscribe
|
||||
|
||||
## Контроль документа
|
||||
|
||||
| Свойство | Значение |
|
||||
|----------|----------|
|
||||
| Документ | Dzengi API Endpoint Research — marketData.subscribe |
|
||||
| Тип документа | Endpoint Research |
|
||||
| Версия | 1.0 |
|
||||
| Статус | Draft |
|
||||
| Степень верификации | Runtime Research |
|
||||
| Проект | Dzentra |
|
||||
| Подсистема | Market Intelligence |
|
||||
| Источник | Dzengi API |
|
||||
| Endpoint | `marketData.subscribe` |
|
||||
| Транспорт | WebSocket Stream |
|
||||
| Язык | Русский |
|
||||
|
||||
---
|
||||
|
||||
## Статус документа
|
||||
|
||||
Настоящий документ содержит результаты исследования endpoint `marketData.subscribe`, выполненного посредством анализа официальной документации Dzengi и фактических сообщений, полученных от биржи.
|
||||
|
||||
Документ предназначен для определения информационных сущностей, передаваемых данным endpoint, без интерпретации состояния рынка.
|
||||
|
||||
---
|
||||
|
||||
## Цель исследования
|
||||
|
||||
Цель настоящего исследования — определить:
|
||||
|
||||
- назначение endpoint;
|
||||
- структуру протокола обмена сообщениями;
|
||||
- типы сообщений;
|
||||
- семантику сообщений;
|
||||
- информационные сущности, содержащиеся в сообщениях;
|
||||
- особенности поведения потока данных;
|
||||
- взаимосвязь с другими endpoint API Dzengi.
|
||||
|
||||
---
|
||||
|
||||
## Основной вопрос исследования
|
||||
|
||||
> **Какую информацию о состоянии рынка предоставляет поток `marketData.subscribe`?**
|
||||
|
||||
---
|
||||
|
||||
## Источники исследования
|
||||
|
||||
Исследование основано на:
|
||||
|
||||
- официальной документации Dzengi;
|
||||
- OpenAPI (Swagger);
|
||||
- официальных примерах сообщений;
|
||||
- фактических сообщениях, полученных посредством Dzengi API Probe.
|
||||
|
||||
---
|
||||
|
||||
# 1. Назначение endpoint
|
||||
|
||||
## Описание документации
|
||||
|
||||
Согласно документации Dzengi, endpoint `marketData.subscribe` предназначен для получения потока рыночных котировок выбранных торговых инструментов.
|
||||
|
||||
---
|
||||
|
||||
## Назначение по результатам исследования
|
||||
|
||||
Исследование подтверждает, что `marketData.subscribe` является командой подписки на поток рыночных котировок.
|
||||
|
||||
После успешного выполнения подписки биржа начинает передавать поток сообщений с актуальными котировками выбранных инструментов.
|
||||
|
||||
Сам endpoint не является типом рыночного сообщения.
|
||||
|
||||
---
|
||||
|
||||
# 2. Способ получения данных
|
||||
|
||||
| Свойство | Значение |
|
||||
|----------|----------|
|
||||
| Транспорт | WebSocket Stream |
|
||||
| Тип взаимодействия | Подписка |
|
||||
| Endpoint | `marketData.subscribe` |
|
||||
| Формат сообщений | JSON |
|
||||
|
||||
---
|
||||
|
||||
# 3. Параметры подписки
|
||||
|
||||
| Параметр | Тип | Обязательный | Назначение |
|
||||
|----------|-----|--------------|------------|
|
||||
| symbols | array | Да | Список торговых инструментов |
|
||||
|
||||
---
|
||||
|
||||
# 4. Протокол взаимодействия
|
||||
|
||||
Исследование показало, что взаимодействие состоит из двух независимых этапов.
|
||||
|
||||
```text
|
||||
Клиент
|
||||
│
|
||||
│ marketData.subscribe
|
||||
▼
|
||||
Биржа
|
||||
│
|
||||
│ Subscription confirmation
|
||||
▼
|
||||
Биржа
|
||||
│
|
||||
│ internal.quote
|
||||
│ internal.quote
|
||||
│ internal.quote
|
||||
▼
|
||||
Клиент
|
||||
```
|
||||
|
||||
Команда `marketData.subscribe` используется исключительно для оформления подписки.
|
||||
|
||||
Информация о состоянии рынка передается сообщениями другого типа — `internal.quote`.
|
||||
|
||||
---
|
||||
|
||||
# 5. Типы сообщений
|
||||
|
||||
## 5.1 Subscription confirmation
|
||||
|
||||
### Назначение
|
||||
|
||||
Подтверждение успешного оформления подписки.
|
||||
|
||||
### Пример сообщения
|
||||
|
||||
```json
|
||||
{
|
||||
"correlationId": "probe-market-data-subscribe",
|
||||
"destination": "marketData.subscribe",
|
||||
"payload": {
|
||||
"subscriptions": {
|
||||
"BTC/USD_LEVERAGE": "PROCESSED"
|
||||
}
|
||||
},
|
||||
"status": "OK"
|
||||
}
|
||||
```
|
||||
|
||||
### Семантика
|
||||
|
||||
Сообщение подтверждает регистрацию подписки.
|
||||
|
||||
Рыночной информации не содержит.
|
||||
|
||||
---
|
||||
|
||||
## 5.2 Quote update (`internal.quote`)
|
||||
|
||||
### Назначение
|
||||
|
||||
Передача актуальных рыночных котировок.
|
||||
|
||||
### Пример сообщения
|
||||
|
||||
```json
|
||||
{
|
||||
"destination": "internal.quote",
|
||||
"payload": {
|
||||
"bid": 62055.80,
|
||||
"bidQty": 5.0,
|
||||
"ofr": 62055.90,
|
||||
"ofrQty": 5.0,
|
||||
"symbolName": "BTC/USD_LEVERAGE",
|
||||
"timestamp": 1783537924352
|
||||
},
|
||||
"status": "OK"
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
# 6. Анализ структуры сообщения
|
||||
|
||||
| Поле | Тип | Изменяется | Назначение | Статус |
|
||||
|------|-----|------------|------------|--------|
|
||||
| bid | Number | Да | Лучшая цена покупки | Подтверждено |
|
||||
| bidQty | Number | Да | Объем на лучшей цене покупки | Предварительно подтверждено |
|
||||
| ofr | Number | Да | Лучшая цена продажи | Подтверждено |
|
||||
| ofrQty | Number | Да | Объем на лучшей цене продажи | Предварительно подтверждено |
|
||||
| symbolName | String | Нет | Торговый инструмент | Подтверждено |
|
||||
| timestamp | Long | Да | Время формирования сообщения биржей | Подтверждено |
|
||||
|
||||
---
|
||||
|
||||
# 7. Информационные сущности, извлекаемые из сообщений
|
||||
|
||||
| Information ID | Источник (JSON Path) | Статус |
|
||||
|----------------|----------------------|--------|
|
||||
| best_bid_price | `payload.bid` | Подтверждено |
|
||||
| best_bid_quantity | `payload.bidQty` | Предварительно подтверждено |
|
||||
| best_ask_price | `payload.ofr` | Подтверждено |
|
||||
| best_ask_quantity | `payload.ofrQty` | Предварительно подтверждено |
|
||||
| instrument_symbol | `payload.symbolName` | Подтверждено |
|
||||
| quote_timestamp | `payload.timestamp` | Подтверждено |
|
||||
|
||||
---
|
||||
|
||||
# 8. Поведение потока
|
||||
|
||||
## Подтвержденные наблюдения
|
||||
|
||||
- Подписка выполняется один раз.
|
||||
- После подтверждения подписки биржа начинает передавать поток сообщений `internal.quote`.
|
||||
- Каждое сообщение содержит полный набор исследованных полей.
|
||||
- Сообщения поступают только при изменении котировки.
|
||||
- Каждое сообщение относится к одному торговому инструменту.
|
||||
|
||||
---
|
||||
|
||||
## Требует дополнительного исследования
|
||||
|
||||
- Всегда ли `bidQty` соответствует объему первого уровня стакана.
|
||||
- Всегда ли `ofrQty` соответствует объему первого уровня стакана.
|
||||
- Возможны ли сообщения без изменения цены.
|
||||
- Возможны ли сообщения с одинаковым `timestamp`.
|
||||
|
||||
---
|
||||
|
||||
# 9. Связь с другими endpoint
|
||||
|
||||
| Потенциальная информационная сущность | Endpoint | Поле | Статус |
|
||||
|--------------------------------------|----------|------|--------|
|
||||
| best_bid_price | REST `/api/v1/depth` | `bids[0][0]` | Подтверждено |
|
||||
| best_bid_price | WSS `/api/v1/depth` | `payload.bids[0][0]` | Подтверждено |
|
||||
| best_bid_price | `marketData.subscribe` | `payload.bid` | Подтверждено |
|
||||
| best_ask_price | REST `/api/v1/depth` | `asks[0][0]` | Подтверждено |
|
||||
| best_ask_price | WSS `/api/v1/depth` | `payload.asks[0][0]` | Подтверждено |
|
||||
| best_ask_price | `marketData.subscribe` | `payload.ofr` | Подтверждено |
|
||||
| best_bid_price | REST `/api/v1/ticker/24hr` | `bidPrice` | Требует исследования |
|
||||
| best_ask_price | REST `/api/v1/ticker/24hr` | `askPrice` | Требует исследования |
|
||||
|
||||
---
|
||||
|
||||
# 10. Итоги исследования
|
||||
|
||||
По результатам исследования подтверждено, что endpoint `marketData.subscribe` не является источником отдельных запросов к бирже, а представляет собой механизм подписки на поток рыночных котировок.
|
||||
|
||||
Фактическая рыночная информация передается сообщениями типа `internal.quote`.
|
||||
|
||||
Исследование также подтвердило эквивалентность информационных сущностей `best_bid_price` и `best_ask_price`, получаемых посредством `marketData.subscribe`, REST `/api/v1/depth` и WSS `/api/v1/depth`.
|
||||
|
||||
Эквивалентность соответствующих полей endpoint `/api/v1/ticker/24hr` на момент подготовки настоящей редакции документа не подтверждена.
|
||||
|
||||
---
|
||||
|
||||
# 11. Связь с архитектурой Dzentra
|
||||
|
||||
Результаты настоящего исследования используются при формировании:
|
||||
|
||||
- Dzengi Market Intelligence Information Mapping;
|
||||
- Dzentra Market Intelligence Information Model;
|
||||
- Dzentra Market Knowledge Catalogue.
|
||||
|
||||
Настоящий документ не определяет:
|
||||
|
||||
- знания о рынке;
|
||||
- интерпретацию состояния рынка;
|
||||
- алгоритмы анализа;
|
||||
- торговые стратегии;
|
||||
- архитектуру Engine.
|
||||
Reference in New Issue
Block a user