QueryDSL 아이템 목록 페이징 처리
2024. 10. 31. 14:35ㆍJava
private Predicate getHavingCondition(Long lastIdx, Long lastItemId, ItemSortType itemSortType) {
return switch (itemSortType) {
case NEW -> item.id.lt(lastIdx);
case HIGHEST_AMOUNT -> item.price.lt(lastIdx)
.or(item.price.eq(lastIdx.intValue()).and(item.id.gt(lastItemId)));
case LOWEST_AMOUNT -> item.price.gt(lastIdx)
.or(item.price.eq(lastIdx.intValue()).and(item.id.gt(lastItemId)));
case DISCOUNT -> item.discount.lt(lastIdx)
.or(item.discount.eq(lastIdx.intValue()).and(item.id.gt(lastItemId)));
default -> JPAExpressions.select(orderItem.quantity.longValue().sum().coalesce(0L))
.from(orderItem)
.where(orderItem.item.eq(item))
.lt(lastIdx);
};
}
- NEW(최신순):
case NEW -> ite[http://m.id.lt(lastIdx);](http://m.id.lt\(lastIdx\);)
마지막으로 본 아이템의 ID보다 작은 ID를 가진 아이템들을 조회
- HIGHEST_AMOUNT (가격 높은순):
case HIGHEST_AMOUNT -> item.price.lt(lastIdx)
.or(item.price.eq(lastIdx.intValue())
.and(item.id.gt(lastItemId)));
마지막 아이템의 가격보다 작은 가격의 아이템들
또는 같은 가격일 경우 ID가 더 큰 아이템들을 조회
LOWEST_AMOUNT (가격 낮은순):
case LOWEST_AMOUNT -> item.price.gt(lastIdx) .or(item.price.eq(lastIdx.intValue()) .and(item.id.gt(lastItemId))); 마지막 아이템의 가격보다 큰 가격의 아이템들 또는 같은 가격일 경우 ID가 더 큰 아이템들을 조회
DISCOUNT (할인율순):
case DISCOUNT -> item.discount.lt(lastIdx) .or(item.discount.eq(lastIdx.intValue()) .and(item.id.gt(lastItemId))); 마지막 아이템의 할인율보다 작은 할인율의 아이템들 또는 같은 할인율일 경우 ID가 더 큰 아이템들을 조회
기본(인기순):
default -> JPAExpressions.select(orderItem.quantity.longValue().sum().coalesce(0L)) .from(orderItem) .where(orderItem.item.eq(item)) .lt(lastIdx); 주문수량의 합계가 마지막 아이템의 주문수량보다 작은 아이템들을 조회
이 구현의 장점:
- 커서 기반 페이징:
- 오프셋 기반보다 성능이 좋음
- 데이터 일관성 보장
- 다양한 정렬 지원
- 최신순
- 가격순 (높은순/낮은순)
- 할인율순
- 인기순(주문수량 기준)
- 동일 값 처리
- 같은 값일 경우 ID로 추가 정렬하여 일관성 보장
- Null 처리
- coalesce(0L)를 사용하여 Null 값을 안전하게 처리
'Java' 카테고리의 다른 글
JWT 그런데 OAuth2.0 곁들인 (2) (1) | 2024.11.10 |
---|---|
JWT 그런데 OAuth2.0 곁들인 (1) | 2024.11.08 |
SSE(Server-Sent Events) (0) | 2024.11.06 |
정적 팩토리 메서드 네이밍의 차이 (of vs from) (0) | 2024.11.04 |
StringUtils 라이브러리 (0) | 2024.10.29 |