Service Mesh와 Istio
학습 목표
- Service Mesh의 필요성과 아키텍처 이해
- Istio 핵심 컴포넌트
- 트래픽 관리 (Canary, Blue-Green)
- mTLS를 통한 서비스 간 보안
Service Mesh란?
문제 상황
마이크로서비스가 늘어나면서 반복적인 문제:
각 서비스마다 구현 필요:
- 서비스 디스커버리
- 로드 밸런싱
- Circuit Breaker
- Retry 로직
- 메트릭 수집
- 분산 추적
- mTLS 암호화
→ 중복 코드, 언어별 구현, 운영 복잡도 증가
Service Mesh 솔루션
인프라 계층에서 통신 관련 기능을 자동으로 처리
┌──────────────┐ ┌──────────────┐
│ Service A │ │ Service B │
│ ┌──────────┐ │ │ ┌──────────┐ │
│ │ App │ │ │ │ App │ │
│ └─────┬────┘ │ │ └─────┬────┘ │
│ │ │ │ │ │
│ ┌─────▼────┐ │ │ ┌─────▼────┐ │
│ │ Sidecar │◄├─────────┤►│ Sidecar │ │
│ │ Proxy │ │ │ │ Proxy │ │
│ └──────────┘ │ │ └──────────┘ │
└──────────────┘ └──────────────┘
│ │
└────────┬───────────────┘
│
┌──────▼───────┐
│ Control Plane│
│ (Istio) │
└──────────────┘
Sidecar Proxy: 각 서비스 옆에 붙어서 모든 통신 처리
Istio 아키텍처
Control Plane (istiod)
중앙 제어:
- 프록시 설정 배포
- 서비스 디스커버리
- 인증서 관리
- 정책 관리
Data Plane (Envoy Proxy)
실제 트래픽 처리:
- 로드 밸런싱
- 트래픽 라우팅
- Health Check
- Metrics 수집
Istio 설치 (Kubernetes)
1. Istio CLI 설치
curl -L https://istio.io/downloadIstio | sh -
cd istio-1.20.0
export PATH=$PWD/bin:$PATH
2. Istio 설치
# Demo 프로필 (개발용)
istioctl install --set profile=demo -y
# Namespace에 자동 주입 활성화
kubectl label namespace default istio-injection=enabled
3. 샘플 앱 배포
# product-service.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: product-service
spec:
replicas: 3
selector:
matchLabels:
app: product
template:
metadata:
labels:
app: product
version: v1
spec:
containers:
- name: product
image: product-api:v1
ports:
- containerPort: 3000
---
apiVersion: v1
kind: Service
metadata:
name: product-service
spec:
selector:
app: product
ports:
- port: 80
targetPort: 3000
kubectl apply -f product-service.yaml
# Pod 확인 (2개 컨테이너: app + envoy)
kubectl get pods
NAME READY STATUS
product-service-xxx 2/2 Running # app + sidecar
트래픽 관리
1. Virtual Service (라우팅 규칙)
# product-virtualservice.yaml
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: product
spec:
hosts:
- product-service
http:
- match:
- headers:
user-type:
exact: premium
route:
- destination:
host: product-service
subset: v2 # Premium 사용자는 v2로
- route:
- destination:
host: product-service
subset: v1 # 나머지는 v1로
2. Destination Rule (서브셋 정의)
# product-destinationrule.yaml
apiVersion: networking.istio.io/v1beta1
kind: DestinationRule
metadata:
name: product
spec:
host: product-service
trafficPolicy:
loadBalancer:
simple: LEAST_REQUEST # 로드 밸런싱 알고리즘
connectionPool:
tcp:
maxConnections: 100
http:
http1MaxPendingRequests: 50
http2MaxRequests: 100
subsets:
- name: v1
labels:
version: v1
- name: v2
labels:
version: v2
trafficPolicy:
connectionPool:
tcp:
maxConnections: 200 # v2는 더 많은 연결 허용
3. Canary 배포
트래픽을 점진적으로 이동:
# 90% v1, 10% v2
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: product-canary
spec:
hosts:
- product-service
http:
- route:
- destination:
host: product-service
subset: v1
weight: 90
- destination:
host: product-service
subset: v2
weight: 10
점진적 롤아웃:
# 1단계: 10% 트래픽
kubectl apply -f canary-10.yaml
# 모니터링 후 문제없으면 2단계
kubectl apply -f canary-50.yaml # 50%
# 최종 단계
kubectl apply -f canary-100.yaml # 100%
4. A/B 테스팅
특정 조건에 따라 버전 분리:
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: product-ab-test
spec:
hosts:
- product-service
http:
- match:
- headers:
experiment:
exact: "true"
route:
- destination:
host: product-service
subset: v2-experiment
- route:
- destination:
host: product-service
subset: v1-stable
복원력 (Resilience)
1. Timeout 설정
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: product-timeout
spec:
hosts:
- product-service
http:
- route:
- destination:
host: product-service
timeout: 3s # 3초 timeout
2. Retry 설정
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: product-retry
spec:
hosts:
- product-service
http:
- route:
- destination:
host: product-service
retries:
attempts: 3
perTryTimeout: 2s
retryOn: 5xx,reset,refused-stream
3. Circuit Breaker
apiVersion: networking.istio.io/v1beta1
kind: DestinationRule
metadata:
name: product-circuit-breaker
spec:
host: product-service
trafficPolicy:
outlierDetection:
consecutiveErrors: 5 # 5번 연속 실패 시
interval: 30s
baseEjectionTime: 30s # 30초간 제외
maxEjectionPercent: 50 # 최대 50% Pod 제외
minHealthPercent: 40 # 최소 40% 건강 유지
보안 (mTLS)
자동 mTLS 활성화
apiVersion: security.istio.io/v1beta1
kind: PeerAuthentication
metadata:
name: default
namespace: default
spec:
mtls:
mode: STRICT # 모든 통신을 mTLS로 암호화
결과:
- Service A ↔ Service B 통신 자동 암호화
- 인증서 자동 발급/갱신 (15일마다)
- 애플리케이션 코드 변경 불필요
Authorization Policy
apiVersion: security.istio.io/v1beta1
kind: AuthorizationPolicy
metadata:
name: product-authz
spec:
selector:
matchLabels:
app: product
rules:
- from:
- source:
principals: ["cluster.local/ns/default/sa/order-service"]
to:
- operation:
methods: ["GET", "POST"]
paths: ["/api/products/*"]
의미:
- order-service만 product-service 호출 허용
- GET, POST 메서드만 허용
- 다른 서비스는 403 Forbidden
관찰성 (Observability)
1. Metrics (Prometheus)
# Prometheus 접근
kubectl port-forward -n istio-system svc/prometheus 9090:9090
# 주요 메트릭
istio_requests_total # 총 요청 수
istio_request_duration_seconds # 요청 처리 시간
istio_request_bytes # 요청 크기
istio_response_bytes # 응답 크기
2. Tracing (Jaeger)
# Jaeger UI 접근
kubectl port-forward -n istio-system svc/tracing 16686:16686
# 브라우저에서 http://localhost:16686
분산 추적 예시:
[API Gateway] → [Order Service] → [Product Service]
↘ [Inventory Service]
각 hop의 latency, 에러 추적 가능
3. Visualization (Kiali)
# Kiali 대시보드
kubectl port-forward -n istio-system svc/kiali 20001:20001
# http://localhost:20001
Kiali 기능:
- 서비스 토폴로지 시각화
- 트래픽 흐름 실시간 확인
- Health Check 상태
- Configuration 검증
실전 시나리오: Blue-Green 배포
# 1. 두 버전 모두 배포
apiVersion: apps/v1
kind: Deployment
metadata:
name: product-blue
spec:
replicas: 3
template:
metadata:
labels:
app: product
version: blue
spec:
containers:
- name: product
image: product-api:v1.0
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: product-green
spec:
replicas: 3
template:
metadata:
labels:
app: product
version: green
spec:
containers:
- name: product
image: product-api:v2.0
---
# 2. 초기에는 Blue로 100% 트래픽
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: product-blue-green
spec:
hosts:
- product-service
http:
- route:
- destination:
host: product-service
subset: blue
weight: 100 # 100% Blue
- destination:
host: product-service
subset: green
weight: 0 # 0% Green
---
# 3. Green 검증 후 전환
# kubectl apply -f product-blue-green-switch.yaml
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
name: product-blue-green
spec:
hosts:
- product-service
http:
- route:
- destination:
host: product-service
subset: blue
weight: 0 # 0% Blue
- destination:
host: product-service
subset: green
weight: 100 # 100% Green
핵심 정리
- Service Mesh는 통신 인프라를 코드에서 분리
- Istio = Control Plane (istiod) + Data Plane (Envoy)
- VirtualService로 라우팅, DestinationRule로 트래픽 정책
- Canary, Blue-Green 등 안전한 배포 전략
- mTLS로 서비스 간 자동 암호화
- Timeout, Retry, Circuit Breaker로 복원력 확보
- Prometheus, Jaeger, Kiali로 완전한 관찰성