feat: use broker-authoritative qty in slots RPC holdings
Co-authored-by: genichin <4282227+genichin@users.noreply.github.com>
This commit is contained in:
co-authored by
genichin
parent
832dcb5fbb
commit
30bcbe1d12
@@ -88,7 +88,11 @@
|
||||
{ "slot_id": "str (UUID)",
|
||||
"status": "inactive | pending_buy | pending_sell | holding | error",
|
||||
"symbol": "str | null",
|
||||
"qty": "float | null", // slot mirror (REQ-062)
|
||||
"qty": "float | null", // holding: broker authority / unavailable=null
|
||||
"qty_source": "broker | unavailable", // holding-only metadata
|
||||
"broker_quantity_available": "bool", // holding-only metadata
|
||||
"broker_quantity_captured_at": "ISO-8601 | null", // holding-only metadata
|
||||
"slot_quantity": "float | null", // core daily_slot mirror (diagnostic)
|
||||
"asset_quantity": "float | null", // hub authority (REQ-062)
|
||||
"avg_price": "float | null",
|
||||
"entry_price": "float | null",
|
||||
@@ -97,7 +101,7 @@
|
||||
"universe_detached": "bool",
|
||||
"cash_balance": "float | null", // hub authority
|
||||
"cash_estimated": "bool", // true = pending ledger outbox delta 반영
|
||||
"warned": "bool", // qty != asset_quantity 시 true (REQ-062)
|
||||
"warned": "bool", // slot_quantity != asset_quantity 시 true
|
||||
"watchdog": { // null if watchdog store unavailable
|
||||
"expired": "bool",
|
||||
"last_seen": "ISO-8601 | null"
|
||||
@@ -119,12 +123,16 @@
|
||||
| 필드 | 권위 소스 | 비고 |
|
||||
|---|---|---|
|
||||
| `slot_id`, `status`, `avg_price`, `entry_price`, `forced_close_at`, `universe_detached` | slot (core) | 슬롯 row 직접 |
|
||||
| `qty` | slot (core) | 슬롯 mirror — broker position |
|
||||
| `qty` | broker account snapshot | holding 슬롯에서만 authoritative. unavailable/stale 시 null |
|
||||
| `qty_source` | 파생(metadata) | holding 슬롯: `broker` \| `unavailable` |
|
||||
| `broker_quantity_available` | 파생(metadata) | holding 슬롯 broker qty freshness 통과 여부 |
|
||||
| `broker_quantity_captured_at` | broker account snapshot | holding 슬롯 broker qty capture 시각 |
|
||||
| `slot_quantity` | slot (core) | 기존 daily_slot.qty mirror(진단용) |
|
||||
| `symbol`, `portfolio_id` | slot (core) | 자산 바인딩 |
|
||||
| `asset_quantity` | hub (SnapshotStore) | portfolio-hub 권위값 (REQ-062) |
|
||||
| `cash_balance` | hub (SnapshotStore) | portfolio-hub 권위값; `cash_estimated=true` 시 ledger outbox delta 추정값 |
|
||||
| `cash_estimated` | ledger outbox | pending delta 있을 때 true (REQ-029) |
|
||||
| `warned` | 파생 | `qty != asset_quantity` (REQ-074 AC-2) |
|
||||
| `warned` | 파생 | `slot_quantity != asset_quantity` (REQ-074 AC-2) |
|
||||
| `watchdog` | WatchdogStore | 만료 여부 + last_seen; null=store 미연결 |
|
||||
| `paused` | PauseStore | durable pause overlay (REQ-032) |
|
||||
| `strategy_name` | hub (PortfolioItem via SnapshotStore) | REQ-116 additive. portfolio-hub 정본. hub 미제공 시 null |
|
||||
@@ -132,6 +140,7 @@
|
||||
| `markets` | hub (PortfolioItem via SnapshotStore) | REQ-116 additive. list[str]; hub 미제공 시 [] |
|
||||
|
||||
- **slot-origin strategy 필드 없음** (REQ-074 AC-5, REQ-116 additive 재도입 후에도 유지): `strategy_id`, `sell_strategy_id`, `active_strategy_id` 는 응답에 포함되지 않는다. `strategy_name`/`strategy_params`/`markets` 는 PortfolioItem(hub) 출처이므로 AC-5 제외 대상과 구분된다 — REQ-116 Notes 참조.
|
||||
- **Breaking change (holding `qty`) rollout**: 기존 전략 클라이언트가 `qty=slot mirror`로 가정했다면 `slot_quantity`를 읽도록 전환해야 한다. 권장 경로는 (1) 클라이언트에 `qty_source`/`broker_quantity_available` 체크 추가 → (2) fail-closed (`qty is null`) 처리 배포 → (3) `qty`를 broker 정본으로 사용하도록 cutover 순서다.
|
||||
- `spy=false`(기본): holding 슬롯 응답 후 `WatchdogStore.update(slot_id)` 호출 — 전략 폴링 = 생존 신호.
|
||||
- `spy=true`: watchdog 갱신 건너뜀 — 운영자 CLI(`universe`/`slots`) 가 항상 사용.
|
||||
|
||||
@@ -645,6 +654,7 @@ trex-core가 `source="trex-core"`, `severity="critical"`로 발행하는 초기
|
||||
결과불명 주문 탐색을 KIS 신형 일별주문체결조회
|
||||
(`TTTC0081R`/`VTTC0081R`, `EXCG_ID_DVSN_CD=ALL`)로 단일화했다.
|
||||
- 2026-07-06 :: BAT-056 (dcy-002 FR-6, REQ-117/118) — `OrderRequest.venue: str = "KRX"` additive 추가(기존 위치 인수 순서 불변 — AMQP wire 계약 영향 없음, 브로커 어댑터 계층 DTO까지만). KIS 어댑터: submit_order/cancel_order body에 `EXCG_ID_DVSN_CD` 항상 명시 전송(기존 미전송 → KRX 명시화 견고성 향상), cancel_order/get_current_price 시그니처 venue/market 파라미터 추가(기본값 KRX/"J" — 기존 호출자 무영향). paper broker 시그니처 정합(venue/market 무시). 실측 근거: 2026-07-06 NXT 주문/취소 rt_cd=0 확인.
|
||||
- 2026-08-24 :: issue #62 — `trex.slots.req` holding row `qty`를 broker holdings snapshot 정본으로 전환. `qty_source`/`broker_quantity_available`/`broker_quantity_captured_at`/`slot_quantity`를 추가하고, broker qty unavailable 또는 stale이면 fail-closed(`qty=null`, no core/hub fallback)로 응답.
|
||||
|
||||
|
||||
## REQ-123 Contract Addendum: cost-basis canonical parsing & sync diagnostics
|
||||
|
||||
@@ -141,10 +141,11 @@
|
||||
1. 요청 payload 디코드: `{filter ∈ {all, inactive, pending, holding, error}, spy: bool}`.
|
||||
2. `slot_repo.list_slots(instance_key)` → status 기준 서버 필터 적용(`inactive`/`pending`/`holding`/`error`; 미인식 = `all`).
|
||||
3. `spy=false` 면 `slot_repo.list_holding_slots()` 의 모든 holding 슬롯에 `WatchdogStore.update(slot_id)`.
|
||||
4. 각 슬롯에 `slot_to_dict(s, snapshot_store=..., watchdog_store=..., pause_store=..., watchdog_timeout_sec=...)` 적용 → 병합 row 산출:
|
||||
- slot 코어 필드: `slot_id/status/symbol/qty/avg_price/entry_price/portfolio_id/forced_close_at/universe_detached`
|
||||
4. 각 슬롯에 `slot_to_dict(s, snapshot_store=..., watchdog_store=..., pause_store=..., watchdog_timeout_sec=...)` 적용 후 broker holdings snapshot 오버레이를 적용해 병합 row 산출:
|
||||
- slot 코어 필드: `slot_id/status/symbol/slot_quantity/avg_price/entry_price/portfolio_id/forced_close_at/universe_detached`
|
||||
- holding authoritative 수량: `qty`(broker), `qty_source`, `broker_quantity_available`, `broker_quantity_captured_at` (`qty_source=unavailable`이면 `qty=null`, mirror fallback 금지)
|
||||
- hub 권위 필드: `asset_quantity`/`cash_balance` (SnapshotStore)
|
||||
- 파생: `warned = (qty != asset_quantity)` (REQ-074 AC-2)
|
||||
- 파생: `warned = (slot_quantity != asset_quantity)` (REQ-074 AC-2)
|
||||
- 추정 현금(REQ-029 OQ-4): `cash_estimated=True` + `cash_balance += pending ledger delta`(best-effort)
|
||||
- 워치독: `watchdog: {expired, last_seen}` inline (WatchdogStore)
|
||||
- 오버레이: `paused` (PauseStore, REQ-032)
|
||||
|
||||
Reference in New Issue
Block a user