Guider/Practical/PracticalDevGuide0002
Practical#02· 17분 읽기

PracticalDevGuide0002

WebSocket & 실시간 통신 기술 배경 지식

list목차(33)
PRACTICAL DEV GUIDE · 02

WebSocket & 실시간 통신 기술 배경 지식

WebSocket · HTTP Polling · Long Polling · SSE · WebRTC · gRPC Streaming · MQTT
각 기술이 무엇이고, 언제 쓰며, 장단점과 사용 시 유의점은 무엇인지 정리

대상: 실시간 기능 도입을 검토 중인 개발자 유형: 배경 지식 / 기술 비교 난이도: ★★★☆☆

"실시간"이라는 요구는 채팅·알림·시세·게임·협업 도구 등 다양한 형태로 등장합니다. 그러나 모든 실시간 통신을 WebSocket으로 풀 필요는 없습니다. 각 프로토콜은 풀려는 문제와 트레이드오프가 다르며, 잘못된 선택은 인프라 비용과 운영 난이도를 동시에 끌어올립니다. 본 문서는 WebSocket과 그 비교 대상이 되는 실시간 통신 기술들을 무엇·언제·장단점·유의점 관점에서 정리합니다.

실시간 통신 기술 분류

기술 방향성 전송 계층 대표 사례
WebSocket 양방향(Full-duplex) TCP 채팅, 협업, 게임, 시세
HTTP Polling 클라이언트 → 서버 TCP 단순 상태 갱신
Long Polling 서버 → 클라이언트(유사 푸시) TCP 레거시 호환 알림
SSE 서버 → 클라이언트(단방향) TCP / HTTP 서버 이벤트 스트림, 알림
WebRTC 양방향 P2P UDP(SRTP/SCTP) 화상회의, 음성통화, P2P 데이터
gRPC Streaming 단/양방향 스트림 HTTP/2 서버 간 스트리밍, 마이크로서비스
MQTT Pub/Sub TCP(또는 WS) IoT, 센서, 모바일 푸시 백엔드

1. WebSocket

표준 양방향 실시간 통신 프로토콜 (RFC 6455)

어떤 기술인가

단일 TCP 연결 위에서 양방향(Full-duplex)으로 메시지를 주고받는 표준 프로토콜. 처음에는 일반 HTTP 요청으로 시작해 Upgrade 헤더로 WebSocket으로 전환(handshake)됩니다. 이후로는 HTTP 요청·응답이 아닌 자체 프레임 포맷으로 통신하며, 한 번 열린 연결은 명시적으로 닫을 때까지 유지됩니다.

어떨 때 쓰이는가

  • 채팅, 협업 도구(공동 편집), 멀티플레이어 게임
  • 주식·암호화폐 시세 스트리밍
  • 실시간 알림 + 사용자 액션 동시 처리가 필요한 경우
  • HTTP 폴링으로는 비용·지연이 부적합한 트래픽 패턴

장점

  • 저지연 양방향 통신 (수십 ms 이하 가능)
  • HTTP 폴링 대비 헤더 오버헤드 절감
  • 대부분의 브라우저·서버 프레임워크가 표준 지원
  • 방화벽 친화적 (80/443 포트 사용 가능)

단점

  • 연결을 유지해야 해서 서버 메모리·FD가 누적
  • HTTP 캐시·CDN을 활용 못함
  • 로드 밸런서·프록시가 sticky session/timeout 설정 필요
  • 재연결·세션 복구 로직을 직접 구현해야 함

⚠ 사용 시 유의점

  • Idle timeout — ALB 기본 60초, NAT/방화벽도 끊을 수 있음 → ping/pong heartbeat 필수
  • 스케일 아웃 — 서버 인스턴스가 여러 개면 메시지 브로드캐스트를 위해 Redis Pub/Sub·Kafka 등 외부 채널 필요
  • 인증 — handshake 시점에만 Cookie/Authorization 헤더 전달 → 토큰 만료 시 재연결 처리
  • 백프레셔(backpressure) — 빠른 발행/느린 수신 시 버퍼 폭증 → 수신 확인·드롭 정책 필요
  • 메시지 크기 — 수 MB 이상 페이로드는 분할 또는 별도 HTTP 업로드로 분리 권장
  • WSS 강제 — 운영에서는 반드시 TLS(WSS) 사용. 평문 WS는 프록시·캐시 환경에서 실패율 높음

