Skip to content

KR_CS_StatefulSet

somaz edited this page Mar 30, 2026 · 1 revision

Q6: StatefulSet과 Stateless 애플리케이션

질문: StatefulSet과 Stateless 애플리케이션의 차이를 설명하고, Kubernetes에서 각각의 배포 방법과 스케일링 전략을 설명하세요. Persistent Volume, Headless Service, Pod Identity의 역할을 중심으로 설명하세요.


주요 용어

용어 설명
StatefulSet 상태를 가진 애플리케이션을 관리하는 K8s 오브젝트
Stateless Application 내부 상태를 유지하지 않고 각 요청을 독립 처리하는 애플리케이션
Headless Service ClusterIP가 None인 서비스 — Pod IP를 직접 반환
Ordinal Index StatefulSet Pod의 순서 번호 (pod-0, pod-1, pod-2)
PVC (PersistentVolumeClaim) Pod가 PV를 요청하는 오브젝트
volumeClaimTemplates StatefulSet에서 각 Pod마다 PVC를 자동 생성하는 템플릿

Stateless vs Stateful 개념

Stateless (Deployment):               Stateful (StatefulSet):
┌──────┐ ┌──────┐ ┌──────┐           ┌──────────┐ ┌──────────┐ ┌──────────┐
│Pod A │ │Pod B │ │Pod C │           │ mysql-0  │ │ mysql-1  │ │ mysql-2  │
│      │ │      │ │      │           │ (Master) │ │ (Slave)  │ │ (Slave)  │
└──────┘ └──────┘ └──────┘           │  PV-0    │ │  PV-1    │ │  PV-2    │
         ↓                           └──────────┘ └──────────┘ └──────────┘
  Shared Database                         └─────── Replication ──────┘
  (External State)

Stateless vs Stateful 비교

항목 Stateless (Deployment) Stateful (StatefulSet)
Pod 이름 랜덤 (nginx-abc123) 순서 번호 (mysql-0, mysql-1)
생성 순서 동시 생성 가능 순차 생성 (0 → 1 → 2)
삭제 순서 동시 삭제 가능 역순 삭제 (2 → 1 → 0)
Network Identity 불안정 (Pod IP 변경) 안정적 (DNS 유지)
Storage 공유 또는 없음 각 Pod마다 PVC
Service Type ClusterIP / LoadBalancer Headless + ClusterIP
사용 사례 웹 서버, API 서버 DB, 메시징, 분산 스토리지

Kubernetes Deployment (Stateless)

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-deployment
spec:
  replicas: 3
  selector:
    matchLabels:
      app: nginx
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
      - name: nginx
        image: nginx:1.21
        resources:
          requests:
            memory: "64Mi"
            cpu: "250m"
          limits:
            memory: "128Mi"
            cpu: "500m"

Rolling Update:

  • maxSurge: 1 → 최대 replica+1개까지 동시 실행 허용
  • maxUnavailable: 0 → 항상 replica 수 유지 (무중단)

Kubernetes StatefulSet (Stateful)

apiVersion: apps/v1
kind: StatefulSet
metadata:
  name: mysql
spec:
  serviceName: mysql-headless   # Headless Service 필수
  replicas: 3
  selector:
    matchLabels:
      app: mysql
  template:
    spec:
      containers:
      - name: mysql
        image: mysql:8.0
        volumeMounts:
        - name: mysql-data
          mountPath: /var/lib/mysql
  volumeClaimTemplates:          # Pod마다 PVC 자동 생성
  - metadata:
      name: mysql-data
    spec:
      accessModes: ["ReadWriteOnce"]
      storageClassName: gp3
      resources:
        requests:
          storage: 10Gi

Headless Service

clusterIP: None 으로 설정하면 VIP 없이 Pod IP를 직접 반환.

apiVersion: v1
kind: Service
metadata:
  name: mysql-headless
spec:
  clusterIP: None
  selector:
    app: mysql
  ports:
  - port: 3306

DNS 조회 결과:

mysql-headless → 10.244.1.10 (mysql-0)
              → 10.244.2.20 (mysql-1)
              → 10.244.3.30 (mysql-2)

개별 Pod DNS:
mysql-0.mysql-headless.default.svc.cluster.local → 10.244.1.10
mysql-1.mysql-headless.default.svc.cluster.local → 10.244.2.20

Pod 재시작 후에도 DNS 이름 유지 → Master/Slave 직접 지정 가능.


Persistent Volume 관리

  • StatefulSet 삭제 시 PVC는 삭제되지 않음 (데이터 보존)
  • Pod 재생성 시 기존 PVC 재사용
  • PVC 수동 삭제 필요: kubectl delete pvc mysql-data-mysql-0

볼륨 확장 (StorageClass에서 allowVolumeExpansion: true 필요):

kubectl patch pvc mysql-data-mysql-0 \
  -p '{"spec":{"resources":{"requests":{"storage":"20Gi"}}}}'

Update Strategy

전략 동작
RollingUpdate (기본) 역순으로 순차 업데이트 (mysql-2 → mysql-1 → mysql-0)
OnDelete 자동 업데이트 없음, Pod 수동 삭제 시 새 버전으로 재생성
Parallel 모든 Pod 동시 생성/삭제 (순서 보장 불필요한 경우)

참고

Clone this wiki locally