DTO 직접 조회: 컬렉션 조회 최적화
이전에 발생한 N+1 문제를 해결해보자.
in 절
@RestController
@RequiredArgsConstructor
public class OrderApiController {
private final OrderRepository orderRepository;
private final OrderQueryRepository orderQueryRepository;
@GetMapping("/api/v5/orders")
public List<OrderQueryDto> ordersV5() {
return orderQueryRepository.findAllByDto_optimization();
}
}
select order0_.order_id as col_0_0_,
member1_.name as col_1_0_,
order0_.order_date as col_2_0_,
order0_.status as col_3_0_,
delivery2_.city as col_4_0_,
delivery2_.street as col_4_1_,
delivery2_.zipcode as col_4_2_
from orders order0_
inner join
member member1_ on order0_.member_id = member1_.member_id
inner join
delivery delivery2_ on order0_.delivery_id = delivery2_.delivery_id
select orderitem0_.order_id as col_0_0_,
item1_.name as col_1_0_,
orderitem0_.order_price as col_2_0_,
orderitem0_.count as col_3_0_
from order_item orderitem0_
inner join
item item1_ on orderitem0_.item_id = item1_.item_id
-- in 절로 한 번에 가져온다.
where orderitem0_.order_id in (
?, ?
)
in절로 여러 orderId에 대한 쿼리를 한 번에 날린 뒤, 메모리 상에서 값을 매칭해 가져온다.
map을 사용해 매칭했기 때문에 성능이 O(1)로 향상되었다.
쿼리는 총 2번 나간다.
루트 쿼리 뒤에 orderItem을 가져오는 쿼리가 한 번만 실행된다.
ToOne 관계를 먼저 조회하고 여기서 얻은 식별자 orderId로 ToMany 관계인 OrderItem을 한 번에 조회한다.
Last updated
Was this helpful?