2. HTTP Polling (Short Polling)

주기적으로 서버에 묻는 가장 단순한 방식

어떤 기술인가

클라이언트가 일정 주기마다 HTTP GET으로 서버 상태를 확인하는 방식. 별도 프로토콜이 없고 일반 HTTP만 쓰면 되므로 구현 부담이 가장 작습니다.

어떨 때 쓰이는가

  • 지연 허용 폭이 큰 상태 갱신 (예: 분 단위 동기화)
  • 실시간성이 거의 없는 단순 대시보드
  • 실시간 인프라 도입이 부담스러운 초기 MVP

장점

  • 구현 가장 단순, 어떤 프록시/캐시와도 호환
  • HTTP 인증·캐싱·로깅 인프라 그대로 활용
  • 서버 상태가 stateless

단점

  • 대부분의 요청이 "변경 없음"이라 네트워크·서버 자원 낭비
  • 주기를 짧게 하면 비용↑, 길게 하면 지연↑
  • 다수 사용자 시 트래픽이 곱하기로 증가

⚠ 사용 시 유의점

  • If-Modified-Since / ETag로 미변경 응답을 304로 처리해 비용 절감
  • 탭 비활성화 시 폴링 주기를 늘리거나 중단 (브라우저 visibility API)
  • 지터(jitter)를 넣어 다수 클라이언트가 동시 요청 몰리는 현상 방지

3. Long Polling

HTTP만으로 푸시를 흉내내는 절충안

어떤 기술인가

클라이언트가 HTTP 요청을 보낸 뒤, 서버는 전달할 이벤트가 생길 때까지 응답을 보류합니다. 이벤트가 생기면 응답을 내려주고, 클라이언트는 즉시 다음 요청을 다시 보냅니다. WebSocket이 널리 쓰이기 전 실시간 푸시의 사실상 표준이었습니다.

어떨 때 쓰이는가

  • WebSocket·SSE를 차단하는 기업 프록시 환경
  • 구형 브라우저·레거시 SDK 호환이 필요한 경우
  • 이벤트 발생 빈도가 낮아 양방향 연결까지는 과한 경우

장점

  • 모든 HTTP 인프라와 호환
  • Short Polling 대비 즉시성·자원 효율 우위
  • 방화벽 통과 가장 쉬움

단점

  • 응답 지연 동안 서버 스레드/연결 점유
  • 이벤트당 새 요청·응답 반복 → 헤더 오버헤드 누적
  • 서버 → 클라이언트만 사실상 단방향

⚠ 사용 시 유의점

  • 비동기 I/O(Node.js, async Java/Python 등) 서버 권장 — 동기 블로킹 모델은 스레드 고갈
  • 로드 밸런서·게이트웨이 timeout(통상 30~60초)을 고려해 응답 보류 한도 설정
  • 중복 이벤트·누락 방지를 위한 cursor(마지막 이벤트 ID) 기반 재요청 설계

4. Server-Sent Events (SSE)

HTTP 기반 단방향 서버 푸시 표준

어떤 기술인가

HTML5 표준의 EventSource API. 일반 HTTP 응답을 끊지 않고 text/event-stream MIME 타입으로 이벤트를 줄줄이 흘려보냅니다. 서버 → 클라이언트 단방향이며, 끊기면 브라우저가 자동 재연결합니다.

어떨 때 쓰이는가

  • 서버 알림, 진행 상황 스트림 (예: AI 응답 토큰 스트리밍, 빌드 로그)
  • 읽기 전용 시세/통계 대시보드
  • 클라이언트 → 서버는 일반 REST로 충분한 워크로드

장점

  • 일반 HTTP라 프록시·CDN과 호환성 우수
  • 브라우저가 자동 재연결 + Last-Event-ID 처리
  • WebSocket 대비 구현·운영 단순
  • HTTP/2·HTTP/3에서 멀티플렉싱으로 동시 연결 효율↑

단점

  • 단방향 (클라이언트 → 서버는 별도 요청)
  • 텍스트 전용 (바이너리 전송 부적합)
  • HTTP/1.1에서 한 도메인당 동시 연결 수 제한
  • 일부 구식 프록시가 chunked stream을 버퍼링

