REST에서 Socket.io·GraphQL로 확장하기
REST 원칙을 기반으로 실시간 전송과 GraphQL을 단계적으로 조합하는 설계 사고
Posted
By okorion
REST에서 Socket.io·GraphQL로 확장하기
결론 요약
- 프로토콜 선택은 구현 편의가 아니라 “요구사항의 형태”로 결정된다.
- REST는 리소스 중심의 상태 전이에 강하고, 실시간은 이벤트 전파 문제다.
- Socket.io는 REST를 대체하지 않으며, 보완 레이어다.
- GraphQL은 over/under-fetching을 해결하지만 설계·운영 비용을 전제로 한다.
- 올바른 확장은 “REST → 실시간 → GraphQL”의 단계적 조합이다.
REST API → 실시간(Socket.io) → GraphQL로 확장하는 설계 사고
요구사항에서 아키텍처로
1️⃣ REST의 핵심 원칙과 흔한 오해
REST의 3대 핵심
- 리소스(Resource): URL은 “대상”을 표현한다.
- 표현(Representation): JSON/HTML 등은 표현일 뿐이다.
- 상태 코드(Status Code): 결과의 의미를 계약으로 전달한다.
흔한 오해: REST = JSON API 실제로 REST는 프로토콜 설계 원칙이지 포맷이 아니다.
올바른 REST 예
1
2
3
4
GET /posts/123 → 게시물 조회
POST /posts → 게시물 생성
PATCH /posts/123 → 게시물 수정
DELETE /posts/123 → 게시물 삭제
URL에 /create, /delete 같은 행동 동사가 보이면 REST 사고가 깨진 신호다.
2️⃣ CORS: 왜 생기고, 어디서 해결하는가
CORS가 생기는 이유
- 브라우저는 출처(origin) 간 요청을 제한한다.
- 서버가 아니라 브라우저 보안 정책이다.
어디서 해결해야 하는가
- 서버에서 헤더로 허용 범위를 명시한다.
- 클라이언트에서 우회하려는 시도는 근본 해결이 아니다.
1
2
3
Access-Control-Allow-Origin
Access-Control-Allow-Methods
Access-Control-Allow-Headers
설계 포인트
- 인증 토큰(JWT)을 쓰면 CORS 설정은 더 엄격해져야 한다.
- 와일드카드(
*)는 개발 단계에서만 허용.
3️⃣ REST에서 인증(JWT) 흐름과 권한 체크 위치
JWT 기반 인증 흐름 (REST)
1
2
3
4
5
POST /login
→ JWT 발급
→ Client 저장
→ Authorization: Bearer <token>
→ 보호된 API 접근
권한 체크 위치
- 라우트 진입 시 미들웨어
- 비즈니스 로직 내부가 아니다.
1
authenticate → authorize → controller
중요 분리
- Authentication: 토큰 유효성
- Authorization: 역할/권한 확인
이 분리가 안 되면 “로그인만 하면 관리자 행동 가능”한 사고가 난다.
4️⃣ 실시간이 필요한 조건과 Socket.io의 위치
실시간이 필요한 조건
- 상태 변경을 즉시 다수에게 전파
- polling 비용이 과도함
- 사용자 체감 지연이 UX를 깨뜨림
예:
- 채팅
- 알림
- 협업 편집
- 실시간 상태판
Socket.io의 정확한 위치
- REST를 대체하지 않는다
- REST로 상태 변경 → 이벤트를 실시간으로 전파
1
2
REST: 데이터의 진실(source of truth)
Socket.io: 변화의 전달(channel)
이 경계를 넘으면 상태 불일치가 발생한다.
5️⃣ GraphQL: 장점과 비용을 동시에 본다
GraphQL의 장점
- over-fetching 제거: 필요한 필드만 요청
- under-fetching 제거: 한 번의 요청으로 조합
- 프론트엔드 주도 쿼리 설계
하지만 반드시 치르는 비용
| 항목 | 비용 |
|---|---|
| 스키마 설계 | 초기 설계 난이도 높음 |
| 리졸버 | 서버 복잡도 증가 |
| N+1 문제 | 잘못 설계하면 성능 급락 |
| 캐싱 | REST보다 난이도 높음 |
GraphQL은 “API를 예쁘게 만드는 도구”가 아니라 요청 패턴이 복잡할 때만 가치가 생기는 도구다.
6️⃣ REST vs GraphQL 비교표
| 항목 | REST | GraphQL |
|---|---|---|
| 요청 단위 | 엔드포인트 | 쿼리 |
| 데이터 제어 | 서버 | 클라이언트 |
| 캐싱 | 쉬움 | 어려움 |
| 스키마 | 암묵적 | 명시적 |
| 성능 | 예측 가능 | 설계 의존 |
| 운영 | 단순 | 복잡 |
7️⃣ 설계 시 흔히 깨지는 지점과 해결 패턴
❌ 나쁜 패턴
- 모든 API를 GraphQL로 시작
- 실시간 요구 없이 Socket.io 도입
- REST에서 권한 체크 누락
✅ 개선 패턴
- REST로 명확한 데이터 경계 먼저 구축
- 실시간은 “필요한 이벤트만” 추가
- GraphQL은 프론트 요구가 복잡해질 때 도입
8️⃣ 결론: 5가지 서비스 시나리오로 선택하기
- 블로그 / CMS
- REST + SSR
- 필요 시 관리자 실시간 알림
- 커머스
- REST (주력)
- Socket.io (재고/주문 상태)
- GraphQL은 선택
- 채팅 / 협업
- REST (기본 데이터)
- Socket.io (핵심 기능)
- 모바일 API
- REST + JWT
- GraphQL은 복잡한 피드에만 제한 사용
- 대규모 프론트 팀
- REST → GraphQL 점진 도입
- 스키마/권한/캐싱 전략 필수
설계 선택 체크리스트 (질문 12개)
- URL이 리소스를 표현하고 있는가?
- 상태 코드를 계약으로 사용하고 있는가?
- CORS를 서버에서 제어하고 있는가?
- 인증과 권한을 분리했는가?
- REST가 source of truth인가?
- 실시간이 정말 필요한가?
- 이벤트 전파와 상태 변경을 분리했는가?
- over/under-fetching 문제가 실제로 존재하는가?
- GraphQL N+1을 방지할 설계가 있는가?
- 캐싱 전략을 설명할 수 있는가?
- 운영 복잡도를 감당할 수 있는가?
- 6개월 뒤에도 이 선택을 유지할 수 있는가?
This post is licensed under CC BY 4.0 by the author.
