Skip to content

PostgreSQL:Queue

Postgres 큐를 건강하게 유지하기

Postgres에서 job queue를 운영할 때 발생하는 고질적 문제인 dead tuple 누적과 이에 따른 테이블 bloat, 성능 저하의 원인과 해결 방법 정리

  • 큐 테이블은 대부분의 행이 삽입-읽기-삭제로 짧게 순환되므로 크기는 일정하지만 누적 처리량이 매우 큼
  • Postgres의 MVCC 구조상 삭제된 행은 즉시 제거되지 않고 dead tuple로 남아 정리되어야 하며, autovacuum이 이를 담당함
  • 장기 실행 트랜잭션이나 겹쳐 실행되는 분석 쿼리가 MVCC horizon을 고정시키면 autovacuum이 dead tuple을 정리하지 못해 큐 성능이 저하됨
  • PlanetScale의 Traffic Control(Insights 확장) 기능이 쿼리 클래스별 리소스 제한으로 이 문제를 해결하는 실용적 수단으로 제시됨

정리:

  • Postgres 기반 큐의 MVCC dead tuple 문제는 2015년의 유물이 아님
  • 현대 Postgres는 B-tree 개선과 SKIP LOCKED 로 상당한 여유를 제공하지만 근본 메커니즘은 동일
    • VACUUM이 dead tuple을 정리하지 못하면 누적됨
    • 장기 실행·겹치는 트랜잭션이 MVCC horizon을 고정하면 VACUUM이 정리하지 못함
  • “Just use Postgres”로 큐·분석·앱 로직을 한 DB에 두는 환경에서 이는 이론적 위험이 아닌 평상시의 운영 조건
  • 위험한 형태는 극적인 크래시가 아니라 조용히 열화되는 균형 상태 — lock time이 서서히 늘고, job이 느려지며, 알람은 울리지 않음
  • Postgres의 타임아웃 도구는 워크로드 클래스 구분이나 동시성 제한이 불가능함
  • 큐를 다른 워크로드와 같이 돌린다면, 가장 효과적인 조치는 VACUUM이 따라갈 수 있도록 보장하는 것이며, Traffic Control이 이를 단순화함

See also