Surqo’s WebSocket server broadcasts new sensor readings to every connected client the moment they arrive from an ESP32 node over MQTT. There is no polling, no delay, and no missed readings — theDocumentation Index
Fetch the complete documentation index at: https://mintlify.com/ricardomb-tech/surqo/llms.txt
Use this file to discover all available pages before exploring further.
WebSocketManager maintains a dictionary of active connections keyed by farm_id and fans out each ingest event to all subscribers for that farm simultaneously. The connection is farm-scoped: each tab or client subscribes to exactly one farm at a time.
The Surqo dashboard and the main landing page (
index.mdx) use this endpoint to power the live sensor feed widgets. Every time a new reading arrives from the field, the dashboard KPI cards, soil moisture chart, and VPD indicator update in real time without a page refresh.Connection Details
| Property | Value |
|---|---|
| Endpoint | wss://surqo-api.fly.dev/api/v1/sensors/ws/live/{farm_id} |
| Auth | JWT token as ?token=<jwt> query parameter |
| Protocol | Standard WebSocket (no subprotocol required) |
| Message format | UTF-8 JSON text frames |
JavaScript Example
Message Types
| type | When sent | Data |
|---|---|---|
initial | Immediately on connection | Last persisted sensor reading (SensorReadingResponse) |
sensor_reading | When a new MQTT reading arrives | Partial reading object with core sensor metrics |
initial message containing the most recent reading stored in the database. This allows the UI to render current values immediately without a separate REST call. Every subsequent sensor_reading message carries the live payload broadcast by the MQTT consumer as readings arrive from the field.
Close Codes
| Code | Reason |
|---|---|
4001 | JWT token missing or invalid |
4002 | Invalid farm UUID format |
4003 | Farm not found or not owned by the authenticated user |
1000 normal, 1001 going away, etc.) are also used for non-auth disconnects.
TypeScript Frontend Utility
The frontend wraps the WebSocket in a helper that handles message routing:NEXT_PUBLIC_WS_URL=wss://surqo-api.fly.dev in production and ws://localhost:8000 in local development.
Reconnection Guidance
If no new MQTT readings arrive — for example, the ESP32 is in deep sleep for its default 15-minute cycle — the WebSocket stays open but idle. The server does not send keepalive pings. For production use, implement a heartbeat check on the client side and reconnect automatically if no message is received within a reasonable window (e.g. 20 minutes).