⚠ 사용 시 유의점

  • 응답 헤더 Cache-Control: no-cache, X-Accel-Buffering: no(Nginx)로 버퍼링 방지
  • 각 이벤트에 id: 필드를 넣어 재연결 시 누락 방지
  • HTTP/2 환경 권장 — HTTP/1.1에서는 동시 연결 제한 회피 위해 도메인 샤딩 필요
  • 장기 연결이라 keep-alive heartbeat 이벤트 주기적으로 송출

5. WebRTC

브라우저 간 P2P 미디어·데이터 통신 표준

어떤 기술인가

브라우저·앱 간 P2P(Peer-to-Peer)로 영상·음성·데이터를 주고받는 기술. UDP 위에서 SRTP(미디어), SCTP(데이터 채널)를 쓰며, NAT/방화벽 통과를 위해 STUN/TURN 서버를 활용합니다. 시그널링(연결 협상) 채널은 별도 구성(WebSocket이나 HTTP)이 필요합니다.

어떨 때 쓰이는가

  • 화상 회의·음성 통화 (Google Meet, Discord 음성)
  • 저지연 라이브 스트리밍
  • P2P 파일 전송, 멀티플레이어 게임의 위치 데이터
  • 중앙 서버를 거치지 않아 비용·지연을 줄여야 하는 케이스

장점

  • 매우 낮은 지연 (수십 ms 이하)
  • P2P → 서버 대역폭 비용 절감
  • 미디어 코덱·에코 캔슬링 등 표준 스택 내장
  • DataChannel은 신뢰성/순서 모드 선택 가능

단점

  • NAT 통과 실패 시 TURN 서버 트래픽 비용 폭증
  • 대규모(수십명+) 회의는 SFU/MCU 미디어 서버 필요
  • 구현·디버깅 난이도 매우 높음
  • UDP 차단 환경에서는 동작 보장 어려움

⚠ 사용 시 유의점

  • TURN 서버는 필수 — 약 10~20% 사용자가 P2P 직결 실패
  • 회의 규모가 크면 SFU(Selective Forwarding Unit) 도입 (mediasoup, Janus, LiveKit)
  • 녹화·녹취·법적 보존이 필요한 경우 P2P가 부적합 → 서버 라우팅 모델 선택
  • 모바일 배터리·발열 영향 고려

6. gRPC Streaming

HTTP/2 기반 RPC의 스트리밍 모드

어떤 기술인가

Google이 만든 RPC 프레임워크 gRPC는 HTTP/2 위에서 동작하며, 단일 호출(unary) 외에도 서버 스트리밍 / 클라이언트 스트리밍 / 양방향 스트리밍 모드를 제공합니다. 메시지는 Protobuf로 직렬화되어 매우 작고 빠릅니다.

어떨 때 쓰이는가

  • 마이크로서비스 간 실시간 데이터 파이프라인
  • 다국어(polyglot) 백엔드의 강한 스키마 계약 필요
  • 대용량/고빈도 메시지 스트림 (텔레메트리, 모니터링)
  • 서버 ↔ 서버 통신 (브라우저는 gRPC-Web 등 별도 처리 필요)

장점

  • Protobuf로 페이로드 매우 작음
  • HTTP/2 멀티플렉싱·헤더 압축
  • 스키마(.proto) 기반 강한 타입 안전성
  • 다언어 코드 자동 생성

단점

  • 브라우저에서 직접 사용 불가 → gRPC-Web + 프록시(Envoy 등) 필요
  • 디버깅 도구·로깅이 텍스트 기반 HTTP보다 불편
  • Proxy/LB가 HTTP/2를 정확히 지원해야 함
  • 학습 곡선·툴체인 의존도 높음

⚠ 사용 시 유의점

  • ALB는 gRPC를 지원하지만 NLB·일부 Ingress는 HTTP/2 trailer 처리 한계 확인 필요
  • Deadline·취소(Cancellation) 전파 설계 — 안 그러면 좀비 스트림 누적
  • 스키마 진화 정책 (필드 번호 재사용 금지, 호환성 규칙) 사전 합의

7. MQTT

IoT·모바일에 최적화된 경량 Pub/Sub 프로토콜

어떤 기술인가

TCP 위에서 동작하는 Publish/Subscribe 모델의 경량 프로토콜. 토픽(topic)에 발행하고 구독하는 구조이며, 헤더가 매우 작아 좁은 대역폭·저전력 환경에 적합합니다. WebSocket 위에 얹는 변형(MQTT over WebSocket)도 표준화되어 브라우저에서도 사용 가능합니다.

