Incident Library
  • 원인
  • 구성 요소
  • 증상
  • 기여 요인
  • 사례

사례24건

24건 중 9~13번째

  1. 증상

    2025-01-15 09:55 CET 무렵부터 11:36 CET까지 데이터베이스 장애로 Magic Pages의 고객 웹사이트가 영향을 받았다. 노드 세 대로 된 MySQL 클러스터에서 내려간 노드를 다시 붙이려 하자 데이터베이스 서버가 메타데이터 정보가 없다는 모호한 오류를 냈다.

    촉발

    그날 앞서 MySQL 클러스터의 세 노드 중 하나가 내려갔고, 창업자가 그 노드를 클러스터에 다시 붙이려 했다.

    원인
    구성 요소
    기여 요인
    조치
    • PVC 프로비저닝 문제를 풀려고 스토리지 서버를 재시작했다. 재시작은 몇 초 만에 끝났다.
    • 스토리지가 돌아온 뒤 클러스터 메타데이터를 다시 만들 수 있도록 MySQL 노드들이 복원되고 서로 동기화되기를 약 45분 기다렸다.
    • 깨진 클러스터 메타데이터를 정리했다.
    • 데이터베이스 노드로 트래픽을 보내는 MySQL Router를 다시 배포했다.
    후속 조치
    • 스토리지 시스템의 상태 모니터링을 강화한다.
    • MySQL Router의 장애 조치 절차를 개선한다.
    • 상태 페이지가 믿을 만한 정보를 보이도록 문제를 조사하고 고친다.
    교훈

    고가용성 구성 덕분에 데이터는 잃지 않았고 첫 노드 장애도 클러스터가 문제없이 넘겼다. 하지만 중복 구성인데도 클러스터 메타데이터가 단일 장애 지점이었다. PVC 상태를 더 잘 모니터링했다면 비슷한 문제를 막을 수 있었고, 45분 걸린 복구는 더 줄일 여지가 있다. 상태 페이지는 고객 사이트 실패를 감지하도록 설정했는데도 이 장애를 바로 알아채지 못했다.

  2. 증상

    FR-PAR-1 가용 영역의 하이퍼바이저 약 25% 가 리전의 나머지와 VPC 로 통신하지 못했다. 7:50 부터 8:01 UTC 까지 Managed Database, Redis, Serverless, Kubernetes Kapsule 처럼 VPC 에 기대는 제품이 함께 영향을 받았다.

    촉발

    6:20 UTC 에 랙 하나의 ToR 스위치 소프트웨어가 충돌했다. 이 불안정이 같은 랙의 하이퍼바이저에서 돌던 VPC 용 BGP 경로 반사기를 비정상 상태에 빠뜨렸다.

    원인
    구성 요소
    기여 요인
    감지

    Scaleway 의 Customer Excellence 팀과 SRE 팀이 영향을 알아채고 사고를 열었다. RR 의 헬스 체크 모니터링도 이상을 잡았지만 자동 재시작은 실패했다.

    조치
    • 멈춘 VPC 경로 반사기 두 대를 손으로 고쳤다.
    후속 조치
    • 멈춘 상태의 경로 반사기를 고치지 못한 자동 복구 장치를 고쳤다. 수정 내용은 https://github.com/FRRouting/frr/pull/17163 이다.
    • 버그 하나가 여러 경로 반사기를 한꺼번에 멈추지 않도록 경로 반사기의 소프트웨어 버전을 서로 다르게 둔다.
    • 경로 반사기를 멈춘 상태에 빠뜨린 소프트웨어 문제를 깊이 조사한다.
  3. 증상

    2024-03-13 10:01 UTC 에 쿠버네티스 노드 하나가 NotReady 상태가 됐다. 그때 노드에 잡힌 requests 는 CPU 78%, 메모리 82% 였다. 10:03 에 Slack 으로 알림이 왔고, 10:05 에 알림을 보고 조사를 시작했다.

    촉발

    Hangfire 로 작업을 실행하는 개발 컨테이너가 Grafana Agent 가 메모리를 많이 쓰고 있던 노드에 배치됐고, 작업이 OOM 으로 실패하며 CrashLoopBackOff 를 반복했다.

    원인
    구성 요소
    기여 요인
    감지

    10:03 UTC 에 Slack 으로 알림이 왔고, 10:05 에 알림을 확인하고 조사를 시작했다. 두 번째 노드는 15:03 에 Slack 알림이 왔고 15:09 에 확인했다. 탐지까지 걸린 시간은 4분이었다.

    조치
    • 10:22 에 EC2 인스턴스를 비정상으로 표시해 새 노드를 띄웠다.
    • 10:30 에 NotReady 노드를 cordon 하고 강제로 drain 했고, 10:36 에 그 EC2 인스턴스를 종료했다.
    • 13:02 에 네임스페이스에서 LimitRange 를 지우고 Grafana Agent 파드를 재시작했다.
    • 14시대에 문제의 개발 컨테이너를 0개로 줄였고, 몇 분 뒤 EC2 네트워크 트래픽이 정상으로 돌아왔다.
    • 두 번째 NotReady 뒤 15:15 에 개발 컨테이너를 다시 0개로 줄였고, 15:18 에 새 노드가 추가됐다.
    • 15:19 에 개발 컨테이너를 맡은 팀에 메일을 보냈고, 15:52 에 그 팀이 문제를 확인하고 수정 중이라고 답했다.
    후속 조치
    • grafana-agent 를 모니터링 노드 그룹으로 옮긴다.
    • 클러스터 전체 대역폭이 정해 둔 기준에 닿으면 알림을 보낸다.
    • grafana-agent Helm 차트에 메모리 한도를 걸 수 있는지 조사한다.
    • grafana-agent 의 메모리 사용량을 조사한다.
    • grafana-agent 에 PVC 를 써야 하는지 Grafana 지원팀에 묻는다.
    • 보존 기간을 제한한 채 노드 로그를 Loki 로 보내는 방안을 검토한다.
    • 쿠버네티스 노드 문제를 조사할 때 확인할 자주 쓰는 지표와 로그 쿼리를 위키 페이지로 만든다.
    교훈

    포스트모템에서 나온 후속 조치를 끝까지 챙겨야 한다. CloudWatch 에서 어떤 지표가 쓸모 있는지가 팀에 제대로 공유되지 않아 진단과 조사가 어려웠다.

  4. 증상

    02:15 UTC 무렵부터 API 수집 엔드포인트의 이벤트 처리가 느려졌다. 실패는 났다가 멎기를 되풀이했고, 끝내 몇 분 동안 수집이 완전히 멈췄다. 기본으로 걸어 둔 알림이 수집 성능과 안정성 문제를 온콜 엔지니어에게 알렸다. 상태 페이지 첫 공지는 수집 서비스의 오류율과 응답 시간이 평소보다 높다는 알림을 조사하고 있다는 내용이었다.

    촉발

    몇 분 사이에 여러 곳에 흩어진 연결에서 비정상적으로 많은 쿼리가 들어왔다.

    원인
    구성 요소
    기여 요인
    감지

    기본으로 걸어 둔 알림이 수집 성능과 안정성 문제를 온콜 엔지니어에게 알렸다. 자동 로드 셰딩 장치도 작동하면서 알림을 더 보냈다. 상태 페이지 첫 공지는 18:28 PST 에 올라왔다.

    조치
    • 엔지니어들이 용량을 확보하려고 수집 호스트 수를 수동으로 크게 늘렸다.
    • 몇 분 동안 수집 트래픽 대부분을 끊고 수집 호스트 용량을 다시 확보했다.
    • 가장 공격적으로 트래픽을 보내던 발신처의 속도 제한을 트래픽이 가라앉을 때까지 임시로 낮춰 클러스터를 안정시켰다.
    후속 조치
    • 장기 해결책을 마련하는 동안 같은 장애가 반복되지 않도록 수집 호스트 수를 늘려 두었다.
    • 이번 장애 경로를 막을 프로젝트를 정하는 일에 집중한다.
    교훈

    Honeycomb 은 이번 장애를 이미 대비책이 있던 장애의 변형으로 보았다. 이번 장애는 그 대비책 일부를 비켜 가는 방식으로 일어났다. 실패했던 호스트들이 쿠버네티스의 CrashLoopBackOff 상태에 걸려 오프라인으로 남으면서 급하게 늘린 용량을 깎아 먹었다. OTel 처럼 배치 단위로 성공과 실패를 알리는 프로토콜에서는 서버가 일부만 버려도 클라이언트가 배치 전체를 다시 보내 트래픽이 크게 불어날 수 있다.

  5. 증상

    인프라를 Google Cloud 로 모두 옮긴 뒤 Postgres 연결 타임아웃이 평소보다 많이 나서 인시던트를 선언했다. 초당 새로 여는 연결 수가 수백 개 수준에서 크게 오르내렸다.

    촉발

    노드에서 짧게 열고 닫는 TCP 연결이 대량으로 생겼다. 연결 풀이 초당 수백 개씩 새 연결을 열었고, 실수로 들어간 데이터베이스 join 때문에 외부 제3자 서비스로 가는 중복 호출 수천 번이 한꺼번에 나갔다.

    원인
    구성 요소
    기여 요인
    감지

    Postgres 연결 타임아웃이 평소보다 많이 나는 것을 보고 인시던트를 선언했다.

    조치
    • Postgres 연결의 최대 수명을 15m 에서 30m 로 두 배 늘렸다.
    • 연결 풀을 늘 N개의 연결을 열어 두는 고정 크기로 바꿨다.
    • memcache 클라이언트의 MaxIdleConns 를 2 에서 20 으로 올렸다.
    • 변수를 줄이려고 Google 이 운영하는 memcached 대신 쿠버네티스 클러스터 안에서 직접 돌리는 memcached 로 옮겼다. 이 전환으로는 거의 달라지지 않았다.
    • 실수로 들어간 데이터베이스 join 때문에 외부 제3자 서비스로 중복 호출을 수천 번 보내던 문제의 수정을 운영에 배포했다. 그 뒤 데이터베이스 연결 문제와 캐시 문제가 거의 사라졌다.
    후속 조치
    • 외부로 나가는 네트워크 호출에 더 알맞은 동시성 한도를 둔다. 공급자의 rate limit 안에 있어도 노드에 영향을 줄 수 있기 때문이다.
    교훈

    가설을 너무 빨리 좁히지 않는다. 이런 네트워크 타임아웃을 보면 같은 파드만이 아니라 같은 노드에서 도는 모든 것을 포함해 시스템 전체의 활동을 봐야 한다. 오류와 그 영향은 대개 요청 하나에 머물지만 늘 그렇지는 않다. 외부로 나가는 네트워크 호출의 동시성도 제한해야 한다. 이전에는 공급자의 rate limit 이 주된 제약이었지만, rate limit 안에 있어도 노드에 영향을 줄 수 있다.

