A one-line Kubernetes fix that saved 600 hours a year
Cloudflare가 Kubernetes StatefulSet의 fsGroupChangePolicy를 Always에서 OnRootMismatch로 변경해 Atlantis 재시작 시간을 30분에서 30초로 단축 및 월 50시간의 엔지니어링 블로킹 시간 제거
AI 요약
Context
Cloudflare는 Terraform 변경사항 관리를 위해 Kubernetes에서 Atlantis를 SingletonStatefulSet으로 운영했으나, 월 100회 재시작 시 30분씩 소요되어 월 50시간 이상의 엔지니어링 생산성이 손실되고 있었다. PersistentVolume에 저장된 수백만 개의 파일로 인해 inode 부족 경고가 반복 발생했으나, 재시작 시간 지연의 근본 원인은 명확하지 않았다.
Technical Solution
- kubelet의 systemd 로그를 Kibana에서 분석해 PersistentVolume 마운트 이후 pod 시작 간에 unexplained delay 발견
- Kubernetes 1.20 이상에서 지원하는 pod.spec.securityContext.fsGroupChangePolicy 필드 검토: 기본값 Always는 PersistentVolume의 모든 파일에 대해 재귀적 권한 변경을 수행
- fsGroupChangePolicy를 OnRootMismatch로 설정: PersistentVolume의 루트 디렉토리만 권한 확인하고, 필요한 경우에만 변경 수행
- StatefulSet 스펙에 한 줄 추가:
spec.template.spec.securityContext.fsGroupChangePolicy: OnRootMismatch - 변경 전 PersistentVolume 내 파일의 그룹 권한이 변경되지 않을 것을 검증
Impact
- Atlantis 재시작 시간: 30분 → 30초 (97% 감소)
- 월간 엔지니어링 블로킹 시간: 50시간 → 0시간 제거
- 연간 생산성 회복: 600시간
- On-call 엔지니어의 거짓 알람 응답 횟수 제거
Key Takeaway
Kubernetes의 기본 설정은 소규모 워크로드에 최적화되어 있으나, 수백만 파일이 저장되는 대용량 PersistentVolume에서는 fsGroup 기반의 재귀적 권한 변경이 성능 병목이 될 수 있다. 대규모 persistent volume을 운영하는 경우 fsGroupChangePolicy와 fsGroup 설정을 감시하고 필요시 OnRootMismatch로 조정해야 한다.
실천 포인트
Kubernetes에서 수백만 개 이상의 파일을 저장하는 PersistentVolume을 사용하는 StatefulSet 운영 환경에서, 원인 불명의 pod 시작 지연이 발생할 때 kubelet 로그를 통해 마운트와 pod 시작 간의 시간 갭을 확인하고, fsGroupChangePolicy를 OnRootMismatch로 설정하면 재귀적 권한 변경 오버헤드를 제거할 수 있다.