FroquizFroquiz
HomeQuizzesSenior ChallengeGet CertifiedBlogAbout
Sign InStart Quiz
Sign InStart Quiz
Froquiz

The most comprehensive quiz platform for software engineers. Test yourself with 10000+ questions and advance your career.

LinkedIn

Platform

  • Start Quizzes
  • Topics
  • Blog
  • My Profile
  • Sign In

About

  • About Us
  • Contact

Legal

  • Privacy Policy
  • Terms of Service

© 2026 Froquiz. All rights reserved.Built with passion for technology
Blog & Articles

What Is WebSocket? The Technology Behind Real-Time Applications

Instant messaging, live notifications, multiplayer games — they all use WebSocket. We break down the bidirectional communication technology that takes over where HTTP falls short.

Yusuf SeyitoğluMarch 5, 20260 views9 min read

What Is WebSocket? The Technology Behind Real-Time Applications

You send a message on WhatsApp and the other person sees it instantly. Prices in a stock trading app update continuously. In a multiplayer game, your opponent's every move appears on your screen in real time.

Behind all of these is the same question: how does the server notify the client when something happens? With HTTP, solving this problem turns out to be much harder than expected.

HTTP's Real-Time Problem

HTTP works on a request-response model. The client asks, the server answers. The server can't send anything to the client on its own — it always has to wait for the client to ask.

The first solution developed for real-time data needs was polling: the client would ask the server at regular intervals "is there anything new?"

javascript
// Bad solution: Polling setInterval(async () => { const response = await fetch("/api/messages/new"); const messages = await response.json(); if (messages.length > 0) displayMessages(messages); }, 1000); // Ask every second

The problem is obvious: with 10,000 users, that's 10,000 requests per second. Most responses are empty. Server under load, high latency, wasted bandwidth.

Long polling was smarter: the client sends a request, the server holds the connection open until new data arrives, responds when data comes, and the client immediately sends a new request.

javascript
// Better but still not ideal: Long Polling async function longPoll() { const response = await fetch("/api/messages/wait"); const messages = await response.json(); displayMessages(messages); longPoll(); // Immediately send new request }

Fewer empty responses, but still a new HTTP connection for every message. The TCP handshake cost is paid every time.

WebSocket: A Persistent Connection

WebSocket establishes a single persistent connection between client and server. Once the connection is established, either side can send data whenever it wants. No extra overhead, no polling, no repeatedly establishing connections.

A WebSocket connection starts with the HTTP upgrade mechanism:

http
GET /chat HTTP/1.1 Host: example.com Upgrade: websocket Connection: Upgrade Sec-WebSocket-Key: dGhlIHNhbXBsZSBub25jZQ== Sec-WebSocket-Version: 13

If the server accepts:

http
HTTP/1.1 101 Switching Protocols Upgrade: websocket Connection: Upgrade Sec-WebSocket-Accept: s3pPLMBiTxaQ9kYGzzhZRbK+xOo=

101 — Switching Protocols. This connection no longer runs on HTTP, it runs on the WebSocket protocol. Either side can send messages whenever it wants.

Using WebSocket in the Browser

javascript
// Establish connection const ws = new WebSocket("wss://example.com/chat"); // When connection opens ws.addEventListener("open", () => { console.log("Connection established"); ws.send(JSON.stringify({ type: "join", room: "general", username: "john" })); }); // When message arrives ws.addEventListener("message", (event) => { const data = JSON.parse(event.data); switch (data.type) { case "message": displayMessage(data); break; case "user_joined": showNotification(`${data.username} joined the room`); break; case "typing": showTypingIndicator(data.username); break; } }); // When connection closes ws.addEventListener("close", (event) => { console.log(`Connection closed: ${event.code} - ${event.reason}`); setTimeout(reconnect, 3000); }); // Send a message function sendMessage(text) { if (ws.readyState === WebSocket.OPEN) { ws.send(JSON.stringify({ type: "message", text, timestamp: Date.now() })); } }

WebSocket Server with Node.js

javascript
import { WebSocketServer } from "ws"; const wss = new WebSocketServer({ port: 8080 }); const rooms = new Map(); wss.on("connection", (ws) => { ws.isAlive = true; ws.on("message", (rawData) => { const data = JSON.parse(rawData); switch (data.type) { case "join": handleJoin(ws, data); break; case "message": handleMessage(ws, data); break; case "typing": handleTyping(ws, data); break; } }); ws.on("close", () => handleDisconnect(ws)); ws.on("pong", () => { ws.isAlive = true; }); }); function handleJoin(ws, data) { ws.username = data.username; ws.room = data.room; if (!rooms.has(data.room)) rooms.set(data.room, new Set()); rooms.get(data.room).add(ws); broadcast(data.room, { type: "user_joined", username: data.username }, ws); } function handleMessage(ws, data) { broadcast(ws.room, { type: "message", username: ws.username, text: data.text, timestamp: Date.now() }); } function broadcast(room, data, exclude = null) { const clients = rooms.get(room) || new Set(); const message = JSON.stringify(data); clients.forEach(client => { if (client !== exclude && client.readyState === 1) { client.send(message); } }); } // Heartbeat: clean up dead connections setInterval(() => { wss.clients.forEach(ws => { if (!ws.isAlive) return ws.terminate(); ws.isAlive = false; ws.ping(); }); }, 30000);

Scaling: Multiple Servers

When a single server isn't enough, a problem emerges: a user connected to server A can't message a user connected to server B. The solution: a pub/sub system.

javascript
import { createClient } from "redis"; const publisher = createClient(); const subscriber = createClient(); await publisher.connect(); await subscriber.connect(); function handleMessage(ws, data) { publisher.publish("chat:general", JSON.stringify({ type: "message", username: ws.username, text: data.text })); } subscriber.subscribe("chat:general", (message) => { localClients.forEach(client => { if (client.readyState === 1) client.send(message); }); });

Every server listens to the Redis channel. Regardless of which server a user is connected to, all users receive the message.

WebSocket vs Server-Sent Events

WebSocket isn't always the right tool. Server-Sent Events (SSE) is a simpler alternative for one-way data flow from server to client.

SSE works over standard HTTP, supports automatic reconnect, and has excellent browser support. But sending data from client to server requires a separate HTTP request.

Use WebSocket: Bidirectional real-time communication. Chat, games, collaboration tools.

Use SSE: One-way streaming. Live notifications, news feed, progress bars, log streaming.

Understanding WebSocket is understanding how real-time systems work. From chat to live collaboration tools, from games to financial platforms — the power of a persistent connection is everywhere.

About Author

Yusuf Seyitoğlu

Author →

Other Posts

  • GraphQL Schema Design: Types, Resolvers, Mutations and Best PracticesMar 12
  • Java Collections Deep Dive: ArrayList, HashMap, TreeMap, LinkedHashMap and When to Use EachMar 12
  • CSS Advanced Techniques: Custom Properties, Container Queries, Grid Masonry and Modern LayoutsMar 12
All Blogs