내 클러스터에도 있는지 확인하기

이 24건에서 가장 많이 나오는 구성 요소: 데이터베이스, 영구 볼륨과 스테이트풀셋. kubegap 은 Claude Code 나 Codex 에서 쿠버네티스 클러스터를 읽기만 하며 이런 틈을 점검합니다. 점검 항목의 근거는 이 라이브러리와 같은 공개 보고서입니다.

원인별7

설정 변경1건

조직
  1. IL-0179 DEBUG 로그가 쏟아지자 동기 로깅을 하던 요청 스레드들이 가득 찬 stdout 파이프에서 멈춘 채 DB 커넥션을 쥐고 있어, HikariCP 커넥션 풀이 고갈되고 요청이 30초 주기로 한꺼번에 실패했다.

용량 한계10건

  1. IL-0435 Aurora MySQL 이 OOM 을 피하려고 커넥션을 끊고 쿼리를 거부해 애플리케이션 오류율이 올랐다
  2. IL-0350 TXL 클러스터 한 곳의 호스트 네트워크가 끊기고 프로비저닝 대기열이 밀려 여러 서비스가 오래 나빠졌다
  3. IL-0100 노드가 파드의 CPU 요청에 비해 작아 CPU 가 포화되면서 PostHog 기능 플래그 서비스에 열흘 사이 장애가 세 번 났다.
  4. IL-0110 Grafana Agent 파드가 메모리를 많이 쓰던 노드에 Hangfire 파드가 함께 올라가 시스템 OOM 으로 CrashLoopBackOff 를 반복했고, 노드가 응답을 멈추고 NotReady 가 됐다.
    DFDS2024
  5. IL-0202 갑자기 몰린 쿼리와 데이터베이스 쓰기로 Honeycomb 수집 호스트가 메모리 부족으로 죽었고, 쿠버네티스 CrashLoopBackOff 가 용량 회복을 막아 US1 이벤트 수집이 한 시간 넘게 불안정했다
  6. IL-0386 Google Cloud 로 옮긴 뒤 GKE 노드에서 Postgres 연결 타임아웃과 memcached i/o timeout 이 간헐적으로 튀었다
  7. IL-0500 UToronto JupyterHub 의 데이터베이스 디스크가 가득 차서 로그인과 서버 시작이 500 오류로 실패했다
    2i2c2022
  8. IL-0206 GKE 파드 안의 Consul 에이전트가 메모리 급증으로 거듭 OOM kill 되어 Rails 파드가 데이터베이스 복제본을 찾지 못했고, 모든 쿼리가 primary 로 몰려 GitLab.com 이 느려졌다.
    GitLab2022
  9. IL-0037 imagePullPolicy가 Always인 DaemonSet이 크래시 루프를 돌며 이미지를 계속 받아, NAT 세 대를 같이 쓰던 리전 전체가 이미지 레지스트리에서 429로 막혔다
  10. IL-0064 CPU 를 많이 쓰는 파드가 Google Cloud 노드 하나에 몰려 노드가 커널 패닉으로 죽었고, 다시 배치된 파드가 다음 노드를 또 죽이며 웹사이트와 API 가 멈췄다.

