7

QueryDSL defines an OrderSpecifier interface and an instance for that can be easily obtained for any field by calling asc() or desc(). The QueryDslPredicateExecutor interface of Spring Data JPA even has a findAll() method which takes OrderSpecifiers as parameters.

org.springframework.data.domain.PageRequest however doesn't know anything about QueryDSL and it has its own way for defining query sort order, namely org.springframework.data.domain.Sort. It can contain a number of org.springframework.data.domain.Sort.Orders which are a lot like OrderSpecifiers, except that they are not type safe etc.

So, if I want to make paged query which uses sorting, is there really no way of using QueryDSL for defining that?

eh.
  • 287
  • 2
  • 9

4 Answers4

9

I know it's been a while and I'm not sure this was available at the time of the OP but there is now a QPageRequest object introduced which allows for sorting via QueryDSL to be added to spring data jpa Query DSL...

Michael Wiles
  • 20,902
  • 18
  • 71
  • 101
8

Here is a much simpler way to construct a Sort object using QueryDSL:

new QSort(user.manager.firstname.asc())

Then you can use it in a PageRequest like so:

new PageRequest(0, 10, new QSort(user.manager.firstname.asc()))
SergeyB
  • 9,478
  • 4
  • 33
  • 47
6

It should work like this if you can't find another way

private Sort sortBy(Path<?> path) {
    return new Sort(Sort.Direction.ASC, path.getMetadata().getExpression().toString());
}
Timo Westkämper
  • 21,824
  • 5
  • 78
  • 111
  • Thanks. A bit ugly, but much less so than using hard-coded expression names. Could you please add the missing parenthesis so that others can copy-paste you comment without modifying it. – eh. Aug 06 '12 at 08:59
  • `getExpression()` seems to have been removed and there seems to be no simple way of getting the whole expression name, only the last element's with `getName()`. – EpicPandaForce Jan 13 '15 at 13:58
  • The whole expression serialized is `path.toString()`, but it contains also the name of the root variable – Timo Westkämper Jan 14 '15 at 07:33
1

The getExpression() method has been removed, and I had expressions akin to QPost.post.period.periCode which needed a traversal, and without the complete name of expression I couldn't do anything about it, so now I made a method that gathers period.periCode and works perfectly on QPost.post.

private String resolveOrderPath(Path<?> path) {
    StringBuilder stringBuffer = new StringBuilder(path.getMetadata().getName());
    path = path.getMetadata().getParent();
    while(!path.getMetadata().isRoot()) {
        stringBuffer.insert(0, path.getMetadata().getName() + ".");
        path = path.getMetadata().getParent();
    }
    return stringBuffer.toString();
}

Path<?> path = QPost.post.period.periCode;
String propertyPath = resolveOrderPath(path);
Sort sort = new Sort("asc".equals(sSortDir0) ? Sort.Direction.ASC : Sort.Direction.DESC, propertyPath);
EpicPandaForce
  • 79,669
  • 27
  • 256
  • 428