web-dev-qa-db-fra.com

Spécification Spring JPA avec tri

J'utilise Spring JPA.

Pour être plus précis, j'utilise un référentiel qui étend JpaRepository et JpaSpecificationExecutor car j'ai besoin de pagination, de filtrage et de tri.

Maintenant, j'ai la pagination et le filtrage qui fonctionnent très bien, mais je ne peux pas faire fonctionner le tri aussi.

Je constate avec une certaine déception que JpaSpecificationExecutor a des méthodes findAll():

findAll(Specification, Pageable);
findAll(Specification, Sort);

Mais celui dont j'ai besoin:

findAll(Specification, Pageable, Sort); //or something like this

n'existe pas!

Donc, plan B, incluez le tri dans la spécification.

Avec l'aide de la réponse acceptée à cette question: JpaSpecificationExecutor JOIN + ORDER BY dans les spécifications J'ai mis en place ce qui suit:

private Specification<MainEntity> matches() {
    return new Specification<MainEntity>() {

        public Predicate toPredicate(Root<MainEntity> root, CriteriaQuery<?> query, CriteriaBuilder cb) {

            List<Predicate> predicates = new ArrayList<Predicate>();

            //Attempt to sort by Surname, has no effect
            query.orderBy(cb.asc(root.get("surname")));

            //add string filters
            for (String field : stringFilterMap.keySet()) {
                String valuePattern = stringFilterMap.get(field);
                predicates.add(cb.like(root.get(field), "%"+valuePattern+"%"));
            }

            //...snip...

            return cb.and(predicates.toArray(new Predicate[predicates.size()]));
        }
    };      
}

springFilterMap est un champ d'instance, Map<String,String> dont les clés sont des noms de champs et des valeurs des valeurs de filtres.

Ci-dessus, vous verrez ma tentative de commande par nom de famille, mais cela semble n'avoir aucun effet.

Qu'est-ce que je fais mal; comment puis-je réaliser le tri avec la pagination et le filtrage?

13
NickJ

Utilisez PageRequest , qui est une implémentation de Pageable , et implémente la pagination et le tri à la fois, comme vous le souhaitez. Par exemple via ce constructeur :

public PageRequest(int page, int size, Sort sort)

MISE À JOUR: Depuis Spring Data JPA 2.0, le constructeur ci-dessus est obsolète et vous devez utiliser la méthode d'usine statique of :

public static PageRequest of(int page, int size, Sort sort)
22
Robert Niestroj