어떨 때 쓰이는가

  • IoT 디바이스 (센서, 가전, 차량 텔레메트리)
  • 모바일 앱의 푸시 백엔드
  • 다대다 메시지 라우팅 (수만~수백만 토픽)
  • QoS(0/1/2) 등 메시지 보장 수준이 다양한 케이스

장점

  • 헤더 ~2바이트 수준의 매우 작은 오버헤드
  • QoS·Retained·Last Will 등 풍부한 기능
  • 브로커(EMQX, HiveMQ, AWS IoT Core) 생태계 성숙
  • 수백만 동시 연결 처리 사례 다수

단점

  • 브로커 운영·HA 구성이 별도 과제
  • Pub/Sub 모델 자체가 1:1 RPC 패턴과 어긋남
  • 토픽 설계가 잘못되면 라우팅 비용 폭증
  • 브라우저 환경은 WebSocket 변형 필요

⚠ 사용 시 유의점

  • QoS 2(정확히 1회)는 비싸므로 정말 필요할 때만
  • 토픽 네임스페이스 정책·와일드카드 권한을 사전 정의
  • Persistent Session vs Clean Session — 디바이스 특성에 맞게 선택
  • 매니지드 서비스(AWS IoT Core, HiveMQ Cloud)의 메시지·연결 단가 모델 사전 검토

기술 비교 매트릭스

항목 WebSocket Long Polling SSE WebRTC gRPC Stream MQTT
방향성 양방향 서버→C(유사) 서버→C 양방향 P2P 단/양방향 Pub/Sub
지연(Latency) 매우 낮음 중간 낮음 최저 매우 낮음 낮음
바이너리 지원 ×
브라우저 직접 지원 × (gRPC-Web) △ (WS 변형)
방화벽·프록시 친화 최고 × (UDP 차단) △ (HTTP/2)
서버 자원 부담 중간 (연결 유지) 높음 중간 낮음 (P2P) 중간 낮음 (브로커 효율)
구현 난이도 중간 낮음 낮음 최고 중간 중간

🛠 실습 — WebSocket 채팅 서버와 SSE 비교

Node.js로 WebSocket 에코·브로드캐스트 서버를 만든 뒤, 같은 알림 기능을 SSE로도 구현해 두 패러다임의 차이를 직접 체감합니다.

사전 준비

  • Node.js 20+ / npm
  • 웹 브라우저 (DevTools Console에서 클라이언트 코드 실행)
  • (선택) wscat CLI로 WS 디버깅

STEP 1 — Node `ws`로 에코 서버

mkdir ws-lab && cd ws-lab
npm init -y
npm i ws

cat > echo-server.js <<'EOF'
const { WebSocketServer } = require('ws');
const wss = new WebSocketServer({ port: 8080 });

wss.on('connection', (socket, req) => {
  console.log('connected:', req.socket.remoteAddress);
  socket.on('message', (data) => socket.send(`echo: ${data}`));
  socket.on('close', () => console.log('closed'));
});
console.log('ws://localhost:8080');
EOF

node echo-server.js
// 브라우저 DevTools 콘솔
const ws = new WebSocket('ws://localhost:8080');
ws.onmessage = (e) => console.log(e.data);
ws.onopen = () => ws.send('hi');

STEP 2 — 다중 클라이언트 브로드캐스트(채팅)

// chat-server.js
const { WebSocketServer } = require('ws');
const wss = new WebSocketServer({ port: 8080 });

function broadcast(payload, except) {
  const msg = JSON.stringify(payload);
  for (const c of wss.clients) {
    if (c.readyState === 1 && c !== except) c.send(msg);
  }
}

wss.on('connection', (socket) => {
  socket.on('message', (raw) => {
    try {
      const { user, text } = JSON.parse(raw);
      broadcast({ user, text, ts: Date.now() }, socket);
    } catch { /* ignore malformed */ }
  });
});

탭 두 개를 띄우고 한쪽에서 보낸 메시지가 다른 쪽에 즉시 도착하는지 확인하세요.

STEP 3 — Heartbeat (ping/pong)

// 서버: 30초마다 ping → 60초 내 pong 없으면 종료 (NAT/ALB Idle timeout 회피)
function heartbeat() { this.isAlive = true; }

