OMS API¶
The Order Management System API surface manages order creation, modification, cancellation, compliance evaluation, and allocation. All operations go through the sidecar on localhost:9191 and are routed to the order-book kernel via command topics.
Order Management¶
CreateOrder¶
Creates a new order. The kernel assigns order_id, created_at, updated_at and sets state to CREATED. Compliance checks are not triggered automatically.
order_id = client.oms.create_order(
portfolio_id="PORT-001",
instrument_id="INS-01936d8a-7c1e-7b2a-8f3d-4e5a6b7c8d9e",
direction="Buy", # Buy | Sell | SellShort | BuyToCover
ordered_quantity=1000,
order_type="Limit", # Market | Limit | Stop | StopLimit | PreviouslyQuoted
time_in_force="Day", # Day | GTC | IOC | FOK | GTD | AtTheOpen | AtTheClose
limit_price=150.25, # required for Limit / StopLimit
)
orderID, err := client.OMS.CreateOrder(ctx, &oms.CreateOrderRequest{
PortfolioID: "PORT-001",
InstrumentID: "INS-01936d8a-7c1e-7b2a-8f3d-4e5a6b7c8d9e",
Direction: oms.DirectionBuy,
OrderedQuantity: decimal.NewFromFloat(1000),
OrderType: oms.OrderTypeLimit,
TimeInForce: oms.TIFDay,
LimitPrice: decimal.NewFromFloat(150.25),
})
Fields: portfolio_id, instrument_id, direction, ordered_quantity, order_type, time_in_force, limit_price (optional), stop_price (optional), basket_id (optional), metadata (optional).
Errors: INVALID_INSTRUMENT, INVALID_PORTFOLIO, INVALID_ORDER_TYPE, DUPLICATE_ORDER.
UpdateOrder¶
Updates a mutable field on an existing order. Economic fields (ordered_quantity, limit_price, stop_price, time_in_force) lock after compliance passes. Booking fields (counterparty_id, metadata) remain updatable post-trade.
updated, err := client.OMS.UpdateOrder(ctx, orderID, &oms.OrderChanges{
LimitPrice: decimal.NewFromFloat(151.00),
})
Errors: ORDER_NOT_FOUND, INVALID_STATE, FIELD_LOCKED.
CancelOrder¶
Cancels an order. Active placements are canceled by the EMS separately. Cancel authority is role-scoped:
| Role | Allowed States |
|---|---|
| PM | CREATED, PENDING_PRE_TRADE_COMPLIANCE, PRE_TRADE_COMPLIANCE_PASSED, PRE_TRADE_COMPLIANCE_FAILED |
| Trader | SENT_TO_TRADER, ROUTED (only if no fills exist) |
| Ops | Cannot cancel orders |
Errors: ORDER_NOT_FOUND, INVALID_STATE, CANCEL_NOT_AUTHORIZED.
CloseOrder¶
Closes an order after execution completes (full or partial). Returns the executed and unfilled quantities. The OMS can then create a remainder order for the unfilled portion.
result = client.oms.close_order(order_id=order_id)
# result.executed_quantity -> Decimal("750")
# result.unfilled_quantity -> Decimal("250")
result, err := client.OMS.CloseOrder(ctx, orderID)
// result.ExecutedQuantity -> 750
// result.UnfilledQuantity -> 250
GetOrder¶
Retrieves a single order by ID.
ListOrders¶
Queries orders with optional filters. Results are ordered by created_at descending.
orders = client.oms.list_orders(
portfolio_id="PORT-001",
instrument_id="INS-01936d8a-...", # optional
state="ROUTED", # optional
direction="Buy", # optional
created_after="2026-03-01", # optional
created_before="2026-03-27", # optional
limit=50, # default 100
offset=0, # default 0
)
All filter parameters are optional. Supported filters: portfolio_id, instrument_id, state, direction, basket_id, created_after, created_before, limit, offset.
Basket and Order Restructuring¶
CreateBasket¶
Groups orders for coordinated execution. Orders must not already belong to another basket.
basket_id = client.oms.create_basket(
name="Tech Rebalance 2026-03-27",
order_ids=[order_id_1, order_id_2, order_id_3],
)
MergeOrders¶
Merges multiple orders into a single order. Source orders are linked to the merged order via OrderLink.
SplitOrder¶
Splits one order into multiple orders by quantity. Source order is linked to the split orders via OrderLink.
Compliance¶
Pre-Trade Compliance¶
Compliance plugins evaluate rules and publish results via kernel commands. The order-book kernel gates state transitions based on these results.
# Compliance plugin passes pre-trade compliance
client.oms.pass_pre_trade_compliance(order_id=order_id)
# Compliance plugin fails pre-trade compliance with violations
client.oms.fail_pre_trade_compliance(
order_id=order_id,
violations=[
{"rule_id": "R-001", "rule_name": "Max Position Size", "severity": "HARD", "description": "Would exceed 5% single-name limit"},
],
)
# Authorized user overrides a failed check
override_id = client.oms.override_pre_trade_compliance(
order_id=order_id,
reason="CIO approved exception for concentrated position",
approver_id="USER-0042",
)
Post-Trade Compliance¶
Same pattern as pre-trade, applied after execution:
client.oms.pass_post_trade_compliance(order_id=order_id)
client.oms.fail_post_trade_compliance(order_id=order_id, violations=[...])
override_id = client.oms.override_post_trade_compliance(
order_id=order_id, reason="...", approver_id="USER-0042"
)
What-If Compliance Check¶
Simulates compliance for proposed orders without committing state changes.
results = client.oms.check_compliance_what_if(proposed_orders=[
{"portfolio_id": "PORT-001", "instrument_id": "INS-...", "direction": "Buy", "ordered_quantity": 5000},
])
# results[0].passed -> False
# results[0].violations -> [...]
Query Compliance Headroom¶
Returns how much capacity remains before a rule limit is breached.
headroom = client.oms.query_compliance_headroom(
portfolio_id="PORT-001",
rule_id="R-001",
)
# headroom.current_value -> Decimal("3200000")
# headroom.limit_value -> Decimal("5000000")
# headroom.headroom -> Decimal("1800000")
# headroom.headroom_pct -> 0.36
Subscribe to Compliance Events¶
Real-time stream of compliance events, including market-driven breaches.
for event in client.oms.subscribe_compliance(portfolio_id="PORT-001"):
print(event.rule_id, event.event_type, event.severity)
Compliance Rule Management¶
Plugins create and maintain rules via CRUD operations. The kernel stores rules and gates lifecycle transitions.
# Create a rule
rule_id = client.oms.create_rule(
rule_type="concentration_limit",
parameters={"max_pct": 0.05, "scope": "single_name"},
target_accounts=["PORT-001", "PORT-002"],
active=True,
)
# Update a rule (immutable fields: rule_id, deployment_id, created_by, created_at)
client.oms.update_rule(rule_id=rule_id, changes={"parameters": {"max_pct": 0.10}})
# Soft-delete a rule (sets active=False, record retained)
client.oms.delete_rule(rule_id=rule_id)
# Query rules
rules = client.oms.list_rules(portfolio_id="PORT-001", rule_type="concentration_limit")
Allocation¶
Allocation operations create per-account allocations for filled orders.
CreateAllocation¶
allocation_id = client.oms.create_allocation(
order_id=order_id,
account_id="ACCT-001",
portfolio_id="PORT-001",
quantity=500,
)
allocID, err := client.OMS.CreateAllocation(ctx, &oms.CreateAllocationRequest{
OrderID: orderID,
AccountID: "ACCT-001",
PortfolioID: "PORT-001",
Quantity: decimal.NewFromFloat(500),
})
UpdateAllocation¶
GetAllocation¶
Ownership Handoff¶
SendToTrader¶
Transfers order ownership from the PM to the trading desk. Valid only after pre-trade compliance passes.
SendToOperations¶
Transfers order ownership from the trading desk to operations. Valid after the order is closed.
18-State Order Lifecycle¶
CREATED
-> PENDING_PRE_TRADE_COMPLIANCE
-> PRE_TRADE_COMPLIANCE_PASSED
-> SENT_TO_TRADER (PM -> Trader handoff)
-> ROUTED
-> PARTIALLY_FILLED
-> FILLED
-> CLOSED
-> SENT_TO_OPERATIONS (Trader -> Ops handoff)
-> PENDING_POST_TRADE_COMPLIANCE
-> POST_TRADE_COMPLIANCE_PASSED
-> CONFIRMED
-> SETTLED
-> RECONCILED (terminal)
Branching states:
PRE_TRADE_COMPLIANCE_FAILED (from PENDING_PRE_TRADE_COMPLIANCE)
POST_TRADE_COMPLIANCE_FAILED (from PENDING_POST_TRADE_COMPLIANCE)
CANCELED (from any non-terminal state, subject to cancel authority)
REJECTED (terminal, system-initiated)
| # | State | Owner | Description |
|---|---|---|---|
| 1 | CREATED |
PM | Order intent recorded |
| 2 | PENDING_PRE_TRADE_COMPLIANCE |
System | Awaiting compliance evaluation |
| 3 | PRE_TRADE_COMPLIANCE_PASSED |
PM | Cleared for trading |
| 4 | PRE_TRADE_COMPLIANCE_FAILED |
PM | Compliance violation detected |
| 5 | SENT_TO_TRADER |
Trader | PM handed to trading desk |
| 6 | ROUTED |
Trader | Placements created at venue(s) |
| 7 | PARTIALLY_FILLED |
Trader | Some quantity executed |
| 8 | FILLED |
Trader | Full quantity executed |
| 9 | CLOSED |
Trader | Execution complete, unfilled mapped |
| 10 | SENT_TO_OPERATIONS |
Ops | Handed to operations for post-trade |
| 11 | PENDING_POST_TRADE_COMPLIANCE |
System | Awaiting post-trade compliance |
| 12 | POST_TRADE_COMPLIANCE_PASSED |
Ops | Post-trade compliance cleared |
| 13 | POST_TRADE_COMPLIANCE_FAILED |
Ops | Post-trade compliance violation |
| 14 | CONFIRMED |
Ops | Middle office confirmed |
| 15 | SETTLED |
Ops | Custodian settled |
| 16 | RECONCILED |
-- | Terminal state, fully reconciled |
| 17 | CANCELED |
-- | Terminal state, order canceled |
| 18 | REJECTED |
-- | Terminal state, system rejected |