graphql-server.sse

Server-Sent Events response utilities for GraphQL subscriptions.

Provides Ring response helpers for streaming data from core.async channels as SSE events. Handles connection lifecycle, keepalive messages, and proper HTTP streaming headers.

The main entry point is sse-response, which creates a Ring streaming response from a core.async channel. Messages on the channel should be maps with :type and :data keys.

sse-headers

Standard HTTP headers for SSE responses.

  • Content-Type: text/event-stream - Required for SSE
  • Cache-Control: no-cache, no-store, must-revalidate - Prevent caching
  • Connection: keep-alive - Maintain persistent connection
  • X-Accel-Buffering: no - Disable nginx buffering

sse-response

(sse-response channel & {:keys [cors-origin], :or {cors-origin "*"}})

Creates a Ring streaming response from a core.async channel.

The channel should emit maps with :type and :data keys. Each message is formatted as an SSE event and written to the response stream.

Uses ring.core.protocols/StreamableResponseBody to ensure headers are written immediately before the body starts streaming.

Automatically sends keepalive comments every 15 seconds to maintain the connection and detect disconnected clients. Closes cleanly when the channel closes or the client disconnects.

Options: - :cors-origin - Value for Access-Control-Allow-Origin header (default "*")

write-sse-event

(write-sse-event out event-type data)

Writes a single SSE event to the output stream.

The event is formatted as:

event: <event-type>
data: <json-data>

The event-type is converted to a name string. The data is JSON-encoded.

write-sse-keepalive

(write-sse-keepalive out)

Writes an SSE comment as a keepalive signal.

SSE comments (lines starting with :) are ignored by clients but keep the connection alive and detect disconnected clients.