Story: Move trade import orchestration to service layer
Table of Contents
This page documents a story in Sprint 22. It captures the goal, current status, acceptance criteria, and the tasks that compose it.
Goal
Trade import today diverges from market data import's architecture:
import_market_data_request (ores.marketdata.core::service::import_service)
is fully server-side — the client just forwards raw file bytes — but
trade import's ~300 lines of orchestration (portfolio XML parsing via
ores.ore.core::xml::importer, per-trade save_trade_request, and a
30-way per-instrument-type save_<type>_instrument_request dispatch)
live entirely inside projects/ores.qt/trading/src/ImportTradeDialog.cpp
(lines ~744-1045), with no service-layer backing. Move that orchestration into a new
ores.trading.core::service::trade_import_service, backed by a new
import_trades_request=/=import_trades_response NATS message pair
mirroring import_market_data_request. This lets Qt shrink back to
progress/cancel UI only, and lets
ores.shell command for market data import's planned trade import
shell command be a thin wrapper around the same service instead of
duplicating the 30-way instrument dispatch a second time.
This story is an enabler with no direct blocker relationship to Synthetic data collections: Basic and Realistic, but both it and the sibling shell story exist to give that story's imports a non-interactive path.
Status
| Field | Value |
|---|---|
| State | BACKLOG |
| Parent sprint | Sprint 22 |
| Now | Not yet started. |
| Waiting on | Nothing. |
| Next | Break the story into tasks. |
| Last touched | 2026-07-04 |
Acceptance
import_trades_request=/=import_trades_responseexist inores.trading.api, andores.trading.core::service::trade_import_serviceparses portfolio XML, saves trades, and dispatches per-instrument-type saves server-side, registered as a NATS handler.ImportTradeDialogsends a singleimport_trades_requestinstead of building 31 requests inline; only progress/cancel UI remains in the client.ores.shellgains atrade import --file <portfolio.xml>command that is a thin wrapper around the same request.
Tasks
| Task | State | Start | End | Description |
|---|---|---|---|---|
| Add import_trades_request/response protocol and trade_import_service | BACKLOG | Define import_trades_request/import_trades_response in ores.trading.api (mirroring import_market_data_request's shape: raw portfolio XML content in, trade_count/instrument_count/error info out), implement ores.trading.core::service::trade_import_service parsing via ores.ore.core::xml::importer, saving each trade and dispatching per-instrument-type saves (the ~300 lines currently in ImportTradeDialog.cpp:744-1045), and register the NATS handler mirroring ores.marketdata.core's import_service registration. | ||
| Refactor ImportTradeDialog to use trade_import_service | BACKLOG | Replace ImportTradeDialog's inline per-trade/per-instrument-type request loop (~744-1045) with a single call to the new import_trades_request, keeping only the ~75 lines of legitimate UI concerns (progress updates, liveness guard, cancellation handling). | ||
| Add ores.shell trade import command | BACKLOG | Add a 'trade import –file <portfolio.xml path>' command to ores.shell (mirroring the marketdata_commands pattern), sending import_trades_request and printing trade_count/instrument_count/errors. Blocked on 'Add import_trades_request/response protocol and trade_import_service'; ideally also after the Qt dialog refactor, though both consume the same server API so order between them is flexible. |