Skip to content

WebSockets

Background

WebSockets allow you to communicate in real time with your Cloudflare Workers serverless functions. For a complete example, refer to Using the WebSockets API.

Constructor

JavaScript
// { 0: <WebSocket>, 1: <WebSocket> }
let websocketPair = new WebSocketPair();

The WebSocketPair returned from this constructor is an Object, with two WebSockets at keys 0 and 1.

These WebSockets are commonly referred to as client and server. The below example combines Object.values and ES6 destructuring to retrieve the WebSockets as client and server:

JavaScript
let [client, server] = Object.values(new WebSocketPair());

Methods

accept

  • accept(options?)
    • Accepts the WebSocket connection and begins terminating requests for the WebSocket on Cloudflare's global network. This effectively enables the Workers runtime to begin responding to and handling WebSocket requests.

Parameters

  • options object optional

    • An optional configuration object with the following properties:

      • allowHalfOpen boolean optional — When true, the runtime will not automatically send a reciprocal Close frame when a Close frame is received from the peer. Instead, readyState remains CLOSING until you explicitly call close(). This is useful for WebSocket proxying where you need to coordinate the close across both sides of the proxy. Defaults to false.

addEventListener

  • addEventListener(eventWebSocketEvent, callbackFunctionFunction)
    • Add callback functions to be executed when an event has occurred on the WebSocket.

Parameters

  • event WebSocketEvent

    • The WebSocket event (refer to Events) to listen to.
  • callbackFunction(messageMessage) Function

    • A function to be called when the WebSocket responds to a specific event.

close

  • close(codenumber, reasonstring)
    • Close the WebSocket connection.

Parameters

  • codeinteger optional

    • An integer indicating the close code sent by the server. This should match an option from the list of status codes provided by the WebSocket spec.
  • reasonstring optional

    • A human-readable string indicating why the WebSocket connection was closed.

send

  • send(messagestring | ArrayBuffer | ArrayBufferView)
    • Send a message to the other WebSocket in this WebSocket pair.

Parameters

  • messagestring
    • The message to send down the WebSocket connection to the corresponding client. This should be a string or something coercible into a string; for example, strings and numbers will be simply cast into strings, but objects and arrays should be cast to JSON strings using JSON.stringify, and parsed in the client.

Properties

readyState

  • readyState number

    • Returns the current state of the WebSocket connection. Possible values:

      ConstantValueDescription
      WebSocket.CONNECTING0The connection is not yet open.
      WebSocket.OPEN1The connection is open and ready to communicate.
      WebSocket.CLOSING2The connection is in the process of closing.
      WebSocket.CLOSED3The connection is closed.

Events

  • close
    • An event indicating the WebSocket has closed. The CloseEvent includes code (number), reason (string), and wasClean (boolean) properties.
  • error
    • An event indicating there was an error with the WebSocket.
  • message
    • An event indicating a new message received from the client, including the data passed by the client.

Types

Message

  • data any - The data passed back from the other WebSocket in your pair.
  • type string - Defaults to message.

Close behavior

With the web_socket_auto_reply_to_close compatibility flag (enabled by default on compatibility dates on or after 2026-04-07), the Workers runtime automatically sends a reciprocal Close frame when it receives a Close frame from the peer. The readyState transitions to CLOSED before the close event fires. This matches the WebSocket specification and standard browser behavior.

If you still call close() inside the close event handler, the call is silently ignored. Existing code that manually replies to Close frames will continue to work without changes.

JavaScript
server.addEventListener("close", (event) => {
// readyState is already CLOSED — no need to call server.close().
console.log(server.readyState); // WebSocket.CLOSED
console.log(event.code); // 1000
console.log(event.wasClean); // true
});

Half-open mode for proxying

The automatic close behavior can interfere with WebSocket proxying, where a Worker sits between a client and a backend and needs to coordinate the close on both sides independently. To support this, pass { allowHalfOpen: true } to accept():

JavaScript
server.accept({ allowHalfOpen: true });
server.addEventListener("close", (event) => {
// readyState is still CLOSING here, giving you time
// to coordinate the close on the other side.
console.log(server.readyState); // WebSocket.CLOSING
// Manually close when ready.
server.close(event.code, "done");
});

Prior behavior

On compatibility dates before 2026-04-07 (or with the web_socket_manual_reply_to_close flag), receiving a Close frame leaves the WebSocket in CLOSING state, and your code must call close() to complete the handshake. Failing to do so can result in 1006 abnormal closure errors on the client.