diff --git a/api/src/main/java/jakarta/persistence/criteria/CriteriaBuilder.java b/api/src/main/java/jakarta/persistence/criteria/CriteriaBuilder.java index 9c5d009f..70c9d2a1 100644 --- a/api/src/main/java/jakarta/persistence/criteria/CriteriaBuilder.java +++ b/api/src/main/java/jakarta/persistence/criteria/CriteriaBuilder.java @@ -117,19 +117,37 @@ public interface CriteriaBuilder { /** * Create an ordering by the ascending value of the expression. - * @param x expression used to define the ordering + * @param expression expression used to define the ordering * @return ascending ordering corresponding to the expression */ - Order asc(Expression x); + Order asc(Expression expression); /** * Create an ordering by the descending value of the expression. - * @param x expression used to define the ordering + * @param expression expression used to define the ordering * @return descending ordering corresponding to the expression */ - Order desc(Expression x); + Order desc(Expression expression); + + /** + * Create an ordering by the ascending value of the expression. + * @param expression expression used to define the ordering + * @param nullPrecedence the precedence of null values + * @return ascending ordering corresponding to the expression + * @since 3.2 + */ + Order asc(Expression expression, Nulls nullPrecedence); + + /** + * Create an ordering by the descending value of the expression. + * @param expression expression used to define the ordering + * @param nullPrecedence the precedence of null values + * @return descending ordering corresponding to the expression + * @since 3.2 + */ + Order desc(Expression expression, Nulls nullPrecedence); + - //aggregate functions: /** diff --git a/api/src/main/java/jakarta/persistence/criteria/Nulls.java b/api/src/main/java/jakarta/persistence/criteria/Nulls.java new file mode 100644 index 00000000..d0198659 --- /dev/null +++ b/api/src/main/java/jakarta/persistence/criteria/Nulls.java @@ -0,0 +1,39 @@ +/* + * Copyright (c) 2008, 2020 Oracle and/or its affiliates. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v. 2.0 which is available at + * http://www.eclipse.org/legal/epl-2.0, + * or the Eclipse Distribution License v. 1.0 which is available at + * http://www.eclipse.org/org/documents/edl-v10.php. + * + * SPDX-License-Identifier: EPL-2.0 OR BSD-3-Clause + */ + +// Contributors: +// Gavin King - 3.2 + +package jakarta.persistence.criteria; + +/** + * Specifies the precedence of null values within query result sets. + * + * @see CriteriaBuilder#asc(Expression, Nulls) + * @see CriteriaBuilder#desc(Expression, Nulls) + * + * @since 3.2 + */ +public enum Nulls { + /** + * Null precedence not specified. + */ + NONE, + /** + * Null values occur at the beginning of the result set. + */ + FIRST, + /** + * Null values occur at the end of the result set. + */ + LAST +} \ No newline at end of file diff --git a/api/src/main/java/jakarta/persistence/criteria/Order.java b/api/src/main/java/jakarta/persistence/criteria/Order.java index d3ea653c..39b5b998 100644 --- a/api/src/main/java/jakarta/persistence/criteria/Order.java +++ b/api/src/main/java/jakarta/persistence/criteria/Order.java @@ -35,6 +35,13 @@ public interface Order { */ boolean isAscending(); + /** + * Return the precedence of null values. + * @return the {@linkplain Nulls precedence of null values} + * @since 3.2 + */ + Nulls getNullPrecedence(); + /** * Return the expression that is used for ordering. * @return expression used for ordering diff --git a/spec/src/main/asciidoc/appendixes.adoc b/spec/src/main/asciidoc/appendixes.adoc index 496ab4a6..ab491956 100644 --- a/spec/src/main/asciidoc/appendixes.adoc +++ b/spec/src/main/asciidoc/appendixes.adoc @@ -108,6 +108,8 @@ Added support for Java record types as embeddable classes Added `||` string concatenation operator +Added support for specifying null precedence when ordering JPQL and criteria queries + Added _getSingleResultOrNull()_ to _Query_, _TypedQuery_, _StoredProcedureQuery_ Overload _concat()_ to accept list of expressions in _CriteriaBuilder_ diff --git a/spec/src/main/asciidoc/ch04-query-language.adoc b/spec/src/main/asciidoc/ch04-query-language.adoc index b95def71..19af1a5d 100644 --- a/spec/src/main/asciidoc/ch04-query-language.adoc +++ b/spec/src/main/asciidoc/ch04-query-language.adoc @@ -320,10 +320,10 @@ future use.] are reserved identifiers: ABS, ALL, AND, ANY, AS, ASC, AVG, BETWEEN, BIT_LENGTH, BOTH, BY, CASE, CEILING, CHAR_LENGTH, CHARACTER_LENGTH, CLASS, COALESCE, CONCAT, COUNT, CURRENT_DATE, CURRENT_TIME, CURRENT_TIMESTAMP, DELETE, DESC, DISTINCT, ELSE, EMPTY, -END, ENTRY, ESCAPE, EXISTS, EXP, EXTRACT, FALSE, FETCH, FLOOR, FROM, -FUNCTION, GROUP, HAVING, IN, INDEX, INNER, IS, JOIN, KEY, LEADING, -LEFT, LENGTH, LIKE, LOCAL, LN, LOCATE, LOWER, MAX, MEMBER, MIN, MOD, -NEW, NOT, NULL, NULLIF, OBJECT, OF, ON, OR, ORDER, OUTER, POSITION, +END, ENTRY, ESCAPE, EXISTS, EXP, EXTRACT, FALSE, FETCH, FIRST, FLOOR, +FROM, FUNCTION, GROUP, HAVING, IN, INDEX, INNER, IS, JOIN, KEY, LEADING, +LAST, LEFT, LENGTH, LIKE, LOCAL, LN, LOCATE, LOWER, MAX, MEMBER, MIN, MOD, +NEW, NOT, NULL, NULLS, NULLIF, OBJECT, OF, ON, OR, ORDER, OUTER, POSITION, POWER, ROUND, SELECT, SET, SIGN, SIZE, SOME, SQRT, SUBSTRING, SUM, THEN, TRAILING, TREAT, TRIM, TRUE, TYPE, UNKNOWN, UPDATE, UPPER, VALUE, WHEN, WHERE. @@ -2510,6 +2510,7 @@ orderby_clause ::= ORDER BY orderby_item {, orderby_item}* orderby_item ::= {state_field_path_expression | general_identification_variable | result_variable} [ASC | DESC] + [NULLS {FIRST | LAST}] ---- An orderby_item must be one of the following: @@ -2586,7 +2587,9 @@ ordering be used for the associated _orderby_item_; the keyword DESC specifies that descending ordering be used. Ascending ordering is the default. -SQL rules for the ordering of null values +The keyword NULLS specifies the ordering of null values, either FIRST or LAST. + +If NULLS is not specified, SQL rules for the ordering of null values apply: that is, all null values must appear before all non-null values in the ordering or all null values must appear after all non-null values in the ordering, but it is not specified which. @@ -2985,6 +2988,7 @@ orderby_item ::= general_identification_variable | result_variable [ASC | DESC] + [NULLS {FIRST | LAST}] subquery ::= simple_select_clause subquery_from_clause [where_clause] [groupby_clause] [having_clause] subquery_from_clause ::=