[JPA2] API개발과 고급- DTO 직접조회-컬렉션 조회 최적화(5)

레몬커드요거트·2022년 11월 10일
0

V5. 컬렉션 조회에서 최적화

public List<OrderQueryDto> findAllByDto_optimization(){
  List<OrderQueryDto> result = findOrders();

  List<Long> orderIds =result.stream()
    .map(o -> o.getOrderId())
    .collect(Collectors.toList());
 //루트 조회(toOne 코드를 모두 한번에 조회)
  List<OrderItemQueryDto> orderItems = em.createQuery(
    "select new jpabook.jpashop.repository.order.query.OrderItemQueryDto(oi.order.id, i.name, oi.orderPrice, oi.count) " +
    "from OrderItem oi" +
    "join oi.item i " +
    "where oi.order.id in :orderIds", OrderItemQueryDto.class)
    .setParameter("orderIds", orderIds)
    .getResultList();
  
  //orderItem 컬렉션을 MAP 한방에 조회
  Map<Long, List<OrderItemQueryDto>> orderItemMap = orderItems.stream()
    .collect(Collectors.groupingBy(orderItemQueryDto -> orderItemQueryDto.getOrderId()));
  
//루프를 돌면서 컬렉션 추가(추가 쿼리 실행X)
  result.forEach(o->o.setOrderItems(orderItemMap.get(o.getOrderId())));

  return result;

}

쿼리를 한 번 날린 후, 메모리에서 map하여 가져온 후 매칭
쿼리가 2번 생성이 된다

 -- 루트 조회(toOne 코드를 모두 한번에 조회)
    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
 -- orderItem 컬렉션을 MAP 한방에 조회
    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 
    where
        orderitem0_.order_id in (
            ? , ?
        )
profile
비요뜨 최고~

0개의 댓글