이 사이트의 실습은 자바스크립트를 켜야 움직입니다. 아래는 같은 내용을 글로 적은 것입니다.
공부 › 아키텍처와 운영 › 서비스 분리
게이트웨이와 점진적 전환
거대한 서버를 멈추지 않고 조금씩 떼어 내기
모든 기능이 한 덩어리인 기존 서버(모놀리스) 앞에 게이트웨이를 두고, 경로별로 요청을 새 서비스로 조금씩 넘깁니다. 사용자가 보는 주소는 그대로입니다.
문서·표준 대조 · Spring Cloud Gateway의 설정 조건
이 실습에 나오는 개념
- API 게이트웨이
- 클라이언트의 모든 요청을 가장 먼저 받아 알맞은 내부 서비스로 전달하는 단일 진입점이다. 인증, 요청 수 제한, 로깅 같은 공통 기능을 한곳에서 처리한다. 클라이언트는 내부 서비스의 구성과 주소를 알 필요가 없다.
- Strangler Fig 패턴
- 기존 시스템을 한 번에 교체하지 않고 기능을 하나씩 새 시스템으로 옮겨 가며 점진적으로 대체하는 방법이다. 요청을 받는 앞단에서 옮겨진 기능의 요청만 새 시스템으로 보내고 나머지는 기존 시스템이 계속 처리한다. 모든 기능이 옮겨지면 기존 시스템을 제거한다.
- 모놀리식과 MSA(마이크로서비스)
- 모놀리식은 모든 기능을 하나의 애플리케이션으로 만들어 함께 배포하는 구조다. MSA는 기능별로 작은 서비스로 나눠 각각 독립적으로 개발, 배포, 확장하는 구조다. MSA는 서비스별로 따로 배포하고 확장할 수 있고 장애가 격리되지만, 서비스 간 통신, 데이터 일관성, 운영의 복잡도가 크게 늘어난다.
- 리버스 프록시
- 클라이언트의 요청을 대신 받아 내부의 서버로 전달하고 그 응답을 클라이언트에 돌려주는 서버다. 클라이언트는 실제 서버를 직접 알지 못한다. 여러 서버로의 요청 분산, TLS 처리, 캐싱, 내부 서버 보호 등의 역할을 한다.
- 롤링, 블루-그린, 카나리 배포
- 서비스 중단 없이 새 버전을 배포하는 방식들이다. 롤링은 서버를 일부씩 차례로 새 버전으로 교체한다. 블루-그린은 새 버전 환경을 통째로 따로 준비한 뒤 트래픽을 한 번에 전환한다. 카나리는 일부 사용자에게만 새 버전을 먼저 적용해 문제가 없는지 확인한 뒤 점차 확대한다.
이렇게 바꿔 보세요
- 처음 설정으로 — 주문 경로만 새 서비스로 넘겼습니다.
- 주문의 10%만 먼저 — 새 서비스를 실제 요청 일부로 검증합니다.
- 전환 전 — 모든 요청이 기존 서버로 갑니다.
- 전환 완료 — 기존 서버로 가는 요청이 없어 종료할 수 있습니다.
- 토큰 없는 요청 — 게이트웨이가 입구에서 걸러 냅니다.
처음 설정으로 실행하면
- 사용자의 모든 요청은 게이트웨이 한 곳으로 들어옵니다. 게이트웨이는 공통 작업(토큰 검증, 로그, 요청 수 제한)을 처리한 뒤, 경로를 보고 뒤쪽의 어느 서버로 넘길지 정합니다. 사용자는 뒤에 서버가 몇 개 있는지 알지 못합니다.
- GET /orders/1: 경로가 /orders로 시작합니다. 이 경로는 새 서비스로 넘기도록 설정돼 있습니다. → 주문 서비스 (새)
- POST /payments: 경로가 /payments로 시작합니다. 따로 지정된 경로가 아니므로 기존 서버로 갑니다. → 기존 서버 (모놀리스)
- GET /members/me: 경로가 /members로 시작합니다. 따로 지정된 경로가 아니므로 기존 서버로 갑니다. → 기존 서버 (모놀리스)
- POST /orders: 경로가 /orders로 시작합니다. 이 경로는 새 서비스로 넘기도록 설정돼 있습니다. → 주문 서비스 (새)
- GET /orders/2: 경로가 /orders로 시작합니다. 이 경로는 새 서비스로 넘기도록 설정돼 있습니다. → 주문 서비스 (새)
- GET /members/7: 경로가 /members로 시작합니다. 따로 지정된 경로가 아니므로 기존 서버로 갑니다. → 기존 서버 (모놀리스)
- POST /orders: 경로가 /orders로 시작합니다. 이 경로는 새 서비스로 넘기도록 설정돼 있습니다. → 주문 서비스 (새)
- GET /payments/9: 경로가 /payments로 시작합니다. 따로 지정된 경로가 아니므로 기존 서버로 갑니다. → 기존 서버 (모놀리스)
- GET /orders/3: 경로가 /orders로 시작합니다. 이 경로는 새 서비스로 넘기도록 설정돼 있습니다. → 주문 서비스 (새)
- GET /orders/4: 경로가 /orders로 시작합니다. 이 경로는 새 서비스로 넘기도록 설정돼 있습니다. → 주문 서비스 (새)
실행 결과
- 기능을 한 번에 다 옮기지 않고 경로 단위로 떼어 냅니다. 새 서비스에 문제가 생기면 설정을 되돌려 요청을 다시 기존 서버로 보낼 수 있습니다(새 서비스가 쓴 데이터는 따로 챙겨야 합니다). 기존 시스템을 조금씩 감싸며 대체해 간다고 해서 Strangler Fig(교살자 무화과) 패턴이라고 부릅니다.
코드
# Spring Cloud Gateway
spring.cloud.gateway:
routes:
- id: order
uri: http://order-service
predicates:
- Path=/orders/**
- id: legacy # 나머지는 전부 기존 서버로
uri: http://legacy-monolith
predicates:
- Path=/**
# 공통 필터: 토큰 검증, 요청 로그, 요청 수 제한
이 모형의 전제
요청 10건의 고정된 예입니다. 비율 설정은 10건 안에서 차이가 보이도록 단순하게 배정했습니다(50%는 주문 요청을 번갈아, 10%는 다섯 번째 주문 요청 하나). 설정 예시는 Spring Cloud Gateway의 경로·가중치 조건을 따랐습니다. 기능을 옮길 때 가장 어려운 데이터 분리와 두 시스템 사이의 동기화는 다루지 않았습니다.
앞 실습: Saga와 Outbox · 다음 실습: CI/CD 파이프라인