본문 바로가기
공부/Spring

스프링 데이터 JPA에서 페이징과 정렬을 해보자

by JERO__ 2022. 8. 25.

먼저, 순수 JPA에서의 페이징은 어떻게 할까?

예제로 알아보자. 검색조건은 다음과 같다

  • 검색조건: 나이가 10살
  • 정렬조건: 이름으로 내림차순
  • 페이징 조건: 첫 번째 페이지, 페이지당 데이터는 3건

 

스프링 데이터 JPA의 페이징과 정렬은 어떻게 할까?

1. 페이징과 정렬 파라미터

  • org.springframework.data.domain.Sort : 정렬 기능
  • org.springframework.data.domain.Pageable : 페이징 기능

2. 특별한 반환 타입

  • org.springframework.data.domain.Page : 추가 count 쿼리 결과를 포함하는 페이징
  • org.springframework.data.domain.Slice : 추가 count 쿼리 없이 다음 페이지만 확인 가능(내부적으로 limit + 1조회)
  • List (자바 컬렉션): 추가 count 쿼리 없이 결과만 반환

위 예시를 적용해보자. 반환타입을 필요에 따라 지정해줄 수 있다.

Page<Member> findByUsername(String name, Pageable pageable); //count 쿼리 사용
Slice<Member> findByUsername(String name, Pageable pageable); //count 쿼리 사용안함
List<Member> findByUsername(String name, Pageable pageable); //count 쿼리 사용안함
List<Member> findByUsername(String name, Sort sort);

위와 같은 예시를 적용해보자.

  • 검색조건: 나이가 10살
  • 정렬조건: 이름으로 내림차순
  • 페이징 조건: 첫 번째 페이지, 페이지당 데이터는 3건

Page 사용 예제 정의 코드

다음과 같이 쉽게 적용할 수 있다.

public interface MemberRepository extends Repository<Member, Long> {
	Page<Member> findByAge(int age, Pageable pageable);
}
  • getTotalPages : 전체 페이지 수
  • getTotalElements : 전체 데이터 수

Pageable

Pageable은 인터페이스이다. org.springframework.data.domain.PageRequest 객체를 사용한다. 또한 Page는 1부터 시작이 아닌 0부터 시작이다.

  • page: 0부터 시작
  • size: 한 페이지 당 개수
  • sort: 정렬기준
PageRequest pageRequest = PageRequest.of(0, 3, Sort.by(Sort.Direction.DESC,"username"));

count 쿼리를 분리할 수 있다!

Page를 사용하면 count가 자동으로 가져온다. 이 count를 가져올 때 쿼리를 분리해보자

@Query(value = “select m from Member m”,    // 기본 쿼리
countQuery = “select count(m.username) from Member m”) // count에 대한 쿼리
Page<Member> findMemberAllCountBy(Pageable pageable);
  • 전체 count 쿼리는 매우 무겁다

Page는 DTO로 변환해 반환하도록 하자.

도메인이 직접 노출되기 때문이다. Page<Member>

쉽게 변환하는 법은? map을 사용하자!

Page<Member> page = memberRepository.findByAge(age, pageRequest);
Page<MemberDto> toMap = page.map(member -> new MemberDto(member.getId(), member.getUsername()));
  • DTO로 변환된 Page는 API에서 반환해도 좋다!

 

 

 

 

댓글