Broker Token Refresh and Connection Failures
A recovery playbook for expired authorization, reconnect storms, stale sockets, ambiguous orders, and safe rearming across broker automation APIs.
A refreshed token is not a recovered trading session
Token renewal restores authorization, but the client must still replace stale connections and reconstruct broker state.
Automated trading systems often report connected when an HTTP health check succeeds with a new token. That can be dangerously incomplete. An older WebSocket may remain closed or authenticated under obsolete state, subscriptions may be missing, and order updates may have occurred during the gap. Local working orders and positions can therefore disagree with the broker even though the next REST request succeeds.
Use a recovery state machine. On an authentication or connection fault, stop accepting new order mutations, keep durable signals queued or rejected according to policy, and elect one session owner to refresh. Recreate streams through the documented flow, resubscribe, retrieve current orders, executions, and positions, resolve uncertain submissions, and only then mark the deployment ready.
Never replay an order queue immediately after login
First determine whether any queued or timed-out order already reached the broker. Replaying before reconciliation can duplicate exposure.
Classify the failure before retrying
Separate expired authorization, invalid credentials, rate limits, network loss, stream gaps, broker rejects, and policy disablement.
A 401-like authorization response, an HTTP 429, a transport timeout, a clean WebSocket close, a missed heartbeat, and an order rejection demand different actions. Refreshing on every error can create a login storm and obscure the original cause. Parse the documented status and response body, preserve broker error fields, and attach the failure to the active credential generation and connection ID.
Invalid or revoked credentials require operator action; repeated automated refresh is unlikely to help. Rate limiting requires documented backoff. Network loss requires reconnect and state recovery. An application schema error requires a code or configuration fix. A provider policy or account-stage disablement must not be retried at all. Unknown errors should fail closed with bounded attempts and alerting.
| Signal | Likely class | Safe response |
|---|---|---|
| Authorization expired | Session lifecycle | Single-flight documented renewal, then reconcile |
| Credential rejected repeatedly | Revoked, invalid, or ineligible | Disable and require operator review |
| HTTP 429 or penalty data | Rate limit | Honor official wait and retry instructions |
| Socket disconnected | Transport or service | Reconnect, resubscribe, backfill state |
| Order failure reason | Broker or account rejection | Do not refresh unless documentation identifies auth |
| Account stage changed | Policy and identity | Disarm and perform fresh approval |
Make refresh a single-flight operation
Exactly one session manager should renew authorization while all other requests wait, fail, or queue behind the same result.
Without coordination, every strategy that receives an authorization error can start its own renewal. That multiplies calls, races token generations, and can trigger strict authentication limits. Tradovate's rate-limit documentation, for example, identifies specific limits for access-token and renewal endpoints and warns about penalty behavior. The architecture should centralize authentication rather than let each order worker log in independently.
Assign a monotonically increasing credential generation. Requests read the current generation and, on expiry, join the same refresh promise. When renewal succeeds, atomically publish the new token and generation, invalidate old connection objects, and prevent late refresh results from overwriting newer credentials. When renewal fails definitively, open a circuit breaker, disarm execution, and notify an operator without printing secrets.
- 1
Elect one owner
Use an in-process mutex or distributed lock appropriate to the deployment.
- 2
Join concurrent callers
Make waiting requests observe one refresh result instead of initiating more logins.
- 3
Publish atomically
Replace token and generation together, then invalidate old clients.
- 4
Bound failure
Back off, trip a breaker, and require operator action after definitive rejection.
Follow each broker's documented lifecycle
Do not impose one generic OAuth refresh model on Tradovate, ProjectX, NinjaTrader, Rithmic, CQG, or another interface.
Tradovate documents access-token operations and rate-limit behavior, including penalty tickets for some endpoint limits. Topstep's ProjectX troubleshooting notes that session tokens expire and tells clients to refresh rather than reuse an old token, while ProjectX documents its own authenticated API limits. NinjaTrader's Trader API, Rithmic interfaces, and CQG products each have their own authorization and connection contracts. Use their current references and approved SDK behavior.
Differentiate a long-lived application secret or API key from the short-lived session material derived from it. Do not regenerate or rotate a user's root key every time an access token expires unless the official process says so. Conversely, do not reuse expired session tokens indefinitely. Store root secrets narrowly, hold access tokens in protected memory where practical, and log only fingerprints and generation numbers.
DISCONNECTED
-> AUTHENTICATING
-> AUTHENTICATED
-> CONNECTING_STREAMS
-> RECONCILING
-> READY
ANY AUTH FAILURE -> REFRESHING | DISABLED
ANY STREAM GAP -> RECONNECTING -> RECONCILING
READY is impossible while broker state is staleReconnect streams with a gap-recovery plan
Create a new authenticated stream, restore subscriptions, and backfill order and position state before consuming live events as complete.
A socket open event proves transport, not continuity. Record the last processed event sequence or broker identifier when the interface provides one. After reconnect, use supported snapshots or queries to obtain working orders, recent executions, and positions. Apply the snapshot and subsequent stream events through an ordering strategy appropriate to the API so late messages cannot roll state backward.
If the broker does not expose a replay cursor, use a conservative overlap window and deduplicate by broker-native event identifiers. Keep the strategy disarmed until snapshot and stream agree. Replace the old socket rather than retaining two active consumers that can produce duplicate updates. Heartbeats should detect liveness, while a separate freshness metric proves that account state is advancing.
- Tag every stream with credential generation and connection ID.
- Ignore late events from superseded connections after a controlled cutover.
- Resubscribe to accounts, orders, positions, and market data explicitly.
- Backfill the disconnect window with supported broker queries or snapshots.
- Require state freshness and reconciliation, not merely socket-open status.
Resolve orders that were in flight during failure
Treat a lost submission response as unknown and query broker state using account, contract, time, and correlation data before retrying.
The client can lose connectivity after the broker accepts a request but before its acknowledgement arrives. Marking that request failed and replaying it can create a second order. Persist intent and a unique client correlation before submission. On recovery, search the supported order and execution state for that correlation or otherwise reconcile the account and contract carefully.
If the interface cannot prove the result, escalate the event as unresolved and block a conflicting strategy action. A human can inspect the broker-native platform and decide whether to cancel, flatten, or leave the position. Never automatically flatten solely because local state is uncertain; an extra flatten can reverse exposure if the assumed position was wrong. Establish actual broker state first.
Unknown is safer than an invented answer
Preserve uncertainty in the data model. Operators need to see unresolved intent, possible live orders, and the last trustworthy account snapshot.
Monitor the lifecycle and rehearse it
Track token generation, refresh outcomes, reconnects, stream freshness, unresolved orders, and reconciliation duration without logging credentials.
Useful metrics include time until known expiry where the API exposes it, refresh attempts and outcomes, requests waiting on refresh, active connection count, reconnect reason, last account event, state age, unresolved intent count, and whether the deployment is armed. Alert on repeated refresh, two concurrent session owners, stale account state, and any transition that remains in reconciling beyond the system's tested expectation.
Run drills in the permitted test environment: expire or invalidate a session, interrupt the stream, restart during a working order, inject a duplicate event, trigger a documented rate limit carefully, and rotate the root credential. Verify that the system disarms, refreshes once, reconstructs state, and requires policy review where appropriate. Document a manual recovery path for times when authorization cannot be restored.
- Dashboards expose readiness, not secrets.
- Refresh and reconnect operations use bounded backoff with jitter.
- Every order intent survives process restart before network submission.
- No queued event replays until broker orders and positions reconcile.
- Definitive credential, account, or policy failures require human review.
Sources and methodology
HexTrade Research uses official product, exchange, regulator, and vendor documentation. Policies and platform behavior can change; follow the linked source and verify current terms before trading.
- 1.Tradovate API key quick setup — Tradovate, accessed Aug 30, 2026
- 2.Tradovate API rate limits — Tradovate, accessed Aug 30, 2026
- 3.ProjectX Gateway API documentation — ProjectX, accessed Aug 30, 2026
- 4.ProjectX API rate limits — ProjectX, accessed Aug 30, 2026
- 5.TopstepX API access — Topstep, accessed Aug 30, 2026
- 6.NinjaTrader developer APIs — NinjaTrader, accessed Aug 30, 2026
- 7.Rithmic APIs — Rithmic, accessed Aug 30, 2026
Frequently asked questions
Should every 401 trigger a broker login?
No. Follow the broker's documented status semantics and centralize renewal. One session manager should refresh once; repeated rejection should trip a breaker and require review rather than create a login storm.
Can I keep the old WebSocket after refreshing a token?
Do not assume it is valid or complete. Follow the API's documented reauthentication behavior; commonly the safe design replaces stale streams, restores subscriptions, and reconciles state before readiness.
Should timed-out orders be retried after reconnect?
Not until broker state proves the original did not arrive. A lost response can hide an accepted order. Treat it as unknown and reconcile orders, executions, and position first.
Is an API key the same as an access token?
Not necessarily. A durable application key or secret can be used to obtain shorter-lived session authorization. Follow the exact broker model and never rotate root credentials merely from a generic assumption.
Next step
Put the research into a controlled workflow
Start small, verify the broker and account rules, and keep risk controls between every signal and live order.
See supported brokersContinue reading
Educational content only. Futures are leveraged products and can produce losses greater than the amount you expected to risk. This article is not financial, legal, or prop-firm compliance advice.