Порядок сортировки в поиске

Я использую этот код для получения строк БД с помощью JPA и Spring:

return transactionService.findAll(page, size)


        public Page<PaymentTransactions> findAll(int page, int size) {
        return dao.findAll(PageRequest.of(page,size, new Sort(Sort.Direction.DESC, "createdAt")));
        }

Я хотел бы реализовать такую ​​же сортировку для этого кода:

return transactionService.getAllBySpecification(specification, pageable)

      @Override
      public Page<PaymentTransactions> getAllBySpecification(final Specification<PaymentTransactions> specification, final Pageable pageable) {
          return dao.findAll(specification, pageable);
      }

Знаете ли вы, как я могу реализовать направление сортировки по столбцу, используя спецификацию. Что-то вроде этого:

return dao.findAll(specification, PageRequest.of(page,size, new Sort(Sort.Direction.DESC, "createdAt")));

Дополнительный вопрос:

Могу ли я установить объект Pagable с направлением сортировки? Что-то вроде этого:

      @Override
      public Page<PaymentTransactions> getAllBySpecification(final Specification<PaymentTransactions> specification, final Pageable pageable) {
          return dao.findAll(specification, PageRequest.of(pageable, new Sort(Sort.Direction.DESC, "createdAt")));
      }

Какая именно проблема? Является ли класс dao производным от CrudRepository или это ваш собственный класс?

Nikolai Shevchenko 16.05.2019 18:14

Dao — репозиторий: public interface PaymentTransactionRepository extends JpaRepository<PaymentTransactions, Integer>, JpaSpecificationExecutor<PaymentTransactions> Не могу найти как реализовать findAll со спецификацией, пейджингом и направлением сортировки.

Peter Penzov 16.05.2019 18:17

Я что-то пропустил? Вам не нужно реализовывать его, если JpaSpecificationExecutor уже предоставляет Page<T> findAll(Specification<T> spec, Pageable pageable); метод. Настройки сортировки упакованы внутри вашего PageRequest

Nikolai Shevchenko 16.05.2019 18:22

хм.... не могли бы вы показать мне пример кода, пожалуйста?

Peter Penzov 16.05.2019 18:26

А в моем случае хочу поставить int page, int size

Peter Penzov 16.05.2019 18:26

Не могу, потому что не понимаю, в чем проблема. Обновите свой пост с помощью минимальный воспроизводимый пример

Nikolai Shevchenko 16.05.2019 18:28
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
Как вычислять биты и понимать побитовые операторы в Java - объяснение с примерами
В компьютерном программировании биты играют важнейшую роль в представлении и манипулировании данными на двоичном уровне. Побитовые операции...
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Поднятие тревоги для долго выполняющихся методов в Spring Boot
Приходилось ли вам сталкиваться с требованиями, в которых вас могли попросить поднять тревогу или выдать ошибку, когда метод Java занимает больше...
Полный курс Java для разработчиков веб-сайтов и приложений
Полный курс Java для разработчиков веб-сайтов и приложений
Получите сертификат Java Web и Application Developer, используя наш курс.
4
6
298
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Ответ принят как подходящий

Вам не нужно ничего, кроме JpaSpecificationExecutor. Spring будет использовать этот интерфейс для автоматического создания:

Page<T> findAll(@Nullable Specification<T> spec, Pageable pageable)

метод, который вы, кажется, ищете. Так вот, непонятно в чем проблема, может не те классы импортируете? Или, если вы просто хотите сгенерировать PageRequest для getAllBySpecification, используя page и size, вы можете сделать что-то вроде этого:

    public Page<Entity> getAllBySpecification(
            Specification<Entity> specification, 
            int page, int size) {

        return dao.findAll(specification, createMyPageRequest(page, size));
    }

    private PageRequest createMyPageRequest(int page, int size) {
        return PageRequest.of(page, size, new Sort(Sort.Direction.DESC, "createdAt"));
    }

В любом случае, если вам нужен полный пример компиляции этих API...

can you show me some code example please?

... вот:

import org.springframework.data.domain.*;
import org.springframework.data.jpa.domain.Specification;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;

public class SortFunctionality {
    private Dao dao;

    public Page<Entity> findAll(int page, int size) {
        return dao.findAll(createMyPageRequest(page, size));
    }

    public Page<Entity> getAllBySpecification(
            Specification<Entity> specification, 
            int page, int size) {

        return dao.findAll(specification, createMyPageRequest(page, size));
    }

    public Page<Entity> getAllBySpecification(
            Specification<Entity> specification, 
            Pageable pageable) {

        PageRequest pageRequest = createMyPageRequest(
                pageable.getPageNumber(), 
                pageable.getPageSize());

        return dao.findAll(specification, pageRequest);
    }   

    private PageRequest createMyPageRequest(int page, int size) {
        return PageRequest.of(page, size, new Sort(Sort.Direction.DESC, "createdAt"));
    }

    static interface Dao extends 
        JpaRepository<Entity, Integer>, JpaSpecificationExecutor<Entity> {}

    static class Entity {}
}

Редактирование дополнительного вопроса:

Да, вы можете добиться этого, извлекая pageNumber и pageSize из аргумента Pageable и используя их для создания собственного PageRequest (PageRequest с жестко заданными критериями сортировки) с помощью утилиты createMyPageRequest, которую я включил в демонстрационный код. Наконец, вы можете использовать этот PageRequest для вызова метода findAll как обычно:

    public Page<Entity> getAllBySpecification(
            Specification<Entity> specification, 
            Pageable pageable) {

        PageRequest pageRequest = createMyPageRequest(
                pageable.getPageNumber(), 
                pageable.getPageSize());

        return dao.findAll(specification, pageRequest);
    }   

Я обновил предыдущую полную демонстрацию, чтобы отразить и это новое дополнение. Кроме того, он немного переработан, поэтому, если вы вставите этот новый метод поверх копии предыдущей версии демо, в нем будут ошибки.

Полный код на GitHub

Надеюсь это поможет.

Спасибо. У меня есть один дополнительный вопрос. Пожалуйста, смотрите обновленный пост.

Peter Penzov 19.05.2019 22:16

Я только что обновил ответ, чтобы рассмотреть дополнительный вопрос. Рад помочь.

Marco R. 19.05.2019 23:17

Вы можете использовать только соглашение об именах и позволить Spring сгенерировать реализацию за вас. Вы должны использовать репозитории данных Spring JPA. Вы можете следовать приведенным примерам и соответствующим образом реорганизовать свою логику.

https://docs.spring.io/spring-data/jpa/docs/current/reference/html/#repositories.special-parameters

Это также берущий параметр Pageable. Пожалуйста, посмотрите на примеры:

List<Person> findByLastnameOrderByFirstnameDesc(String lastname);

И этот:

Page<User> findByLastname(String lastname, Pageable pageable);

Pageable и Slice описаны в 4.4.4 Обработка специальных параметров.

Другие вопросы по теме