Recipe: Long-polling design & tradeoffs
When WebSockets are blocked or impractical, long-polling keeps clients in sync with minimal infrastructure.
Core loop
Client Server
| |
|--- GET /poll?since=ts -------->|
| |-- wait for event or timeout
|<-- 200 { events[] } ----------|
| |
|--- GET /poll?since=new_ts --->|The client holds an open HTTP connection. The server blocks until data is available or a configurable timeout expires, then responds. The client immediately reconnects.
Tradeoffs
- Latency — bounded by poll interval + network RTT. Acceptable for dashboards and license-sync flows.
- Connection churn — every cycle tears down and rebuilds TCP/TLS. HTTP/2 multiplexing mitigates this.
- Server cost — blocked threads or async tasks per client. Use an event bus (Redis pub/sub, in-memory channel) to unblock efficiently.
- Ordering — a monotonic cursor (timestamp or sequence number) prevents gaps. Store the cursor client-side.
When to use
Prefer long-polling when you control both client and server, need real-time updates, and cannot deploy WebSocket infrastructure. Meridian uses it for license-status push and config hot-reload behind restrictive corporate firewalls.