목차
1. 개요: 왜 인프라를 변경했는가?
지난 Sprint #2까지 AWS ECS(Fargate) 기반으로 서비스를 운영했으나, 서비스 규모가 커짐에 따라 더 세밀한 트래픽 제어, 선언적 배포(GitOps), 그리고 복잡한 마이크로서비스 간의 트랜잭션 관리가 필요해졌습니다.
이번 Sprint #3에서는 Kubernetes(EKS)로 플랫폼을 전환하며, Istio Service Mesh와 Kafka(MSK) 기반의 이벤트 구동 아키텍처(EDA)를 도입하여 시스템의 유연성과 안정성을 확보하는 데 주력했습니다.
2. Architecture Overview
전체적인 아키텍처는 Network, Compute, Service, Data, DevOps, Observability 계층으로 나누어 설계했습니다.
주요 변화 (ECS vs EKS)
구분 | 기존 (Sprint #2) | 변경 (Sprint #3) | 도입 이유 |
Orchestration | ECS Fargate | EKS + Karpenter | 확장성 및 벤더 종속성 탈피 |
CI/CD | Jenkins | GitHub Actions + ArgoCD | GitOps 기반 선언적 관리 |
Network | Spring Gateway | Istio Ingress + Envoy | mTLS 보안 및 카나리 배포 |
Event | - | Kafka (MSK) | 결제/주문 간 결합도 감소 |
Observability | CloudWatch | Prometheus+Grafana+Loki | 상세한 메트릭/로그/트레이싱 |
3. 핵심 설계 포인트
① Event-Driven Architecture와 SAGA 패턴 (결제 시스템)
결제(Payment), 주문(Order), 상품(Product) 서비스 간의 데이터 정합성을 보장하기 위해 Kafka(MSK)를 도입하고 SAGA 패턴(Choreography)을 적용할 것입니다.
•
문제: 결제는 성공했으나 재고 감소가 실패할 경우, 데이터 불일치 발생
•
해결:
1.
성공 시: payments-paid 이벤트 발행 → 주문 상태 변경
2.
실패 시(보상 트랜잭션): payments-failed 발행 → 주문 취소 및 재고 롤백 수행
Engineer's Note: 장애 대응을 위한 DLT (Dead Letter Topic) Kafka Consumer가 메시지 처리에 실패할 경우를 대비해 DLT(Dead Letter Topic) 전략을 수립했습니다.
•
단순 네트워크 지연 등은 자동 재시도하지만, 논리적 오류로 처리가 불가능한 메시지는 DLT로 격리하여 운영자가 수동으로 복구하거나 원인을 분석할 수 있도록 설계했습니다.
② 안전한 배포 전략: Istio 기반 Canary Deployment
기존 Blue/Green 배포는 리소스가 2배로 필요하다는 단점이 있었습니다. 이번에는 Istio VirtualService를 활용해 트래픽을 점진적으로 전환하는 Canary 배포를 구현할 예정입니다.
•
배포 시나리오:
1.
Phase 0: 신규 버전(v2) 배포 (트래픽 0%)
2.
Phase 1: 트래픽 10% 전환 → 로그 및 에러율 검증
3.
Phase 2: 트래픽 50% 전환 → 비즈니스 에러 모니터링
4.
Phase 3: 트래픽 100% 전환 (완료)
•
Rollback: 5xx 에러율이 3%를 넘거나 Latency가 200ms 이상 증가할 경우 즉시 v1으로 롤백합니다.
③ 효율적인 오토스케일링: Karpenter + HPA
기존 Cluster Autoscaler는 노드가 뜨는 데 시간이 오래 걸리는 문제가 있습니다. 이를 해결하기 위해 Karpenter를 도입했습니다.
•
Karpenter: Pod가 Pending 상태가 되기 직전, 적절한 인스턴스 타입을 찾아 JIT(Just-in-Time)으로 노드를 프로비저닝합니다.
•
버퍼 전략: 노드가 생성되는 수십 초의 딜레이 동안 서비스 장애를 막기 위해, 주요 서비스(결제/주문)의 HPA minReplicas를 평시 대비 130~150% 여유 있게 설정하여 트래픽 스파이크를 방어하도록 설계했습니다.
4. Observability (관찰 가능성)
MSA 환경에서는 장애 추적이 어렵기 때문에 LGTM(Loki, Grafana, Tempo, Prometheus) Stack을 구축하려합니다.
•
Metrics: Prometheus Operator를 통해 Spring Boot Actuator와 Istio 메트릭 수집
•
Logs: Fluent Bit를 DaemonSet으로 띄워 컨테이너 로그를 Loki로 전송
•
Tracing:
◦
Envoy(Network Layer)와 Application(Code Layer)의 Trace를 연결했습니다.
◦
Envoy에서 생성된 Zipkin 포맷과 앱의 OTel 정보를 Trace ID로 결합하여, 요청이 인그레스부터 DB까지 도달하는 전 과정을 End-to-End로 추적할 수 있습니다.
5. 마치며 (Retrospective)
이번 아키텍처 고도화를 통해 배포의 안정성(Canary)과 데이터 처리의 신뢰성(Kafka SAGA)을 확보할 것으로 기대합니다.
특히 GitOps(ArgoCD)를 도입함으로써 인프라 변경 사항을 코드(Code)로 관리하고 추적할 수 있게 된 점이 운영 측면에서 큰 이점으로 다가올 것입니다.
향후에는 현재 수동으로 진행하는 Canary 배포 검증 과정을 Argo Rollouts를 도입해 완전 자동화하는 것을 목표로 하고 있습니다.
