HHH-16848 add SelectionQuery.ascending(int) & descending(int)
This commit is contained in:
parent
23df9eb785
commit
bec6cfab12
|
@ -1074,6 +1074,16 @@ public class ProcedureCallImpl<R>
|
|||
throw new UnsupportedOperationException( "Not supported for procedure calls" );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> ascending(int element) {
|
||||
throw new UnsupportedOperationException( "Not supported for procedure calls" );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> descending(int element) {
|
||||
throw new UnsupportedOperationException( "Not supported for procedure calls" );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> unordered() {
|
||||
return this;
|
||||
|
|
|
@ -905,6 +905,12 @@ public interface Query<R> extends SelectionQuery<R>, MutationQuery, TypedQuery<R
|
|||
@Override
|
||||
Query<R> descending(SingularAttribute<? super R, ?> attribute);
|
||||
|
||||
@Override
|
||||
Query<R> ascending(int element);
|
||||
|
||||
@Override
|
||||
Query<R> descending(int element);
|
||||
|
||||
@Override
|
||||
Query<R> unordered();
|
||||
|
||||
|
|
|
@ -493,6 +493,28 @@ public interface SelectionQuery<R> extends CommonQueryContract {
|
|||
@Incubating
|
||||
SelectionQuery<R> descending(SingularAttribute<? super R, ?> attribute);
|
||||
|
||||
/**
|
||||
* Add an element of the select list to be used to order the query results
|
||||
* in ascending order.
|
||||
*
|
||||
* @param element an integer identifying an element of the select list
|
||||
*
|
||||
* @since 6.3
|
||||
*/
|
||||
@Incubating
|
||||
SelectionQuery<R> ascending(int element);
|
||||
|
||||
/**
|
||||
* Add an element of the select list to be used to order the query results
|
||||
* in descending order.
|
||||
*
|
||||
* @param element an integer identifying an element of the select list
|
||||
*
|
||||
* @since 6.3
|
||||
*/
|
||||
@Incubating
|
||||
SelectionQuery<R> descending(int element);
|
||||
|
||||
/**
|
||||
* Clear the ordering conditions for this query.
|
||||
*
|
||||
|
|
|
@ -136,8 +136,22 @@ public interface SqmQueryImplementor<R> extends QueryImplementor<R>, SqmQuery, N
|
|||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
default SqmQueryImplementor<R> ascending(int element) {
|
||||
addOrdering( element, SortOrder.ASCENDING );
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
default SqmQueryImplementor<R> descending(int element) {
|
||||
addOrdering( element, SortOrder.DESCENDING );
|
||||
return this;
|
||||
}
|
||||
|
||||
SqmQueryImplementor<R> addOrdering(SingularAttribute<? super R, ?> attribute, SortOrder order);
|
||||
|
||||
SqmQueryImplementor<R> addOrdering(int element, SortOrder order);
|
||||
|
||||
@Override
|
||||
SqmQueryImplementor<R> unordered();
|
||||
|
||||
|
|
|
@ -39,7 +39,6 @@ import org.hibernate.query.IllegalQueryOperationException;
|
|||
import org.hibernate.query.Query;
|
||||
import org.hibernate.query.QueryParameter;
|
||||
import org.hibernate.query.ResultListTransformer;
|
||||
import org.hibernate.query.SelectionQuery;
|
||||
import org.hibernate.query.TupleTransformer;
|
||||
import org.hibernate.query.named.NamedQueryMemento;
|
||||
|
||||
|
@ -288,6 +287,16 @@ public abstract class AbstractQuery<R>
|
|||
throw new UnsupportedOperationException( "Should be implemented by " + this.getClass().getName() );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> ascending(int element) {
|
||||
throw new UnsupportedOperationException( "Should be implemented by " + this.getClass().getName() );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> descending(int element) {
|
||||
throw new UnsupportedOperationException( "Should be implemented by " + this.getClass().getName() );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> unordered() {
|
||||
throw new UnsupportedOperationException( "Should be implemented by " + this.getClass().getName() );
|
||||
|
|
|
@ -1510,6 +1510,16 @@ public class NativeQueryImpl<R>
|
|||
throw new UnsupportedOperationException("Not yet supported for native queries");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> ascending(int element) {
|
||||
throw new UnsupportedOperationException("Not yet supported for native queries");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> descending(int element) {
|
||||
throw new UnsupportedOperationException("Not yet supported for native queries");
|
||||
}
|
||||
|
||||
@Override
|
||||
public Query<R> unordered() {
|
||||
return this;
|
||||
|
|
|
@ -88,6 +88,7 @@ import org.hibernate.query.sqm.tree.SqmTypedNode;
|
|||
import org.hibernate.query.sqm.tree.delete.SqmDeleteStatement;
|
||||
import org.hibernate.query.sqm.tree.domain.SqmPath;
|
||||
import org.hibernate.query.sqm.tree.expression.JpaCriteriaParameter;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmAliasedNodeRef;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmExpression;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmJpaCriteriaParameterWrapper;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmParameter;
|
||||
|
@ -99,6 +100,7 @@ import org.hibernate.query.sqm.tree.insert.SqmValues;
|
|||
import org.hibernate.query.sqm.tree.select.SqmQueryPart;
|
||||
import org.hibernate.query.sqm.tree.select.SqmSelectStatement;
|
||||
import org.hibernate.query.sqm.tree.select.SqmSelectableNode;
|
||||
import org.hibernate.query.sqm.tree.select.SqmSortSpecification;
|
||||
import org.hibernate.query.sqm.tree.update.SqmAssignment;
|
||||
import org.hibernate.query.sqm.tree.update.SqmUpdateStatement;
|
||||
import org.hibernate.sql.results.internal.TupleMetadata;
|
||||
|
@ -982,6 +984,36 @@ public class QuerySqmImpl<R>
|
|||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmQueryImplementor<R> addOrdering(int element, SortOrder order) {
|
||||
if ( sqm instanceof SqmSelectStatement ) {
|
||||
sqm = sqm.copy( SqmCopyContext.noParamCopyContext() );
|
||||
SqmSelectStatement<R> select = (SqmSelectStatement<R>) sqm;
|
||||
int size = select.getSelection().getSelectionItems().size();
|
||||
if ( element < 1) {
|
||||
throw new IllegalArgumentException("Cannot order by element " + element + " (the first select item is element 1)");
|
||||
}
|
||||
if ( element > size) {
|
||||
throw new IllegalArgumentException("Cannot order by element " + element + " (there are " + size + " select items)");
|
||||
}
|
||||
NodeBuilder nodeBuilder = sqm.nodeBuilder();
|
||||
List<Order> orders = new ArrayList<>( select.getOrderList() );
|
||||
orders.add( new SqmSortSpecification(
|
||||
new SqmAliasedNodeRef(
|
||||
element,
|
||||
nodeBuilder.getTypeConfiguration().standardBasicTypeForJavaType( Integer.class ),
|
||||
nodeBuilder
|
||||
),
|
||||
order
|
||||
) );
|
||||
select.orderBy( orders );
|
||||
return this;
|
||||
}
|
||||
else {
|
||||
throw new IllegalStateException( "Not a select query" );
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmQueryImplementor<R> unordered() {
|
||||
if ( sqm instanceof SqmSelectStatement ) {
|
||||
|
|
|
@ -61,11 +61,13 @@ import org.hibernate.query.sqm.internal.SqmInterpretationsKey.InterpretationsKey
|
|||
import org.hibernate.query.sqm.tree.SqmCopyContext;
|
||||
import org.hibernate.query.sqm.tree.domain.SqmPath;
|
||||
import org.hibernate.query.sqm.tree.expression.JpaCriteriaParameter;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmAliasedNodeRef;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmJpaCriteriaParameterWrapper;
|
||||
import org.hibernate.query.sqm.tree.expression.SqmParameter;
|
||||
import org.hibernate.query.sqm.tree.from.SqmRoot;
|
||||
import org.hibernate.query.sqm.tree.select.SqmSelectStatement;
|
||||
import org.hibernate.query.sqm.tree.select.SqmSelection;
|
||||
import org.hibernate.query.sqm.tree.select.SqmSortSpecification;
|
||||
import org.hibernate.sql.results.internal.TupleMetadata;
|
||||
import org.hibernate.type.descriptor.java.JavaType;
|
||||
|
||||
|
@ -567,6 +569,18 @@ public class SqmSelectionQueryImpl<R> extends AbstractSelectionQuery<R>
|
|||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmSelectionQuery<R> ascending(int element) {
|
||||
addOrdering( element, SortOrder.ASCENDING );
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmSelectionQuery<R> descending(int element) {
|
||||
addOrdering( element, SortOrder.DESCENDING );
|
||||
return this;
|
||||
}
|
||||
|
||||
private void addOrdering(SingularAttribute<? super R, ?> attribute, SortOrder order) {
|
||||
sqm = sqm.copy( SqmCopyContext.noParamCopyContext() );
|
||||
NodeBuilder nodeBuilder = sqm.nodeBuilder();
|
||||
|
@ -581,6 +595,28 @@ public class SqmSelectionQueryImpl<R> extends AbstractSelectionQuery<R>
|
|||
sqm.orderBy( orders );
|
||||
}
|
||||
|
||||
private void addOrdering(int element, SortOrder order) {
|
||||
sqm = sqm.copy( SqmCopyContext.noParamCopyContext() );
|
||||
int size = sqm.getSelection().getSelectionItems().size();
|
||||
if ( element < 1) {
|
||||
throw new IllegalArgumentException("Cannot order by element " + element + " (the first select item is element 1)");
|
||||
}
|
||||
if ( element > size) {
|
||||
throw new IllegalArgumentException("Cannot order by element " + element + " (there are " + size + " select items)");
|
||||
}
|
||||
NodeBuilder nodeBuilder = sqm.nodeBuilder();
|
||||
List<Order> orders = new ArrayList<>( sqm.getOrderList() );
|
||||
orders.add( new SqmSortSpecification(
|
||||
new SqmAliasedNodeRef(
|
||||
element,
|
||||
nodeBuilder.getTypeConfiguration().standardBasicTypeForJavaType( Integer.class ),
|
||||
nodeBuilder
|
||||
),
|
||||
order
|
||||
) );
|
||||
sqm.orderBy( orders );
|
||||
}
|
||||
|
||||
@Override
|
||||
public SqmSelectionQuery<R> unordered() {
|
||||
sqm = sqm.copy( SqmCopyContext.noParamCopyContext() );
|
||||
|
|
|
@ -210,6 +210,47 @@ public class OrderTest {
|
|||
});
|
||||
}
|
||||
|
||||
@Test void testAscendingDescendingBySelectElement(SessionFactoryScope scope) {
|
||||
scope.inTransaction( session -> session.createMutationQuery("delete Book").executeUpdate() );
|
||||
scope.inTransaction( session -> {
|
||||
session.persist(new Book("9781932394153", "Hibernate in Action"));
|
||||
session.persist(new Book("9781617290459", "Java Persistence with Hibernate"));
|
||||
});
|
||||
scope.inSession(session -> {
|
||||
List<?> titlesAsc = session.createSelectionQuery("select isbn, title from Book", Object[].class)
|
||||
.ascending(2)
|
||||
.getResultList()
|
||||
.stream().map(book -> book[1])
|
||||
.collect(toList());
|
||||
assertEquals("Hibernate in Action", titlesAsc.get(0));
|
||||
assertEquals("Java Persistence with Hibernate", titlesAsc.get(1));
|
||||
|
||||
List<?> titlesDesc = session.createSelectionQuery("select isbn, title from Book", Object[].class)
|
||||
.descending(2)
|
||||
.getResultList()
|
||||
.stream().map(book -> book[1])
|
||||
.collect(toList());
|
||||
assertEquals("Hibernate in Action", titlesDesc.get(1));
|
||||
assertEquals("Java Persistence with Hibernate", titlesDesc.get(0));
|
||||
|
||||
List<?> isbnAsc = session.createSelectionQuery("select isbn, title from Book", Object[].class)
|
||||
.ascending(1).descending(2)
|
||||
.getResultList()
|
||||
.stream().map(book -> book[1])
|
||||
.collect(toList());
|
||||
assertEquals("Hibernate in Action", isbnAsc.get(1));
|
||||
assertEquals("Java Persistence with Hibernate", isbnAsc.get(0));
|
||||
|
||||
List<?> isbnDesc = session.createSelectionQuery("select isbn, title from Book", Object[].class)
|
||||
.descending(1).descending(2)
|
||||
.getResultList()
|
||||
.stream().map(book -> book[1])
|
||||
.collect(toList());
|
||||
assertEquals("Hibernate in Action", isbnDesc.get(0));
|
||||
assertEquals("Java Persistence with Hibernate", isbnDesc.get(1));
|
||||
});
|
||||
}
|
||||
|
||||
@Entity(name="Book")
|
||||
static class Book {
|
||||
@Id String isbn;
|
||||
|
|
Loading…
Reference in New Issue