Real-Time on the Web

Live cricket scores, chat messages, notifications, and AI answers that appear word by word all need the server to push data to the browser without being asked each time.

Two standard ways to do that are WebSockets and Server-Sent Events (SSE). They're often treated as interchangeable. They're not, and picking the simpler one can save you a lot of infrastructure work.


🎯 Quick Answer (30-Second Read)

  • SSE: a long-lived HTTP response where the server streams events to the browser. One-way, text only, auto-reconnects, works with normal HTTP infrastructure.
  • WebSocket: a persistent two-way connection. Client and server send messages any time, text or binary.
  • Use SSE for live feeds, notifications, dashboards and streaming AI responses (the Claude and OpenAI APIs stream with SSE).
  • Use WebSockets for chat, multiplayer games and collaborative editing, where both sides talk constantly.
  • Not sure? If the client only occasionally sends data, SSE + normal POST requests is usually simpler.

How Each One Works

sequenceDiagram participant B as Browser participant S as Server Note over B,S: Server-Sent Events B->>S: GET /events (Accept: text/event-stream) S-->>B: data: score 120/2 S-->>B: data: score 124/2 S-->>B: data: score 124/3 Note over B,S: WebSocket B->>S: GET /ws (Upgrade: websocket) S-->>B: 101 Switching Protocols B->>S: {"type":"message","text":"hi"} S-->>B: {"type":"message","text":"hello!"} B->>S: {"type":"typing"}
SSE
Plain HTTP. The server keeps the response open and writes lines like data: .... The browser's built-in EventSource handles parsing and reconnection.
WebSocket
Starts as HTTP, then "upgrades" to a different protocol. After that it's a raw two-way message channel. You handle reconnection and message formats yourself.

Side-by-Side Comparison

SSE WebSocket
Direction Server → client Both ways
Data Text (UTF-8) Text and binary
Protocol Standard HTTP Upgraded from HTTP to ws:// / wss://
Reconnect Automatic, can resume with Last-Event-ID You build it
Browser API EventSource (built in) WebSocket (built in)
Proxies, CDNs, auth Works like any HTTP request May need special configuration
Connection limit HTTP/1.1: about 6 per domain per browser (HTTP/2 removes this in practice) No such limit
Best for Feeds, notifications, AI token streaming Chat, games, collaboration

Code: SSE

Server (Node.js / Express):

app.get("/events", (req, res) => {
  res.set({
    "Content-Type": "text/event-stream",
    "Cache-Control": "no-cache",
    Connection: "keep-alive",
  });
  const timer = setInterval(() => {
    res.write(`data: ${JSON.stringify({ time: Date.now() })}\n\n`);
  }, 1000);
  req.on("close", () => clearInterval(timer));
});

Browser:

const source = new EventSource("/events");
source.onmessage = (e) => console.log(JSON.parse(e.data));
// reconnects automatically if the connection drops

Code: WebSocket

Server (Node.js with the ws library):

import { WebSocketServer } from "ws";

const wss = new WebSocketServer({ port: 8080 });
wss.on("connection", (socket) => {
  socket.on("message", (msg) => {
    for (const client of wss.clients) client.send(msg.toString()); // broadcast
  });
});

Browser:

const ws = new WebSocket("wss://example.com:8080");
ws.onmessage = (e) => console.log(e.data);
ws.onopen = () => ws.send("hello");
// no auto-reconnect: handle ws.onclose yourself

Why AI Chat Apps Use SSE

When you ask Claude or ChatGPT a question, the answer appears word by word. The Anthropic and OpenAI APIs deliver this with SSE: the client sends one normal request, and the server streams tokens back as events.

It fits perfectly: the conversation is request → long one-way response. There's no need for a two-way socket, and SSE works through standard HTTP load balancers and CDNs.

Key takeaway: the question isn't "which is more real-time?" Both are. The question is who needs to talk: if mostly the server, use SSE. If both sides constantly, use WebSockets.

Scaling Either One

Both keep a connection open per user, so the challenges are similar:

flowchart LR U1["Users"] --> LB["Load balancer
(long timeouts)"] LB --> S1["Server 1
10k open connections"] LB --> S2["Server 2
10k open connections"] PUB["Event source
(new message, score)"] --> PS[["Pub/sub
Redis, Kafka"]] PS --> S1 PS --> S2
  • Many open connections per server: use async servers (Node.js, Go, Python asyncio).
  • Load balancer timeouts: raise idle timeouts and send periodic heartbeats.
  • Broadcasting across servers: a user on server 1 must receive an event produced on server 2, so servers subscribe to a shared pub/sub channel.
  • Serverless limits: many serverless platforms cap request duration, which affects long-lived connections. Check your platform.

Frequently Asked Questions

Is SSE better than WebSocket?

Neither is better overall. SSE is simpler for one-way server-to-client updates and works with standard HTTP infrastructure, with built-in reconnection. WebSockets are better when both client and server send frequent messages, such as chat or multiplayer games, or when you need binary data.

Does ChatGPT use WebSockets or SSE?

The OpenAI and Anthropic APIs stream model responses using Server-Sent Events: the client sends a normal HTTP request and receives tokens as a stream of events. Individual apps may use other transports for features like voice, but text streaming in the APIs is SSE.

Can SSE send data from the client to the server?

No. SSE is one-way, from server to client. The client sends data with ordinary HTTP requests such as POST. For many apps, this combination is simpler than WebSockets, since client messages are occasional and server updates are frequent.


Conclusion

SSE and WebSockets both push data in real time, but they suit different shapes of communication. Use SSE for one-way streams like notifications, dashboards and AI responses, with free reconnection and plain HTTP. Use WebSockets when both sides need to talk constantly. Either way, plan for many open connections and a pub/sub layer as you scale.


Sources

Last verified: 14 October 2026.


Related reads: WhatsApp System Design · How Figma's Multiplayer Works · Load Balancer Explained · Claude API Pricing

I write about building products and how real systems work. Follow on LinkedIn or X, or invite me to speak.