피드로 돌아가기
Dev.toDatabase
원문 읽기
N+1 Query 최적화로 인프라 확장 없이 DB 부하 및 응답 시간 대폭 개선
The N+1 Query That Killed Our Database, And How I Fixed It
AI 요약
Context
Django ORM 사용 중 Serializer 내 연관 데이터 접근으로 인한 N+1 Query 발생. 개발 환경의 소규모 데이터셋에서는 감지되지 않았으나, Production 환경의 데이터 증가에 따라 DB CPU 점유율 상승 및 API 응답 속도 저하 유발.
Technical Solution
- 단일 쿼리로 부모 레코드 조회 후 자식 레코드를 위해 N번 추가 쿼리가 발생하는 비효율적 패턴 식별
- ForeignKey 및 OneToOne 관계 해결을 위해 SQL JOIN을 수행하는 select_related() 도입을 통한 쿼리 횟수 최소화
- ManyToMany 및 역참조 관계 해결을 위해 별도 쿼리 후 Python 메모리에서 병합하는 prefetch_related() 적용
- IN 절을 활용한 Bulk Retrieval 방식으로 수백 개의 개별 쿼리를 단 2개의 최적화된 쿼리로 전환
- 단순 로직 구현을 넘어 Serializer의 데이터 접근 패턴이 생성하는 실제 SQL 쿼리 횟수를 분석하는 설계 방식 채택
실천 포인트
1. ORM 사용 시 Serializer 내에서 연관 필드 접근 시 발생하는 SQL 쿼리 횟수 확인
2. 1:1 또는 1:N 관계에서는 select_related()를 통한 SQL JOIN 적용 검토
3. M:N 또는 역참조 관계에서는 prefetch_related()를 통한 Bulk Fetching 적용 검토
4. Production 규모의 더미 데이터를 활용한 Load Test로 잠재적 N+1 문제 조기 발견