FIX Order Entry
The FIX order-entry session accepts order placement, cancellation, and cancel-replace flows.
FIX authentication is session/agent-based: Logon binds the engine account
and HMAC credential, and submitted actions carry a placeholder signature
rather than a per-message client crypto signature. ClOrdID(11) is threaded
into the signed ActionPayload, so it is part of the action signing hash and
influences the derived OrderId.
Acknowledgement model
FIX order entry returns a synchronous admission acknowledgement, then the real working and terminal states arrive asynchronously over the drop-copy stream:
NewOrderSinglereturns a synchronous PendingNew ExecutionReport (35=8,150=A,39=A) withExecIDof the formfix-pending-new-{seq}. This is an admission acknowledgement, not a fill.OrderCancelReplaceRequestsubmits one atomic(Spot)QuoteReplaceaction and returns PendingReplace (35=8,150=E,39=E) withExecIDof the formfix-pending-replace-{seq}.OrderCancelRequestreturns150=4/39=4.- Actual fills, partial fills, cancels, and other terminal order states are
emitted later through the drop-copy / execution stream to sessions scoped
drop_copy/dropcopy. See Drop copy.
There is no immediate "New" fill acknowledgement; clients must reconcile working and terminal state from the drop-copy stream.
New order
Use NewOrderSingle (35=D) for standard orders.
| Field | FIX tag | Required | Notes |
|---|---|---|---|
| ClOrdID | 11 | Yes | Client order id; threaded into the signed ActionPayload and influences the derived OrderId |
| Account | 1 | Logon | Engine account is bound at Logon |
| Symbol | 55 | Yes | Numeric Senticore marketId |
| Side | 54 | Yes | 1 buy, 2 sell |
| OrdType | 40 | Yes | 1 market, 2 limit |
| OrderQty | 38 | Yes | Integer quantity in engine units |
| Price | 44 | Limit only | Integer price in micros |
| TimeInForce | 59 | Optional | empty, 0, or 1 = session GTC; 3 IOC; 4 FOK; unsupported values reject |
| Book | 9100 | Prediction/binary only | Required for prediction/binary markets: YES or NO; omit for spot markets |
| STP override | 7928 | Optional | 1 cancel maker, 2 cancel taker, 3 reject, 4 skip self |
If tag 7928 is absent, the effective default is cancel taker. An
account/credential policy may override that default, and an explicit valid
order value has highest priority. Unknown values are rejected as
invalid_stp_mode; they are never silently mapped to another mode. Post-only
cross detection runs before STP, including a cross against the same account.
TimeInForce(59)=6/GTD and ExpireTime(126)/ExpireDate(432) are rejected on
this path rather than silently downgraded. Post-only and reduce-only flags are
not carried through FIX ExecInst(18); use BSL/FIXP or signed HTTP actions when
those semantics are required.
Cancel
Use OrderCancelRequest (35=F) with the original ClOrdID and a new cancel
request id. The gateway resolves OrigClOrdID(41) through persisted FIX order
references for the session. The cancel acknowledgement is returned as an
ExecutionReport with 150=4/39=4.
Cancel retries converge: canceling a known, owned order that is already
canceled or filled succeeds without changing state. An unknown order id
still returns not found, and an order owned by another account still returns
unauthorized.
Cancel-replace
Use OrderCancelReplaceRequest (35=G) for atomic amend flows. If the replace is
rejected, the original order remains active unless the rejection explicitly
states otherwise.
The current implementation submits one atomic QuoteReplace or
SpotQuoteReplace action with one nonce. Either the cancel and replacement both
apply, or the group rolls back. Cancel-replace returns the synchronous
PendingReplace ExecutionReport (35=8, 150=E, 39=E) for the replacement
order. Clients must reconcile final order state from the async drop-copy stream
and should not assume queue-priority amend semantics.
Status and mass cancel
| MsgType | Purpose |
|---|---|
H | OrderStatusRequest by ClOrdID(11) or OrderID(37) |
q | OrderMassCancelRequest, optionally filtered by Symbol(55) and Side(54) |
AF | OrderMassStatusRequest, optionally filtered by Symbol(55) and Side(54) |
AF returns one or more ExecutionReport(35=8) messages when matching open
orders exist. If the request is valid but the filtered set is empty, the gateway
returns BusinessMessageReject(35=j) with RefMsgType(372)=AF and a
no open orders text. Treat this as an empty terminal response and continue the
session.
Rejections
Malformed messages and general application-level rejections return
BusinessMessageReject or OrderCancelReject. A valid NewOrderSingle blocked
by the global trading halt or degraded-ledger admission gate returns a rejected
ExecutionReport(35=8) with ExecType(150)=8, OrdStatus(39)=8,
OrdRejReason(103)=99 (Other), and a human-readable Text(58).
The stable Senticore reason is carried separately in
SenticoreRejectReason(9101): 103 means TradingHalted, and 104 means
LedgerDegraded. Do not interpret the value of custom tag 9101 as the value
of standard FIX tag 103. Pre-trade business rule failures map to the error
concepts documented in Error Model.
Senticore extension areas
| Extension | Purpose |
|---|---|
9100 | Prediction book, YES or NO |
9101 | Outbound stable Senticore reject reason (103 trading halted, 104 ledger degraded) |
7928 | Self-trade-prevention override |