Running inventory and explicit data synchronization¶
These endpoints query the current user's running inventory and read or upsert marker data for an existing run. They do not start, stop or execute strategies, generate markers, or invent timestamps or instruments. Live backend behavior remains unverified; read and write flags default to off.
| Operation | REST POST | MCP | CLI |
|---|---|---|---|
| Inventory page | /api/get-quant-running-inventory |
futu_get_quant_running_inventory |
get-quant-running-inventory |
| Data page | /api/get-quant-running-data |
futu_get_quant_running_data |
get-quant-running-data |
| Explicit upsert | /api/upsert-quant-running-data |
futu_upsert_quant_running_data |
upsert-quant-running-data |
Gateway and gRPC use the corresponding public protocols; private gateway requests require API-key-authenticated native binary WebSocket. MCP and CLI forward through authenticated REST and require its address and the caller's API key. Reads require acc:read; writes require both acc:read and qot:write. All account-restricted keys, including an empty account list, are rejected because these are user-wide documents. A caller cannot select another UID.
Every request requires extension_version: 1. Inventory accepts optional filter, sort_field, is_asc, from, and count. The starting index is nonnegative and an explicit count is 1–200. Filters support details, up to 300 running IDs, status/reason/pod-level lists, and creation/stop intervals with optional bounds and exclusion flags. Times are Unix seconds. Only one page is returned; original pagination presence and unknown response states are retained. Raw detail_info is separate from its decoded view and decode status.
Data requests require a real inventory-owned running_id representable as a positive int64, plus data_type: 1. Archive IDs and local strategy IDs are not substitutes. Every new data operation checks the current inventory. Optional next_offset is a nonnegative int64 exclusive cursor; zero or absence starts at the beginning/end according to optional sort_ascend. Count accepts 0–1000, with zero/absence left to the backend default. A size-limited short page does not prove end of data.
Upsert requires an immutable intent_key, the real run ID, and 1–500 data_list entries. Each supplies type 1, a positive int64 data_offset, and data bytes containing all four required public BarMarker fields: bar_marker_time, bar_marker_stock, bar_marker_icon, and bar_marker_content. Zero and empty values must still have actual protobuf presence. Duplicate targets within a batch are rejected. The backend inserts or updates by run, type and offset.
The complete serialized backend request must be smaller than 1,024,000 bytes. Upsert REST JSON has a separate 10 MiB limit, including byte-array expansion. Responses preserve raw data bytes, invalid inner payloads and unknown types alongside separate decoded views.
The durable receipt exposes receipt_id, ack_state, optional backend_code, and replayed. ack_success, ack_rejected, and submitted_unknown distinguish acknowledged outcomes from uncertainty. Replaying the same intent sends no additional business RPC; a new intent cannot bypass an unresolved claim on the same target. Upsert never reads back automatically. An independent GET is only an observation: matching data is not an ACK, and a missing row does not prove the write failed. There is no cross-client CAS or global ordering guarantee.