IL-0569 DeNA · 2026-06-11 (게시일)database
MySQL master 장애 때 MHA 자동 Failover 뒤 slave 한 대가 relaylog를 적용하지 못해 레플리케이션이 멈췄다
DeNA는 MySQL 레플리케이션에서 master가 고장 나도 짧은 다운타임과 최소한의 데이터 손실로 레플리케이션 구성을 되살리는 고가용성 툴 MHA를 쓴다. MHA는 Failover 때 slave에 전송됐지만 실행되지 않은 relaylog, 다른 slave에만 전송된 relaylog, 옛 master에만 남은 binlog를 i1, i2, X 순서로 이어 붙여 mysqlbinlog로 MySQL에 적용한다. 그래서 이어 붙인 파일의 맨 앞에는 늘 relaylog가 온다.
binlog의 첫 이벤트인 Format_description_event, 줄여서 FDE는 MySQL 버전 같은 메타데이터를 담고, mysqlbinlog는 이 FDE를 보고 binlog를 읽는 데 필요한 정보를 얻는다. relaylog에는 slave가 쓴 FDE와 master에서 전송된 FDE가 차례로 두 번 나온다. 2015년에 나온 MySQL 5.7.9는 Bug #76887을 고치면서 mysqlbinlog가 relaylog의 첫 FDE, 곧 slave가 쓴 FDE를 읽어도 그 내용을 출력하지 않게 바꿨다. MHA는 첫 파일의 첫 FDE만 잘라 쓰도록 구현돼 있었다. 그래서 이 변경 뒤에는 MHA가 꼭 필요한 master FDE를 쓰지 못했고, mysqlbinlog는 데이터 갱신 이벤트를 만나면 FDE를 아직 읽지 않았다고 판단해 에러를 냈다.
이 에러는 MySQL 5.7.9 이상에서만 난다. 그중에서도 Failover 때 자신보다 옛 master의 binlog를 더 많이 읽은 다른 slave가 있는 slave나, 받았지만 실행하지 않은 relaylog가 남은 slave에서만 난다. 이런 상황은 binlog 전송 중 특정 시점에 master가 갑자기 멈춰야 생기므로 드물었고, 그래서 버그도 오래 드러나지 않았다. DeNA 환경에서는 글이 나오기 몇 년 전 이벤트 당일 한 번만 일어났다. slave 3대 중 1대만 영향을 받아 그 인스턴스를 서비스에서 빼 운영 환경에 미치는 영향을 줄였다. 원인은 데이터 불일치에서 시작해 MHA 소스코드, MySQL 소스코드, binlog 사양까지 거슬러 올라가 찾았다.
- 심각도
- –
- 영향 범위
- One of three replicas of the failed master could not apply data and was removed from service; the automatic failover kept the game service running
- 영향 사용자
- –
- 지역
- –
- 감지까지
- –
- 복구까지
- –
증상
글로벌 게임의 이벤트 당일, 인스턴스마다 1000 rps 가까운 부하가 걸린 가운데 master 인스턴스 한 대가 호스트 고장으로 멈췄다. MHA가 평소대로 자동 Failover를 해 서비스는 이어졌지만, 원래 있던 slave 3대 중 1대가 레플리케이션 에러를 내며 최신 데이터를 따라가지 못했다.
조사해 보니 MHA가 slave의 데이터를 최신으로 맞추는 과정에서 relaylog를 읽지 못하고 다음 에러를 냈다. ERROR: malformed binlog: it does not contain any Format_description_log_event. I now found a Update_rows event, which is not safe to process without a Format_description_log_event.
이 slave는 옛 master의 최신 데이터를 받지 못했고, 그 뒤 새 master에서 받은 relaylog에서도 데이터 불일치를 일으켜 데이터를 갱신하지 못했다.
증상 복제 지연
원인
- 촉발
- 부하가 높은 이벤트 당일 master 인스턴스 한 대가 호스트 고장으로 멈췄고, MHA가 Failover 중 slave의 데이터를 최신화하면서 mysqlbinlog로 relaylog를 적용했다.
감지
–
조치
- 최신 데이터를 받지 못한 slave 인스턴스를 서비스에서 빼 운영 환경에 미치는 영향을 줄였다.
후속 조치
–
교훈
MySQL을 대규모로 쓰면 MySQL 5.7.9의 mysqlbinlog 변경을 MHA가 따라가지 못한 것처럼 드문 조건에서만 드러나는 문제도 만난다. 이번에도 운영 환경의 데이터 불일치에서 시작해 MHA와 MySQL의 소스코드, binlog 사양까지 거슬러 올라가서야 원인을 찾았다.
출처
참고 문서
관련 사례
IL-0308RevenueCat 이 Aurora PostgreSQL 10 에서 14 새 클러스터로 넘어간 직후 쿼리가 극도로 느려져 대시보드와 SDK 엔드포인트가 세 시간 넘게 실패했다RevenueCat · 2022같은 원인 · 공통 데이터베이스 복제, 데이터베이스
IL-0572Merpay 회계 이벤트 처리 시스템에서 Cloud Pub/Sub 메시지 1000만 건이 밀려 새 회계 데이터가 하루 넘게 Cloud Spanner에 들어가지 못했다Mercari · 2026같은 원인 · 공통 데이터베이스
같은 원인 · 공통 데이터베이스
IL-0316밀린 배포가 한꺼번에 몰린 Control Plane 에서 새 버전 PgBouncer 가 CPU 와 메모리를 비정상적으로 많이 써 데이터베이스 연결이 타임아웃됐다Railway · 2025같은 원인 · 공통 데이터베이스
같은 원인 · 공통 데이터베이스
IL-0444Aurora MySQL 에서 ALTER TABLE 을 실행할 때마다 그 테이블을 reader 로 읽던 커넥션이 끊겨 애플리케이션 오류가 쏟아졌다Repro · 2024같은 원인 · 공통 데이터베이스
IL-0117인그레스 업그레이드가 네트워크 컨트롤 플레인 회귀를 일으켜 데이터 플레인이 잠깐 끊겼고, 한꺼번에 재시작한 서비스들이 백엔드 저장소에 과부하를 일으켜 OpenAI API 오류가 늘었다OpenAI · 2024같은 원인 · 공통 데이터베이스
같은 원인 · 공통 데이터베이스
같은 원인 · 공통 데이터베이스
같은 원인 · 공통 데이터베이스
내 클러스터에도 있는지 확인하기
AI 도구와 스크립트용
- 이 사례의 JSON: https://incidentlib-api.benchlet.com/cases/IL-0569
- 가장 비슷한 사례들: https://incidentlib-api.benchlet.com/cases/IL-0569/similar
- MCP 서버(Streamable HTTP, 키 없음):
https://incidentlib-mcp.benchlet.com/mcp
API 는 키가 필요 없습니다. MCP 서버는 search_incidents, get_incident, list_incidents, get_topic, vocab 도구를 내놓습니다. 사용법은 API 와 MCP.