← 스터디 홈
6편 · 약 10분

binlog 운영·보존·모니터링

운영자의 binlog 걱정 세 가지

binlog를 실제로 운영할 때 반복되는 고민은 크게 세 가지다.

  1. 디스크가 찬다 — 만료 설정을 잘못하거나 레플리카가 멈추면 binlog가 무한 쌓인다.
  2. 어디까지 삭제해도 되는지 모른다 — 잘못 삭제하면 레플리카가 깨진다.
  3. 무슨 이유로 복제가 늦는지 보이지 않는다 — 지표 없이 장애를 감지하기 어렵다.

이 챕터는 이 세 가지 문제를 각각 다루는 운영 레시피다.

보존 기간 설정

binlog_expire_logs_seconds

MySQL 8.0부터 expire_logs_days는 폐기됐다. 초 단위로 표현하는 binlog_expire_logs_seconds를 쓴다.

-- 7일 보존 (604800초)
SET PERSIST binlog_expire_logs_seconds = 604800;

자동 만료는 두 시점에 트리거된다.

  • 서버 시작 시
  • binlog가 로테이션될 때(새 파일로 전환될 때)

즉, 만료 설정을 줄여도 현재 쓰고 있는 파일이 로테이션되기 전까지는 삭제가 일어나지 않는다.

CDC 도구(Debezium 등)를 쓴다면: CDC 도구가 오프라인이던 사이에 binlog가 만료되면 재시작 시 전체 스냅샷을 다시 해야 한다. CDC 도구의 최대 예상 다운타임보다 넉넉하게 설정한다. 최소 14일 이상을 권장하는 이유가 여기에 있다.

클라우드 환경의 차이

AWS RDS/Aurora에서는 인스턴스 변수 대신 전용 프로시저를 사용한다.

-- RDS MySQL — 시간 단위
CALL mysql.rds_set_configuration('binlog retention hours', 168);

-- Aurora MySQL
CALL mysql.rds_set_configuration('binlog retention hours', 168);

binlog_expire_logs_seconds를 직접 수정해도 RDS에서는 적용되지 않거나 재시작 후 초기화될 수 있다.

현재 binlog 파일 목록 확인

SHOW BINARY LOGS;

출력 예:

+------------------+-----------+-----------+
| Log_name         | File_size | Encrypted |
+------------------+-----------+-----------+
| binlog.000087    | 107374182 | No        |
| binlog.000088    | 107374182 | No        |
| binlog.000089    |  45128341 | No        |
+------------------+-----------+-----------+

File_size 합계가 디스크 binlog 점유량이다. 현재 쓰고 있는 파일(마지막 항목)은 아직 닫히지 않아 파일 크기가 작게 보인다.

로테이션: 파일이 바뀌는 조건

binlog는 단일 파일에 계속 추가되다가 다음 조건 중 하나가 충족되면 새 파일로 전환된다.

  • max_binlog_size(기본 1 GB)에 도달
  • 서버 재시작
  • FLUSH BINARY LOGS 실행
-- 현재 파일을 닫고 다음 번호 파일을 연다 (삭제 아님)
FLUSH BINARY LOGS;

백업 직전에 FLUSH BINARY LOGS를 실행하면 "백업 완료 시점"과 "binlog 파일 경계"를 일치시켜 PITR(Point-in-Time Recovery) 처리를 단순하게 만들 수 있다.

안전한 수동 삭제

자동 만료 외에 수동으로 정리해야 할 때가 있다. 레플리카가 읽고 있는 파일을 삭제하면 복제가 깨진다.

레플리카 위치 확인 후 삭제

-- 1단계: 각 레플리카의 읽기 위치 확인
SHOW REPLICA STATUS\G
-- Read_Source_Log_Pos 와 Source_Log_File 필드 확인

-- 2단계: 모든 레플리카가 binlog.000088 이상을 읽고 있다면
PURGE BINARY LOGS TO 'binlog.000088';

-- 또는 날짜 기준
PURGE BINARY LOGS BEFORE '2026-06-01 00:00:00';

PURGE BINARY LOGS는 MySQL이 내부적으로 레플리카 위치를 고려한다. 등록된 레플리카가 아직 읽고 있는 파일보다 이전 파일만 삭제한다. 그러나 레플리카가 연결 해제된 상태면 MySQL이 위치를 알 수 없어 잘못 삭제될 위험이 있다.

원칙: 수동 삭제 전에 반드시 SHOW REPLICA STATUS를 실행하고, 모든 레플리카가 삭제 대상보다 앞선 위치에 있음을 확인하라.

운영 흐름 다이어그램

