Skip to main content
The stream is not live yet. Connections are refused until it is enabled.
The WebSocket stream at wss://live.trendlinelabs.ai/public/v1/stream sends live book, price and trades frames for the markets you subscribe to: book and price frames on the venues whose order books are served, trades frames on the venues whose trades are served (Venues). It needs a key granted market:read, sent once, at the handshake, as Authorization: Bearer <key>. The stream takes no query parameters. The stream is not live yet: until it is enabled, a handshake is refused. Use the stream when you need every change as it happens; use the REST routes for a one-off read, history (candles) and anything you poll. Both read the same market data.

Connect

Browsers cannot set the Authorization header on a WebSocket, so connect from your server.

Subscribe

Send JSON messages with an op and your own id; the answer to each echoes that id. A channel’s type is book (the order book to depth levels per side, 1 to 10, default 10), price (the top of book on each side) or trades (prints). market is the market’s universal_id and venue is the venue its leg trades on, as on the REST routes. A message is at most 16384 bytes, and a connection may send 10 messages a second (bursts to 20).
Each result carries a sub id for that channel, or an error (see Codes in frames).

Frames

Every frame has v (the protocol version, 1), type, seq (rising by exactly 1 per frame on the connection) and ts (when it was sent, ms). Data frames carry the sub they belong to. book: the whole book to your depth, both outcomes, with the same freshness fields as the REST order book.
price: the best bid and ask on each side.
trades: the first frame is a snapshot of recent trades (snapshot: true), then each new print.
status: a subscription’s state, live once frames flow, or a code from the table below.
The server also sends a heartbeat every 15 seconds, and a pong for each ping.

Handshake refusals

A refused handshake is an HTTP answer carrying the same error envelope as the REST routes. Its auth refusals (unauthorized, access_not_granted, tier_required, insufficient_scope, ip_not_allowed, rate_limited) are described on Errors.

Codes in frames

Frame codes carry no HTTP status. Each arrives in the frame named in the first column.

Close codes

Reading the stream

Treat every book and price frame as complete; append trades, and when a trades frame says gap: true, read the REST trades route if you need the missing prints. A Limitless trade can arrive about a minute after its ts_ms (an estimate from one observed trade). Limitless trades subscriptions are not affected by the Limitless liveness check that applies to book and price subscriptions. On a gap in seq, a close, or no heartbeat for two heartbeat intervals, reconnect and subscribe again. Read your frames as they arrive: frames you have not read count against your connection’s bound, and unsubscribing lowers that bound at once, so a client that stops reading can be closed 4408. Closed statuses not yet read are also capped across the server (closing_cap): past it, the connection whose unread ones have waited longest is closed 4408, never one for statuses that have just closed. GET https://live.trendlinelabs.ai/public/v1/stream/protocol returns the protocol’s current numbers: the message and channel-change rates, the heartbeat interval, the connection’s bound and the closed-status cap. The free plan allows 2 open stream connections per key at a time, counted across all our stream servers, and 50 subscriptions per connection. A third connection is refused at the handshake with 429 connection_limit, and a 51st subscription on one connection answers subscription_limit.