소프트웨어 결함4건

  1. IL-0150 DynamoDB DNS 자동화의 경쟁 조건이 us-east-1 리전 엔드포인트의 DNS 레코드를 비워 DynamoDB 와 EC2 인스턴스 시작이 실패했고, 그 여파로 EKS, ECS, Fargate 의 컨테이너 시작과 클러스터 스케일링이 14시간 넘게 막혔다
  2. IL-0347 FR-PAR-1 가용 영역에서 하이퍼바이저 약 25% 의 VPC 연결이 11분 동안 끊겼다
  3. IL-0462 GKE 위 MySQL 파드 일부가 시작과 종료에 오래 걸려 KateSQL 인스턴스 교체가 느려졌다
  4. IL-0196 Redis Operator 로 레플리카를 늘리면서 메모리 한도를 낮추자 데이터를 가진 유일한 Redis 파드가 재시작됐고, Sentinel 이 빈 레플리카를 마스터로 올려 데이터가 모두 지워졌다.
    Palark2020

의존성 장애2건

  1. IL-0162 데이터베이스 업데이트 뒤 LKE 내부 DNS 서비스가 멈춰 사용자가 LKE 클러스터 컨트롤 플레인과 LKE 대시보드에 접속하지 못했다
    Linode2025
  2. IL-0489 Kubernetes 위 3노드 MySQL 클러스터에 노드를 다시 붙이다 메타데이터가 깨져 Magic Pages 고객 사이트가 내려갔다

