JPA

[JPA] JPQL에서 limit절을 사용해보자

kkkkkkkkkkkk 2023. 1. 10. 18:07

들어가기전 상황은 이렇다.

예매한 영화의 정보 중에 제일 많이 예약을 한 영화를 카운트를 하고 내림차순으로 카운트를 기준으로 정렬 한 다음 첫 번째 행의 데이터를 가져오려는 상황이다.

 

즉, 예매를 가장 많이 한 영화를 가져오는 기능이다.

 

jpql로 limit query를 사용하여 query를 작성하였다.

하지만 컴파일 에러가 발생한다.

 

 

nativeQuery를 사용하면 limit 절이 제공이 되지만 jpql에서는 제공이 안된다.

구글링을 통해 jpql에서 limit 키워드를 지원하지 않는다고 한다. 대신에 JPA query method의 결과를 제한하는 기능이 있다.

 

아래 링크를 참조하겠습니다.

https://docs.spring.io/spring-data/jpa/docs/current/reference/html/#repositories.limit-query-result

 

Spring Data JPA - Reference Documentation

Example 119. Using @Transactional at query methods @Transactional(readOnly = true) interface UserRepository extends JpaRepository { List findByLastname(String lastname); @Modifying @Transactional @Query("delete from User u where u.active = false") void del

docs.spring.io

 

방법

  • findFristBy…..()
  • findTopBy……()
  • Page<?> findFirstBy….(Pageable pageable)
  • List<?> findFirstBy…..(Pageable pageable)

여러 가지 방법 중에 저는 Pageable을 인자로 넘겨주고 List 타입으로 받는 방법으로 문제를 해결했다.

Pageable 인자는 PageRequest.of()로 page를 0으로 size를 1로 넘겨준다.

이렇게 넘겨주면 첫번째 page에 size 하나로만 나오기에 위에서 원하던 상황을 해결할 수 있다.

 

public List<PopularMovieResponseDto> bestMovieFind() {
        return reservationRepository.findBestMovie(PageRequest.of(0, 1));
    }

 

@Query(value = "select new com.example.springbootmoviereservationsystem.controller.reservation.dto.PopularMovieResponseDto(r.screening.movie, count(r.screening.movie.title)) " +
            "from Reservation r " +
            "join r.screening " +
            "join r.screening.movie " +
            "group by r.screening.movie.title " +
            "order by count(r.screening.movie.title) desc")
    List<PopularMovieResponseDto> findBestMovie(Pageable pageable);