binlog 생명주기 ① 기록 트랜잭션 커밋 → 활성 파일에 추가 ② 로테이션 max_binlog_size 도달 또는 FLUSH BINARY LOGS ③ 보존 expire_logs_seconds 기간 동안 유지 ④ 삭제 자동(만료) 또는 PURGE BINARY LOGS Replica SHOW REPLICA STATUS Source_Log_File Read_Source_Log_Pos 수동 삭제 전 위치 확인 모니터링 포인트 • SHOW BINARY LOGS → 디스크 점유량 • Seconds_Behind_Source → 복제 지연 • Relay_Log_Space → relay log 크기 • binary_log_transaction_compression_stats PITR (Point-in-Time Recovery) 흐름 ① 전체 백업 복원 ② 복구 목표 시점 직전 binlog 파일 특정 ③ mysqlbinlog 적용 mysqlbinlog --start-datetime="..." --stop-datetime="..." binlog.000089 | mysql -u root -p
binlog 운영 사이클 — 생성·로테이션·보존·삭제

PITR: binlog로 특정 시점 복구

풀 백업 직후 실수로 데이터를 삭제했다면 binlog를 재생해 복구할 수 있다.

# 특정 시간 범위의 binlog 이벤트를 추출해 적용
mysqlbinlog \
  --start-datetime="2026-06-11 09:00:00" \
  --stop-datetime="2026-06-11 09:14:00" \
  /var/lib/mysql/binlog.000089 | mysql -u root -p

주의: mysqlbinlog를 쓸 때 압축 binlog(binlog_transaction_compression = ON)는 도구가 자동으로 압축을 푼다. 특별한 옵션 없이 동일하게 사용할 수 있다.

시간 기반 복구는 클록 스큐(clock skew)로 오차가 생길 수 있다. 정밀하게 복구할 때는 --start-position / --stop-position으로 이벤트 오프셋을 직접 지정한다.

모니터링 지표 정리

복제 지연

SHOW REPLICA STATUS\G
-- Seconds_Behind_Source: 레플리카가 소스 대비 몇 초 뒤처지는지
-- Relay_Log_Space: relay log 누적 크기
-- Source_Log_File / Read_Source_Log_Pos: 현재 읽고 있는 파일/위치

Seconds_Behind_SourceNULL이면 I/O 스레드가 중단된 것이다. 0이라도 순간적으로 낮아 보일 수 있으므로 10초 이상 추이를 추적한다.

디스크 사용량 쿼리

SELECT
  SUM(file_size) / 1024 / 1024 / 1024 AS binlog_gb
FROM information_schema.FILES
WHERE file_type = 'REDO LOG';
-- 단, FILES 뷰는 InnoDB redo log를 보여준다.
-- binlog 크기 합산은 SHOW BINARY LOGS를 파싱하거나
-- OS 레벨에서 du 를 사용한다.

실제로는 셸 스크립트로 주기적으로 SHOW BINARY LOGS 결과를 파싱해 Prometheus/Grafana에 푸시하는 방식이 일반적이다.

알림 설정 가이드

지표경고(Warning) 임계값위험(Critical) 임계값
binlog 디스크 점유율60%80%
Seconds_Behind_Source30초300초
Relay_Log_Space20 GB50 GB
binlog 파일 수보존 기간 × 2배 이상

보존 기간 × 2배를 넘는 파일 수는 자동 만료가 제대로 작동하지 않고 있다는 신호다.

운영 체크리스트

배포나 스키마 변경 전에 점검해야 할 사항:

  • binlog_expire_logs_seconds 값이 CDC/레플리카 예상 다운타임보다 넉넉한가?
  • SHOW REPLICA STATUS에서 모든 레플리카의 Seconds_Behind_Source가 0에 가까운가?
  • max_binlog_size가 디스크 여유 공간과 비교해 적절한가?
  • 수동 PURGE BINARY LOGS 전에 레플리카 위치를 확인했는가?
  • PITR 복구 절차가 문서화되어 있고, 마지막으로 실제로 테스트한 날짜가 최근인가?

References

  • https://dev.mysql.com/doc/refman/8.4/en/purge-binary-logs.html
  • https://dev.mysql.com/doc/refman/8.4/en/point-in-time-recovery-binlog.html
  • https://dev.mysql.com/doc/refman/8.4/en/replication-options-binary-log.html
  • https://docs.upsolver.com/upsolver-1/connecting-data-sources/cdc-data-sources-debezium/mysql-cdc-data-source/binlog-retention-in-mysql
  • https://www.mydbops.com/blog/maintenance-of-mysql-binary-logs
  • https://repost.aws/knowledge-center/aurora-mysql-increase-binlog-retention
  • https://www.percona.com/blog/mysql-replication-got-fatal-error-1236-causes-and-cures/