-
컬렉션 조회 최적화(oneToMany)Working/jpa 성능 최적화 2021. 3. 2. 19:01
- v1 : Entity 직접 노출
Order -> List<OrderItem> -> item별 name (lazy loading 초기화)
- v2 : DTO로 변환 리턴
DTO 안에 Entity가 Wrapping 되어있다. OrderItem 도 DTO로 바꿔야 됨
결과 List 안에 또 List가 있으면 N^2으로 쿼리가 늘어남
컬렉션 경우에도 Fetch Join으로 최적화 가능
- v3 : Fetch Join
원하지 않게 join이 많이 됨
distinct o 추가로 사용하면 유니크하게 나옴
sql 쿼리는 1번만 요청한다.
단점 - 페이징 불가능
- v3.1 : 컬렉션을 페치조인 하면 페이징 불가
1:N 조인 -> 데이터가 N개가 된다, 데이터는 N을 기준으로 페이징이 됨 -> 1을 기준으로 하고싶다.
1. xToOne(OneToOne, ManyToOne) 관계를 모두 fetch join 한다(row수 증가 X)
2. 컬렉션은 지연 로딩
3. hibernate.default_batch_fetch_size, @BatchSize를 적용한다
-> sql문에서 in절을 사용해서 한번에 가져온다
-> 쿼리 호출 수가 1+N -> 1+1 로 최적화 된다.
xToOne 관계는 fetch join해도 페이징에 영향을 주지 않기때문에 사용해서 쿼리 수를 줄이고 hibernate.default_batch_fetch_size 사용!
100~1000(in절 size limit 1000), 500정도가 안전? 1000이하에서 순간 부하를 견딜수 있을 만큼
- v4 : 컬렉션 DTO
받을수 있는 부분만 받고 컬렉션은 바로 받을수 없기 때문에 결과를 한번 더 돌면서 조회
N + N 문제 발생
- v5: 두번째 컬렉션을 조회할 때 in절을 사용해서 N->1로 한번에 가져오게 바꾼다.
toOne 관계들을 먼저 조회하고, 여기서 얻은 id로 toMany관계를 in절을 사용해서 한번에 조회하자
Collectors.groupingBy로 받아서 채워주자
'Working > jpa 성능 최적화' 카테고리의 다른 글
지연 로딩과 조회 성능 최적화 (0) 2021.03.02 데이터 저장(Post) API(엔티티를 API 스펙에 노출하지 말자) (0) 2021.03.02