Added OrderBy.Order.NULL.
"order by null" can be used in a query with a "group by" in it to tell the database to suppress the overhead of sorting the results. (Supported in postgres and mysql.) Changed the build visitors to have a whitelist of supported Orders, and to NPE on a null value for the Order enum. Note that previously "order by null" could be accomplished by passing a null value to your OrderBy, but now the enum constant must be used. I can change that if this disrupts anything.
This commit is contained in:
@@ -20,6 +20,10 @@ public class OrderBy implements QueryClause
|
||||
/** Indicates the order of the clause. */
|
||||
public enum Order
|
||||
{
|
||||
/** Ordering by null can be used to suppress sorting in the database when using
|
||||
* a GROUP BY in your query (postgres and mysql only). */
|
||||
NULL,
|
||||
|
||||
/** Ascending (nulls last). */
|
||||
ASC,
|
||||
|
||||
|
||||
@@ -84,6 +84,7 @@ import com.samskivert.depot.impl.operator.MultiOperator;
|
||||
import com.samskivert.depot.impl.operator.Not;
|
||||
|
||||
import static com.google.common.base.Preconditions.checkArgument;
|
||||
import static com.google.common.base.Preconditions.checkNotNull;
|
||||
import static com.samskivert.Log.log;
|
||||
|
||||
/**
|
||||
@@ -979,17 +980,27 @@ public abstract class BuildVisitor implements FragmentVisitor<Void>
|
||||
*/
|
||||
protected OrderBy.Order validateOrder (OrderBy.Order order)
|
||||
{
|
||||
if ((order == OrderBy.Order.ASC_NULLS_FIRST) || (order == OrderBy.Order.DESC_NULLS_LAST)) {
|
||||
if (false /*Boolean.getBoolean("com.samskivert.depot.massageOrderByNulls")*/) {
|
||||
order = (order == OrderBy.Order.ASC_NULLS_FIRST)
|
||||
? OrderBy.Order.ASC : OrderBy.Order.DESC;
|
||||
} else {
|
||||
throw new RuntimeException(order + " is not supported on your database.");
|
||||
}
|
||||
checkNotNull(order);
|
||||
if (orderSupported(order)) {
|
||||
return order;
|
||||
}
|
||||
return order;
|
||||
// Note: the following code was never "live". If needed it can be made so.
|
||||
// The property name is up for debate.
|
||||
// if (Boolean.getBoolean("com.samskivert.depot.massageNullOrders")) {
|
||||
// switch (order) {
|
||||
// case ASC_NULLS_FIRST: return OrderBy.Order.ASC;
|
||||
// case DESC_NULLS_LAST: return OrderBy.Order.DESC;
|
||||
// }
|
||||
// }
|
||||
throw new IllegalArgumentException(
|
||||
"Order '" + order.name() + "' is not supported by your database.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Is the specified order supported by this database?
|
||||
*/
|
||||
protected abstract boolean orderSupported (OrderBy.Order order);
|
||||
|
||||
protected BuildVisitor (DepotTypes types, boolean allowComplexIndices)
|
||||
{
|
||||
_types = types;
|
||||
|
||||
@@ -18,6 +18,7 @@ import com.samskivert.depot.Ops;
|
||||
import com.samskivert.depot.PersistentRecord;
|
||||
import com.samskivert.depot.annotation.FullTextIndex;
|
||||
import com.samskivert.depot.annotation.GeneratedValue;
|
||||
import com.samskivert.depot.clause.OrderBy;
|
||||
import com.samskivert.depot.expression.ColumnExp;
|
||||
import com.samskivert.depot.expression.SQLExpression;
|
||||
import com.samskivert.depot.impl.expression.AggregateFun;
|
||||
@@ -183,6 +184,15 @@ public class HSQLBuilder
|
||||
@Override protected void appendIdentifier (String field) {
|
||||
_builder.append("\"").append(field).append("\"");
|
||||
}
|
||||
|
||||
@Override protected boolean orderSupported (OrderBy.Order order)
|
||||
{
|
||||
switch (order) {
|
||||
case ASC: case DESC:
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
public HSQLBuilder (DepotTypes types)
|
||||
|
||||
@@ -14,6 +14,7 @@ import com.samskivert.util.StringUtil;
|
||||
|
||||
import com.samskivert.depot.PersistentRecord;
|
||||
import com.samskivert.depot.annotation.FullTextIndex;
|
||||
import com.samskivert.depot.clause.OrderBy;
|
||||
import com.samskivert.depot.expression.ColumnExp;
|
||||
import com.samskivert.depot.operator.FullText;
|
||||
|
||||
@@ -162,6 +163,15 @@ public class MySQLBuilder
|
||||
{
|
||||
_builder.append("() values ()");
|
||||
}
|
||||
|
||||
@Override protected boolean orderSupported (OrderBy.Order order)
|
||||
{
|
||||
switch (order) {
|
||||
case NULL: case ASC: case DESC:
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
protected static String massageFTQuery (FullText fullText)
|
||||
|
||||
@@ -119,8 +119,13 @@ public class PostgreSQLBuilder
|
||||
_builder.append("\"").append(field).append("\"");
|
||||
}
|
||||
|
||||
@Override protected OrderBy.Order validateOrder (OrderBy.Order order) {
|
||||
return order;
|
||||
@Override protected boolean orderSupported (OrderBy.Order order)
|
||||
{
|
||||
switch (order) {
|
||||
case NULL: case ASC: case DESC: case ASC_NULLS_FIRST: case DESC_NULLS_LAST:
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
protected PGBuildVisitor (DepotTypes types)
|
||||
|
||||
Reference in New Issue
Block a user