배포 결함1건

  1. IL-0324 External Storage 데이터베이스 클러스터에 과부하가 걸려 mw-api-int, mw-parsoid, mw-jobrunner 의 지연과 데이터베이스 오류가 늘었다

클라우드 제공자 장애4건

  1. IL-0119 Cosmos DB 장애 뒤 ChatGPT 웹 서비스 파드가 헬스 체크 실패로 크래시 루프에 빠져 chatgpt.com 과 일부 API 의 오류율이 높아졌다.
    OpenAI2025
  2. IL-0145 Australia East 의 전압 강하로 냉각기가 멈춰 데이터 홀 장비가 꺼지면서, 영역 중복이 아닌 AKS 작업 큐 데이터베이스가 내려가 두 리전의 AKS 생성, 수정, 삭제 작업이 막혔다
  3. IL-0172 AWS 도쿄 리전 한 AZ 의 냉각 장애로 쿠버네티스 위에서 돌던 CockroachDB 노드 60대 중 6대가 22분 만에 죽었고, AZ 토폴로지 설정이 없어 일부 Range 가 정족수를 잃었다.
  4. IL-0193 GCP SSD 영구 디스크 장애로 Cassandra 파드가 볼륨을 붙이지 못했고, OrderedReady 정책 때문에 나머지 파드도 다시 뜨지 못한 데다 Metrictank 가 바뀐 Cassandra IP 로 다시 연결하지 못해, Grafana Cloud Graphite 쿼리 일부가 최대 23시간 실패했다.

운영 실수2건

  1. IL-0207 로컬 개발 환경에서 돌린 작업이 운영 컨텍스트로 넘어가 Kubernetes 클러스터의 Consul 릴리스를 통째로 지웠고, Patroni 가 무너져 GitLab.com 전체가 5XX 오류를 냈다.
    GitLab2022
  2. IL-0506 UC Berkeley DataHub 의 JupyterHub sqlite 데이터베이스가 빈 데이터베이스로 덮어써져 로그인이 실패하고 홈 디렉터리가 비어 보이고 다른 사용자로 로그인되는 문제가 났다