| Quote request created | — (no dedicated “created” event; the stream opens after creation and the first frame is best_quote, often null) | quote_request | not delivered on this channel — WebSocket starts at quote acceptance | not delivered on this channel — webhooks are post-trade only | quote request status: "active" — GET /v1/quote-requests/{id} |
| Quote updated (price changes, or legs/amount edited) | best_quote | quote_request:updated — only fires when the request itself changes (PATCH); no MM stream event exists for an individual quote submission, yours or a competitor’s | not delivered on this channel | not delivered on this channel | quote request version/book_seq increments; status stays "active" |
| Quote accepted / committed | status (status: "committed") followed immediately by the terminal committed event, then the stream closes | quote_request_expired (reason: "committed"; won: true for the winning MM, false for every other MM) | quote:accepted + mm_quote:accepted — MM only. Nothing pushes to the user on WebSocket; they already have the outcome from the synchronous commit response | parlay.status_changed (status: "accepted", accepted_quote_id set) | RFQ status: "accepted" — GET /v1/rfqs/{id} |
| Confirmed by maker | not delivered on this channel — the stream already closed at commit | not delivered on this channel | quote:confirmed — MM only. No user-facing WebSocket event marks this step specifically | parlay.status_changed (status: "confirmed") | RFQ status: "confirmed" |
| Executed on-chain | not delivered on this channel | not delivered on this channel | quote:executed (MM channel) and position:created (rfq:{rfq_id} channel — collateral locked, position_pda set) | parlay.status_changed (status: "executed") | RFQ status: "executed" |
| Settled | not delivered on this channel | not delivered on this channel | position:settled (outcome, tx_signature) | position.settled — the terminal outcome event; parlay.status_changed’s status values stop at executed/cancelled and never include "settled" | RFQ status: "settled" |
| Exited early (cashout auction) | not on this stream — see the separate cashout stream, whose own terminal status event reports "committed" | cashout_request announces only the opening of the auction, broadcast to every market maker; there is no SSE event for its completion — see Early cashout | position:bought_back on rfq:{rfq_id}, when the winning bid closes the position. Nothing is delivered when a bid instead acquires the position — see the transfer gap below | position.bought_back (amount, mm_pays_user, tx_signature) on a close; position.transferred is attributed to the seller only | Depends on the lane. A close gives RFQ status: "bought_back" with the cashout object populated. A transfer leaves the position active and repoints ownership to the buyer, so the RFQ does not become bought_back — do not wait on that state to detect an acquisition. |
| Cancelled | cancelled — quote request abandoned pre-commit via Cancel | quote_request_expired (reason: "cancelled") | position:cancelled — only for a post-commit cancellation (e.g. the maker missed the confirmation deadline); a pre-commit quote request cancellation never reaches a position, so nothing fires here | not delivered pre-commit; post-commit fires both parlay.status_changed (status: "cancelled") and position.cancelled together (dedupe on X-Totalis-Event-Id) | quote request status: "cancelled" pre-commit, or RFQ status: "cancelled" post-commit |
| Expired | expired — quote request’s TTL lapsed with no commit | quote_request_expired (reason: "expired") | quote:expired — a specific MM’s accepted quote lapsed before confirmation; there’s no distinct WebSocket event for a whole RFQ expiring | not delivered on this channel — no webhook event exists for expiry, before or after commit | quote request status: "expired" pre-commit, or RFQ status: "expired" post-commit |