Ограничаване на резултатите от заявките с JPA и Spring Data JPA

1. Въведение

В този урок ще научим за ограничаването на резултатите от заявките с JPA и Spring Data JPA.

Първо ще разгледаме таблицата, която искаме да направим, както и SQL заявката, която искаме да възпроизведем.

След това ще се потопим направо в това как да постигнем това с JPA и Spring Data JPA.

Да започваме!

2. Тестовите данни

По-долу имаме таблицата, която ще отправяме към цялата статия.

Въпросът, на който искаме да отговорим, е: „Кое е първото заето място и кой го заема?“.

Първо име Фамилия Номер на седалката
Джил Смит 50
Ева Джаксън 94
Фред Bloggs 22.
Рики Боби 36
Сия Колиси 85

3. SQL

С SQL можем да напишем заявка, която изглежда по следния начин:

SELECT firstName, lastName, seatNumber FROM passengers ORDER BY seatNumber LIMIT 1;

4. Настройка на JPA

С JPA първо се нуждаем от Entity, за да картографираме нашата таблица:

@Entity class Passenger { @Id @GeneratedValue @Column(nullable = false) private Long id; @Basic(optional = false) @Column(nullable = false) private String fistName; @Basic(optional = false) @Column(nullable = false) private String lastName; @Basic(optional = false) @Column(nullable = false) private int seatNumber; // constructor, getters etc. }

След това се нуждаем от метод, който капсулира нашия код на заявка, реализиран тук като PassengerRepositoryImpl # findOrderedBySeatNumberLimitedTo (int limit) :

@Repository class PassengerRepositoryImpl { @PersistenceContext private EntityManager entityManager; @Override public List findOrderedBySeatNumberLimitedTo(int limit) { return entityManager.createQuery("SELECT p FROM Passenger p ORDER BY p.seatNumber", Passenger.class).setMaxResults(limit).getResultList(); } }

В нашия метод на хранилище, ние използваме EntityManager, за да създадем заявка, по която извикваме метода setMaxResults () .

Това извикване на Query # setMaxResults в крайна сметка ще доведе до оператора за ограничение, приложен към генерирания SQL:

select passenger0_.id as id1_15_, passenger0_.fist_name as fist_nam2_15_, passenger0_.last_name as last_nam3_15_, passenger0_.seat_number as seat_num4_15_ from passenger passenger0_ order by passenger0_.seat_number limit ?

5. С Spring Data JPA

Също така можем да генерираме нашия SQL, използвайки Spring Data JPA.

5.1. първи или отгоре

Един от начините, по които бихме могли да подходим към това, е да използваме извеждането на име на метод с ключовите думи first или top.

По желание можем да посочим число като максимален размер на резултата, който ще бъде върнат. Ако го пропуснем, Spring Data JPA приема размер на резултата 1.

Като си спомним, че искаме да знаем кое е първото заето място и кой го заема, можем да го пропуснем по следните два начина:

Passenger findFirstByOrderBySeatNumberAsc(); Passenger findTopByOrderBySeatNumberAsc();

Ако ограничим до един резултат от екземпляра, както по-горе, тогава можем също да обгърнем резултата, като използваме Незадължително :

Optional findFirstByOrderBySeatNumberAsc(); Optional findTopByOrderBySeatNumberAsc();

5.2. Страничен

Като алтернатива можем да използваме Pageable обект:

Page page = repository.findAll( PageRequest.of(0, 1, Sort.by(Sort.Direction.ASC, "seatNumber")));

Ако можем да погледнем в стандартното внедряване на JpaRepository, на SimpleJpaRepository, можем да видим, че тя също така призовава за заявки # setMaxResults :

protected  Page  readPage(TypedQuery  query, Class  domainClass, Pageable pageable, @Nullable Specification  spec) { if (pageable.isPaged()) { query.setFirstResult((int) pageable.getOffset()); query.setMaxResults(pageable.getPageSize()); } return PageableExecutionUtils.getPage(query.getResultList(), pageable, () -> { return executeCountQuery(this.getCountQuery(spec, domainClass)); }); }

5.3. Сравнение

И двете алтернативи ще създадат SQL, който търсим:

select passenger0_.id as id1_15_, passenger0_.fist_name as fist_nam2_15_, passenger0_.last_name as last_nam3_15_, passenger0_.seat_number as seat_num4_15_ from passenger passenger0_ order by passenger0_.seat_number asc limit ?

С първо и най- предпочитано споразумение и Pageable предпочитано конфигуриране.

6. Заключение

Ограничаването на резултатите от заявката в JPA е малко по-различно от SQL - ние не включваме ключовата дума limit директно в нашия JPQL.

Вместо това просто правим едно извикване на метод на Query # maxResults или включваме ключовата дума first или top в името на метода ни Spring Spring JPA.

Както винаги, можете да намерите кода на GitHub.