Stop polling: your trading bot is acting on stale prices
Stop polling. How to stream tickers, order books, trades, and your own orders over WebSockets with CCXT — and what the library does for you under the hood.
By CCXT Team
The first version of every bot polls: call fetchTicker in a loop, sleep, repeat. It works —
until you want more than one symbol, or faster reactions, or you hit the exchange's rate
limit. Polling gives you a snapshot per request; markets move between your requests.
Exchanges solve this with WebSocket streams: you subscribe once and the exchange pushes every
update to you. CCXT ships WebSocket support in the same package you already have, in all six
languages, behind an API that mirrors the REST one: where REST has fetchOrderBook,
WebSockets have watchOrderBook.
The watch loop
A watch* method resolves every time a new update arrives, so real-time code is just a loop:
import ccxt from 'ccxt';
const exchange = new ccxt.pro.binance();
while (true) {
const orderbook = await exchange.watchOrderBook('BTC/USDT');
console.log(orderbook.bids[0], orderbook.asks[0]);
}The first call opens the connection and subscribes; every following call just waits for the
next update. The same pattern works for watchTicker, watchTrades, watchOHLCV, and — with
API keys — watchBalance, watchOrders, and watchMyTrades for your own fills.
What CCXT does for you under the hood
Raw exchange WebSocket APIs are messy, and this is where most hand-rolled integrations go
wrong. When you call watchOrderBook, CCXT:
- Maintains the book from deltas. Most exchanges send an initial snapshot and then incremental updates. CCXT applies them in order, checks sequence numbers, and hands you a complete, sorted order book every time — not a raw diff message.
- Manages connections. One WebSocket per stream group, shared across your subscriptions. Subscribe to fifty symbols and CCXT multiplexes them properly for that exchange.
- Reconnects and resubscribes. Exchanges drop connections routinely (Binance, for example, cuts every connection after 24 hours). CCXT reconnects, re-authenticates, and re-subscribes automatically; your loop just keeps receiving updates.
- Handles keepalives — ping/pong frames, heartbeat messages, and the exchange-specific quirks you'd otherwise discover at 3 a.m.
Many symbols, many exchanges
For dashboards, scanners, and market making you rarely want a single stream. watchTickers
subscribes to a list of symbols in one shot and returns a structure keyed by symbol, updated
as events arrive:
const symbols = ['BTC/USDT', 'ETH/USDT', 'SOL/USDT'];
while (true) {
const tickers = await exchange.watchTickers(symbols);
console.log(tickers['BTC/USDT'].last);
}There are ...ForSymbols variants (watchTradesForSymbols, watchOrderBookForSymbols,
watchOHLCVForSymbols) when you need one loop over many markets, and running several
exchanges concurrently is just multiple loops — one async task per exchange in
JavaScript/Python/PHP/C#/Java, one goroutine per exchange in Go.
Watching your own orders
The same mechanism covers private data, which is how bots track fills without polling
fetchOrder:
const exchange = new ccxt.pro.binance({ apiKey: KEY, secret: SECRET });
while (true) {
const orders = await exchange.watchOrders();
for (const order of orders) {
console.log(order.id, order.status, order.filled);
}
}Practical notes
- Check support first. Not every exchange implements every stream. Capability flags tell
you at runtime:
exchange.has['watchOrderBook'],exchange.has['watchOrders'], and so on. - Always
close()on shutdown. WebSocket connections hold sockets and background tasks; callawait exchange.close()when your program exits. - REST still has a job. Placing and canceling orders, fetching history, and one-shot queries are REST's territory. The standard architecture is: WebSockets for state you watch (prices, books, fills), REST for actions you take.
- Throughput beats latency for most people. The realistic win of WebSockets is not microseconds — it's watching hundreds of markets simultaneously without touching a rate limit, which is simply impossible with polling.
If you're building toward strategies that need this — scanners, market making — the follow-up posts pick up exactly here: arbitrage strategies and market making.