악성 우결충 윤아는 스터디원에게 실시간으로 여자를 소개해주는 WebSocket 기반 웹게임을 만들었다.
그런데 예상치 못한 스터디원의 인기로 동시 접속자가 급증하자 메시지 딜레이와 화면 끊김 현상이 발생했다.
이 문제가 서버 병목인지, 프론트엔드 렌더링 병목인지 어떻게 구분하고 분석할 것인가?
질문답변에 대한 고민 이전에, 용어 개념들을 간략히 정리해보자.
별도의 클라이언트 설치 없이 웹에서 즐길 수 있는 게임.
브라우저에서 게임 요소를 Dom 기반으로 랜더링하고 있다면,
웹페이지의 버튼 요소 등과 같은 방식으로 개발자 도구에서 조작도 가능하다.


검은 룩 체스말에 display:none 설정을 부여한 모습.
검은 룩이 사라진 것으로 element.style이 잘 적용되고 있음을 확인 가능하다.
웹소켓(WebSocket)은 웹에서 클라이언트와 서버 간의 지속적인 양방향 연결을 유지하여 실시간으로 데이터를 주고받을 수 있게 해주는 통신 프로토콜(통신 규약)이다.
일반적인 HTTP 통신은 클라이언트가 요청을 보내야 서버가 응답할 수 있는 요청-응답 방식인 반면, 웹소켓은 한 번 연결이 수립되면 클라이언트와 서버 어느 쪽이든 필요할 때 데이터를 전송할 수 있다.
또한 OSI 7계층 기준으로 일반적인 소켓 통신은 TCP·UDP와 같은 전송 계층(4계층) 프로토콜을 기반으로 동작한다. 반면 웹소켓은 연결 수립 과정에서 HTTP를 사용하며, 웹 애플리케이션에서 활용되는 응용 계층(7계층) 프로토콜로 분류된다.
| 소켓 | 웹소켓 | |
|---|---|---|
| 통신 방식 | 단방향 (요청-응답) | 양방향 |
| 기반 프로토콜 | TCP / UDP | TCP + HTTP |
| OSI 계층 | 4계층 (전송 계층) | 7계층 (응용 계층) |
| 연결 방식 | 요청마다 연결 | 한 번 연결 후 유지 |
| 주요 사용처 | 네트워크 통신 전반 | 실시간 웹 서비스 |
전체 시스템에서 가장 느린 구간이 전체 성능을 제한하는 현상.
예시)
1(1초) → 2(1초) → 3(1초) = 총 3초
# 2번에서 병목 발생시
1(1초) → 2(1.5초) → 3(1초) = 총 3.5초
↑
여기서 막혀서 전체가 느려짐
SSR(서버 사이드 렌더링)은 서버에서 렌더링 작업이 끝나기 전까지는 전까지 사용자에게 그 어떤 정보도 제공할수 없다는 특성상 병목 현상에 취약하다. 애플리케이션 규모가 커지고 요청이 복잡하게 얽힐수록 병목이 심해져, 오히려 사용자 경험을 해치는 결과로 이어질 수 있다.
서버 또는 서버 구성요소(DB, Redis, 메시지 큐 등)에서 처리 지연이 발생하여 전체 서비스의 성능이 저하되는 현상을 의미한다.
서버는 여러 사용자가 공유하는 자원이므로, 서버 병목이 발생하면 일반적으로 다수의 사용자에게 영향을 미친다.
예시 1. DB 병목
예시 2. 게임 서버 CPU 포화
예시 3. Redis 병목
프론트엔드 병목은 사용자의 브라우저에서 JavaScript 실행, 렌더링, 메모리 사용 등의 문제로 인해 성능 저하가 발생하는 현상을 의미한다.
프론트엔드는 각 사용자의 브라우저에서 개별적으로 실행되므로 특정 사용자에게만 영향을 줄 수 있으며, 잘못된 코드가 배포된 경우에는 모든 사용자가 동시에 영향을 받을 수도 있다.
예시 1. JavaScript 번들 크기 증가
예시 2. 과도한 렌더링(Re-render)
예시 3. 메모리 누수