Skip to main content

Heartbeat

Send a ping every 30 seconds to keep the connection alive:
{
  "type": "ping",
  "timestamp": 1769056941234
}
The server responds with:
{
  "type": "pong",
  "timestamp": 1769056941234
}
If the server receives no ping within 60 seconds, it closes the connection.

Reconnection strategy

Network disruptions are inevitable. Your client should handle disconnections gracefully with exponential backoff:
  1. On disconnect, wait a short initial delay (e.g., 1 second).
  2. On each failed reconnection attempt, double the delay up to a maximum (e.g., 30 seconds).
  3. Add random jitter to prevent thundering herd when many clients reconnect simultaneously.
  4. After reconnecting, re-authenticate and re-subscribe to all channels on that connection.
const BASE_DELAY = 1000;
const MAX_DELAY = 30000;
let attempt = 0;

function reconnect() {
  const delay = Math.min(BASE_DELAY * Math.pow(2, attempt), MAX_DELAY);
  const jitter = delay * 0.5 * Math.random();
  setTimeout(() => {
    attempt++;
    connect(); // your connection logic
  }, delay + jitter);
}

function onConnected() {
  attempt = 0; // reset on successful connection
  authenticate();
  resubscribe();
}

Best practices

  • One connection per endpoint family — share one book connection for orderbook channels and one nonbook connection for everything else, rather than opening one connection per subscription.
  • Subscribe in batches — send all channels in a single public/subscribe message rather than one message per channel.
  • Handle backpressure — keep your message handler lightweight. Offload heavy processing (database writes, analytics) to a background queue.
  • Track subscriptions client-side — maintain a local registry of active subscriptions so you can re-subscribe after reconnection.
  • Use compression — enable brotli compression to reduce bandwidth, especially for high-frequency channels like TRADE and BLOCK_BOOK_SNAPSHOT.