Skip to content

WebSocket Error Handling

Error handling in WebSocket applications is essential for building a robust, predictable real-time experience. Since WebSockets are persistent and event-driven, your system must clearly communicate both protocol-level and application-level errors.

This page covers error categories, message formats, best practices, and how to gracefully handle failures.


โ— 1. Types of Errors

Type Description Examples
Connection-level Issues during connection or handshake Invalid auth token, unsupported path
Application-level Errors in event logic or payload processing Invalid room ID, permission denied
Transport-level Network failures, client disconnects, timeouts Lost connection, ping timeout

๐Ÿงฑ 2. Error Message Format

Your application should return errors in a consistent JSON structure:

{
  "type": "error",
  "data": {
    "code": 4001,
    "message": "Room not found"
  },
  "meta": {
    "request_id": "abc-123",
    "timestamp": "2025-08-04T12:00:00Z"
  }
}

Field Definitions

Field Description
type Always "error"
data.code Numeric error code
data.message Human-readable error message
meta Optional context (timestamp, request ID)

๐Ÿ”ข 3. Custom Error Codes

Code Meaning Use Case
4000 Bad request Malformed JSON or missing fields
4001 Not found Room, user, or resource not found
4002 Invalid action Sending message to closed room
4003 Unauthorized Token missing or expired
4004 Forbidden User lacks permission
4005 Rate limited Too many requests
5000 Internal server error Unexpected backend failure

๐Ÿšจ 4. Closing with Errors

If a critical error requires closing the connection, send an error message first, then close:

Server:

{
  "type": "error",
  "data": {
    "code": 4003,
    "message": "Authentication failed"
  }
}

Then:

await websocket.close(code=4003)

Clients should listen for both message and close events.


๐Ÿ›  5. Client Handling Example (JavaScript)

socket.onmessage = (event) => {
  const msg = JSON.parse(event.data);

  if (msg.type === "error") {
    console.error(`[WebSocket Error] ${msg.data.code}: ${msg.data.message}`);
    alert("Something went wrong: " + msg.data.message);
  }
};

socket.onclose = (event) => {
  if (event.code === 4003) {
    alert("You were disconnected due to authentication failure.");
  }
};

โœ… 6. Best Practices

  • Use structured error responses with consistent codes.
  • Never expose stack traces or internals in messages.
  • Log all server-side errors with context and traceback.
  • Differentiate between recoverable and fatal errors.
  • Allow clients to retry or reconnect after soft failures.

๐Ÿงช 7. Testing Your Error Handling

  • Simulate invalid messages (e.g., bad JSON, unknown type).
  • Force auth failures (e.g., expired tokens).
  • Disconnect network mid-session.
  • Exceed rate limits to test throttling responses.
  • Monitor logs for uncaught exceptions.

๐Ÿ”š Next Steps