목록을 한 번 조회(1)한 뒤 각 행의 연관 엔티티를 따로 조회해서 쿼리가 N번 더 나가는 문제. 데이터가 적은 개발 환경에서는 잘 보이지 않는다. 원인은 대개 지연 로딩이다.
해법은 상황에 따라 고른다.
- fetch join: JPQL(Jakarta Persistence Query Language)
join fetch로 한 번에 가져온다(JPQL과 @Query). 컬렉션을 fetch join하면 페이징과 함께 쓰기 어렵다 @EntityGraph: 메서드마다 함께 가져올 연관을 선언한다- 배치 페치(batch fetching):
default_batch_fetch_size로 지연 로딩을IN (?, ?, …)묶음 조회로 바꾼다 - DTO(Data Transfer Object) 프로젝션(projection): 필요한 컬럼만 조회한다
sequenceDiagram
participant A as 애플리케이션
participant DB as DB
Note over A,DB: 지연 로딩 그대로 - 1 + N번
A->>DB: 목록 조회 1번
loop 행마다 N번
A->>DB: 연관 엔티티 조회
end
Note over A,DB: fetch join - 1번
A->>DB: join fetch로 목록과 연관을 함께 조회
무엇보다 SQL 로그를 켜 두고 쿼리 수를 눈으로 확인하는 습관이 먼저다.
출처: Hibernate ORM User Guide: Batch fetching · Entity graph · Best practices: Fetching