-
Notifications
You must be signed in to change notification settings - Fork 12
Order Management Service
tien.nguyen edited this page Jul 30, 2026
·
1 revision
The Order Management Service (OMS) is the central core service of the Emporia Trading Platform. It acts as the authoritative ledger and state machine manager for all equity order lifecycles, execution fill roll-ups, idempotency records, and order domain event broadcasting.
-
Directory:
order-management-service -
HTTP Port:
8086 -
Database Boundary:
emporia_order_data(PostgreSQL) -
Primary Roles:
- State machine authority for
TradingOrderentities. - Idempotent handler for order placement (
CREATE), modifications (MODIFY), and cancellations (CANCEL). - Execution fill processor (
FILL), deduplicating venue executions. - CQRS query API provider (
GET /api/orders).
- State machine authority for
flowchart TD
subgraph InboundEvents ["Inbound Kafka Channels"]
K1[["emporia.order.commands.v1"]] -->|OrderCommand| OCH["OrderCommandHandler"]
K2[["emporia.execution.commands.v1"]] -->|ExecutionCommand| ECH["ExecutionCommandHandler"]
end
subgraph CoreOMS ["Order Management Service Core"]
OCH --> IdempotencyCheck{"Processed Before?"}
IdempotencyCheck -- Yes --> CachedOutcome["Return Cached ProcessingOutcome"]
IdempotencyCheck -- No --> OrderSM["TradingOrder Entity (State Machine)"]
ECH --> DeduplicateFill{"Execution Ref Exists?"}
DeduplicateFill -- Yes --> IgnoreFill["Ignore Duplicate Venue Fill"]
DeduplicateFill -- No --> OrderSM
OrderSM --> DB[("PostgreSQL: emporia_order_data")]
end
subgraph OutboundEvents ["Outbound Event Channels"]
OrderSM --> K3[["emporia.orders.v1 (OrderDomainEvents)"]]
OCH --> K4[["emporia.order.results.v1 (OrderCommandResult)"]]
end
subgraph RestClients ["REST API Clients"]
WebUI["React 19 Trading Dashboard"] -->|GET /api/orders| QueryCtrl["OrderQueryController"]
QueryCtrl --> DB
end
Handles order command records produced by order-command-service:
-
CREATE: Instantiates a newTradingOrderinPENDING_NEWstatus, validates lot/tick sizes, saves to DB, advances toLIVE, and publishesOrderCreatedtoemporia.orders.v1. -
MODIFY: Validates new quantity/price parameters against static data constraints and updates active orders. -
CANCEL: InvokesTradingOrder.requestCancel()to transition order toCANCELLED. -
CANCEL_ALL: Performs bulk cancellation of active orders for a trading desk. -
Idempotency Guard: Checks
ProcessedCommandRepositorybycommandId. If a command was previously processed, it immediately returns the cachedProcessingOutcomewithout re-executing logic.
Processes venue execution updates produced by execution-service or exchange matching engines:
-
FILL: InvokesTradingOrder.applyFill(fillQuantity, fillPrice). Recalculates traded quantity, remaining quantity, and volume-weighted average price (VWAP). -
REJECT: Transitions order toREJECTEDstatus with failure error messages. -
CANCEL: Confirms venue cancellation viaTradingOrder.confirmCancel(). -
Fill Deduplication: Checks
ExecutionRepository.existsByExecutionReference()to ignore duplicate venue fill messages.
Synchronized domain methods ensure thread safety under high concurrency:
-
Quantity Conservation Invariant:
quantity = tradedQuantity + remainingQuantity -
Volume-Weighted Average Price (VWAP): Recalculates average price on each fill:
P_new = ((P_prev Γ Q_prev) + (P_fill Γ ΞQ)) / (Q_prev + ΞQ) -
Late Fill Safety: Accepts fills on orders even if in
CANCELLEDstatus, ensuring zero execution accounting is lost.
| Table Name | Entity Class | Purpose |
|---|---|---|
trading_orders |
TradingOrder |
Primary table storing order status, side, quantities, VWAP price, user ID, and desk ID. |
order_events |
OrderEvent |
Immutable audit trail storing domain state events (OrderCreated, OrderFilled, etc.). |
executions |
Execution |
Log of all execution fills received from market venues with unique execution references. |
processed_commands |
ProcessedCommand |
Idempotency table storing command IDs and correlated command results. |
-
Optimistic Locking: JPA
@Versionannotation onTradingOrdertriggersOptimisticLockExceptionif two threads attempt to mutate the same order record concurrently. -
Pessimistic Locking:
TradingOrderRepository.findByIdWithLock()executesSELECT ... FOR UPDATEfor critical execution fill roll-ups. -
Verified Concurrency: Validated under 200 controlled thread schedule iterations by Fray (
TradingOrderFraySpec) and PostgreSQL container concurrency specs (TradingOrderPostgresConcurrencySpec).
- Trading Terminology Glossary
- Order Lifecycle & Validation
- Order Routing & SOR
- Market Data & Pricing
- Portfolio & Risk Management
- Architecture & Order Flow
- Static Data Service
- Market Data Service
- Order Command Service
- Order Management Service (OMS)
- Execution Service
- Portfolio Service
- Design Patterns
- Microservices Overview
- Exchange-Core Integration
- Testing & Verification
- Deployment & Operations
- Repository: emporia
- Tech Stack: Java 21 | Spring Boot 4.0.7 | React 19 | Kafka | gRPC
- Coverage: 91.95% JaCoCo