A Gentle Guide to HTTP Polling, WebSocket's, SSE, and Streamable HTTP

Imagine you're building a chat app. You've got users who want to send messages, get replies instantly, and see who's typing. Sounds simple, right? But under the hood, making a real-time chat app is all about choosing the right communication strategy between your user's browser and your server.

Let’s explore five major ways to build a real-time chat app—from the oldest trick in the book to the most modern web-streaming approach.


1. HTTP Polling – The Curious Kid

Analogy: Think of a curious kid asking their parent every few seconds: "Did I get any new messages? Did I? Now? What about now?"

How it works:
The browser (chat client) sends a request to the server every few seconds like:

setInterval(() => {
  fetch('/chat/messages')
    .then(response => response.json())
    .then(showMessages);
}, 5000); // every 5 seconds

Pros:

  • Super simple to implement.

  • Works with any browser or backend.

Cons:

  • Slow: users get messages late.

  • Wasteful: lots of empty checks.

  • Not really "real-time."

Use case: Okay for very basic chat apps or low traffic scenarios.


2. WebSocket – The Phone Call

Analogy: Like a phone call where both people can speak and listen at any time.

How it works:
Once the WebSocket connection is open, both client and server can send messages to each other freely:

const socket = new WebSocket('wss://chat.example.com');

socket.onmessage = (event) => {
  showMessage(JSON.parse(event.data));
};

socket.send(JSON.stringify({ user: 'Alice', message: 'Hello!' }));

Pros:

  • Truly real-time and bi-directional.

  • Great for rich interactions like typing indicators, online presence, etc.

Cons:

  • Needs a separate WebSocket server.

  • Can be tricky with proxies/CDNs/firewalls.

Use case: Ideal for fully-featured chat apps (e.g., Slack, Discord).


3. SSE (Server-Sent Events) – The Magazine Subscription

Analogy: You subscribe to a magazine, and they send you new issues automatically.

How it works:
You open a one-way stream from server to browser:

const evtSource = new EventSource('/chat/stream');

evtSource.onmessage = (event) => {
  showMessage(JSON.parse(event.data));
};

Pros:

  • Simple, uses regular HTTP.

  • Great for live updates from server.

Cons:

  • One-way only: client can't send messages back.

  • Less control over reconnection, resending, etc.

Use case: Notification systems or apps where the server is mostly sending.


4. HTTP + SSE – Postman & Magazine Combo

Analogy: You write and send letters via postman (HTTP POST), and receive a magazine subscription with new messages (SSE).

How it works:

  • Use fetch() to send messages.

  • Use EventSource to receive messages.

// Send message
fetch('/chat/send', {
  method: 'POST',
  body: JSON.stringify({ user: 'Alice', message: 'Hello!' }),
  headers: { 'Content-Type': 'application/json' }
});

// Receive messages
const evtSource = new EventSource('/chat/stream');

evtSource.onmessage = (event) => {
  showMessage(JSON.parse(event.data));
};

Pros:

  • Simple real-time setup.

  • Uses standard HTTP.

Cons:

  • Two separate connections (one for send, one for receive).

  • SSE has limitations on error handling and resuming.

Use case: Lightweight chat apps or support chat tools.


5. Streamable HTTP – A Live Conversation

Analogy: You're on a voice call where you're listening to a story, and the other person reads it to you as they write it.

How it works:

  • Open a POST request from client to server.

  • Server keeps the connection open and streams events back over it.

  • You send and receive on the same pipe.

Example:

const stream = new ReadableStream({
  start(controller) {
    controller.enqueue(JSON.stringify({ user: 'Alice', message: 'Hello!' }));
    controller.close();
  }
});

fetch('/chat/stream', {
  method: 'POST',
  body: stream,
  headers: { 'Content-Type': 'application/json' }
}).then(response => {
  const reader = response.body.getReader();
  reader.read().then(function processText({ done, value }) {
    if (done) return;
    showMessage(value);
    return reader.read().then(processText);
  });
});

Pros:

  • Single endpoint: stream in and out.

  • Works better with modern cloud infrastructure.

  • Easier scaling compared to WebSocket.

Cons:

  • Requires HTTP/2 or HTTP/3 for full potential.

  • Still evolving as a pattern.

Use case: Modern chat systems or AI-driven messaging (e.g., chat with AI bots).


Comparison Table

PatternReal-TimeBi-DirectionalComplexityBest For
HTTP PollingBasic chat apps
WebSocket⭐⭐⭐Rich, real-time interaction
SSEServer announcements
HTTP + SSEPartial⭐⭐Lightweight two-way chat
Streamable HTTP⭐⭐Modern apps, serverless-ready

0
Subscribe to my newsletter

Read articles from Srujana Penugonda directly inside your inbox. Subscribe to the newsletter, and don't miss out.

Written by

Srujana Penugonda
Srujana Penugonda