wss.on('connection', (ws) => {
  ws.isAlive = true;
  ws.on('pong', heartbeat);
});

setInterval(() => {
  for (const ws of wss.clients) {
    if (!ws.isAlive) return ws.terminate();
    ws.isAlive = false;
    ws.ping();
  }
}, 30_000);

실제 운영에서는 ALB(기본 60초)·NAT·기업 프록시가 idle 연결을 끊으므로 heartbeat는 선택이 아닌 필수입니다.

STEP 4 — 인증 + 재연결 클라이언트

// 서버: handshake 시점에만 토큰 검사 가능
wss.on('connection', (ws, req) => {
  const url = new URL(req.url, 'http://x');
  const token = url.searchParams.get('token');
  if (!isValid(token)) return ws.close(4001, 'unauthorized');
});

// 클라이언트: 지수 백오프 재연결
function connect(retries = 0) {
  const ws = new WebSocket(`ws://localhost:8080/?token=${getToken()}`);
  ws.onclose = () => {
    const delay = Math.min(1000 * 2 ** retries, 30_000);
    setTimeout(() => connect(retries + 1), delay);
  };
  ws.onopen = () => { retries = 0; };
}
connect();

STEP 5 — 같은 기능을 SSE로 (단방향)

// sse-server.js — Express 없이 순수 http
const http = require('http');

http.createServer((req, res) => {
  if (req.url !== '/events') return res.end();
  res.writeHead(200, {
    'Content-Type': 'text/event-stream',
    'Cache-Control': 'no-cache',
    'Connection': 'keep-alive',
    'X-Accel-Buffering': 'no',
  });
  let i = 0;
  const id = setInterval(() => {
    res.write(`id: ${++i}\n`);
    res.write(`data: ${JSON.stringify({ tick: i, ts: Date.now() })}\n\n`);
  }, 1000);
  req.on('close', () => clearInterval(id));
}).listen(8090, () => console.log('sse on 8090'));
// 브라우저 — 자동 재연결과 Last-Event-ID는 EventSource가 처리
const es = new EventSource('http://localhost:8090/events');
es.onmessage = (e) => console.log('sse:', e.data);

관찰 포인트

  • WebSocket: 양방향 메시지가 자유롭지만 재연결·인증·heartbeat를 직접 짜야 함
  • SSE: 클라이언트 → 서버는 별도 REST. 대신 재연결·이벤트 ID는 브라우저가 무료로 처리
  • 둘 다 운영에서는 TLS(WSS / HTTPS) 강제, 프록시·LB의 idle timeout 점검 필수

의사결정 가이드 — 무엇을 언제 쓸까

상황 권장 기술 이유
실시간 채팅·게임·협업 도구 WebSocket 양방향, 저지연, 표준 지원
서버 푸시만 필요 (알림·진행상황·LLM 토큰 스트림) SSE 단방향, HTTP 인프라 그대로, 자동 재연결
분 단위 갱신으로도 충분한 단순 대시보드 HTTP Polling 구현 비용 최소
프록시·방화벽이 WS/SSE를 차단 Long Polling HTTP만 통과하면 됨
화상회의, 음성통화, 저지연 미디어 WebRTC P2P, UDP, 미디어 표준 스택 내장
서비스 간 고빈도 데이터 스트림 (S2S) gRPC Streaming 스키마, Protobuf, HTTP/2
IoT 디바이스, 수백만 동시 연결 푸시 MQTT 초경량 헤더, Pub/Sub, QoS

🎯 핵심 요약

  • WebSocket — 양방향이 정말 필요할 때의 표준 선택
  • HTTP/Long Polling — 인프라가 받쳐주지 않거나 빈도가 낮을 때의 현실적 대안
  • SSE — 서버 → 클라이언트 단방향이면 가장 간단·견고
  • WebRTC — 오디오·비디오·P2P 데이터의 사실상 표준
  • gRPC Streaming — 서버 간 강한 스키마 + 고빈도 스트림
  • MQTT — IoT·수백만 디바이스 푸시의 정답

"실시간"은 단일 기술이 아니다. 양방향성, 지연 허용 폭, 클라이언트 환경, 서버 자원 모델, 운영 가능성을
함께 따져 트래픽 성격에 맞는 프로토콜을 고르는 것이 핵심이다.