[#11851] Do this only for aggregate window functions
This commit is contained in:
parent
fbda63cae6
commit
153de56fa7
@ -90,6 +90,7 @@ import org.jooq.WindowRowsAndStep;
|
||||
import org.jooq.WindowRowsStep;
|
||||
import org.jooq.WindowSpecification;
|
||||
import org.jooq.impl.Tools.BooleanDataKey;
|
||||
import org.jooq.impl.Tools.DataExtendedKey;
|
||||
|
||||
/**
|
||||
* @author Lukas Eder
|
||||
@ -105,18 +106,6 @@ implements
|
||||
{
|
||||
private static final Set<SQLDialect> SUPPORT_NO_PARENS_WINDOW_REFERENCE = SQLDialect.supportedBy(MYSQL, POSTGRES, SQLITE);
|
||||
|
||||
private static final Set<SQLDialect> REQUIRES_ORDER_BY_IN_LEAD_LAG = SQLDialect.supportedBy(H2, MARIADB);
|
||||
private static final Set<SQLDialect> REQUIRES_ORDER_BY_IN_NTILE = SQLDialect.supportedBy(H2);
|
||||
private static final Set<SQLDialect> REQUIRES_ORDER_BY_IN_RANK_DENSE_RANK = SQLDialect.supportedBy(H2, MARIADB);
|
||||
private static final Set<SQLDialect> REQUIRES_ORDER_BY_IN_PERCENT_RANK_CUME_DIST = SQLDialect.supportedBy(MARIADB);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
// Other attributes
|
||||
WindowSpecificationImpl windowSpecification;
|
||||
WindowDefinitionImpl windowDefinition;
|
||||
@ -179,22 +168,11 @@ implements
|
||||
if (window == null)
|
||||
return;
|
||||
|
||||
Boolean ordered =
|
||||
this instanceof Ntile && REQUIRES_ORDER_BY_IN_NTILE.contains(ctx.dialect())
|
||||
|| this instanceof PositionalWindowFunction && ((PositionalWindowFunction<?>) this).isLeadOrLag() && REQUIRES_ORDER_BY_IN_LEAD_LAG.contains(ctx.dialect())
|
||||
|| this instanceof RankingFunction && ((RankingFunction<?>) this).isRankOrDenseRank() && REQUIRES_ORDER_BY_IN_RANK_DENSE_RANK.contains(ctx.dialect())
|
||||
|| this instanceof RankingFunction && !((RankingFunction<?>) this).isRankOrDenseRank() && REQUIRES_ORDER_BY_IN_PERCENT_RANK_CUME_DIST.contains(ctx.dialect())
|
||||
|
||||
|
||||
|
||||
|
||||
;
|
||||
|
||||
ctx.sql(' ')
|
||||
.visit(K_OVER)
|
||||
.sql(' ');
|
||||
|
||||
ctx.data(BooleanDataKey.DATA_WINDOW_FUNCTION_REQUIRES_ORDER_BY, ordered, c -> c.visit(window));
|
||||
ctx.data(DataExtendedKey.DATA_WINDOW_FUNCTION, this, c -> c.visit(window));
|
||||
}
|
||||
|
||||
|
||||
|
||||
@ -59,8 +59,6 @@ final class ConditionAsField extends AbstractField<Boolean> {
|
||||
public final void accept(Context<?> ctx) {
|
||||
switch (ctx.family()) {
|
||||
|
||||
// Some databases don't accept predicates where column expressions
|
||||
// are expected.
|
||||
|
||||
|
||||
|
||||
|
||||
@ -280,6 +280,7 @@ import org.jooq.TableField;
|
||||
import org.jooq.TableRecord;
|
||||
import org.jooq.UDT;
|
||||
import org.jooq.UpdatableRecord;
|
||||
import org.jooq.WindowSpecification;
|
||||
import org.jooq.XML;
|
||||
import org.jooq.conf.BackslashEscaping;
|
||||
import org.jooq.conf.ParseNameCase;
|
||||
@ -504,12 +505,6 @@ final class Tools {
|
||||
*/
|
||||
DATA_EMULATE_BULK_INSERT_RETURNING,
|
||||
|
||||
/**
|
||||
* [#1535] We're currently generating the window specification of a
|
||||
* window function that requires an ORDER BY clause.
|
||||
*/
|
||||
DATA_WINDOW_FUNCTION_REQUIRES_ORDER_BY,
|
||||
|
||||
/**
|
||||
* [#9925] In some cases the <code>AS</code> keyword is required for aliasing, e.g. XML.
|
||||
*/
|
||||
@ -699,7 +694,14 @@ final class Tools {
|
||||
/**
|
||||
* [#9017] We've already transformed ROWNUM expressions to LIMIT.
|
||||
*/
|
||||
DATA_TRANSFORM_ROWNUM_TO_LIMIT
|
||||
DATA_TRANSFORM_ROWNUM_TO_LIMIT,
|
||||
|
||||
/**
|
||||
* [#1535] [#11851] The window function object that uses a
|
||||
* {@link WindowSpecification}.
|
||||
*/
|
||||
DATA_WINDOW_FUNCTION,
|
||||
|
||||
}
|
||||
|
||||
// ------------------------------------------------------------------------
|
||||
|
||||
@ -39,13 +39,23 @@ package org.jooq.impl;
|
||||
|
||||
import static java.lang.Boolean.TRUE;
|
||||
// ...
|
||||
// ...
|
||||
import static org.jooq.SQLDialect.CUBRID;
|
||||
// ...
|
||||
// ...
|
||||
import static org.jooq.SQLDialect.H2;
|
||||
// ...
|
||||
// ...
|
||||
import static org.jooq.SQLDialect.MARIADB;
|
||||
// ...
|
||||
import static org.jooq.SQLDialect.MYSQL;
|
||||
// ...
|
||||
// ...
|
||||
// ...
|
||||
import static org.jooq.SQLDialect.SQLITE;
|
||||
// ...
|
||||
// ...
|
||||
// ...
|
||||
import static org.jooq.impl.DSL.field;
|
||||
import static org.jooq.impl.DSL.one;
|
||||
import static org.jooq.impl.DSL.select;
|
||||
@ -59,6 +69,7 @@ import static org.jooq.impl.Keywords.K_PARTITION_BY;
|
||||
import static org.jooq.impl.Keywords.K_PRECEDING;
|
||||
import static org.jooq.impl.Keywords.K_UNBOUNDED_FOLLOWING;
|
||||
import static org.jooq.impl.Keywords.K_UNBOUNDED_PRECEDING;
|
||||
import static org.jooq.impl.Tools.DataExtendedKey.DATA_WINDOW_FUNCTION;
|
||||
import static org.jooq.impl.WindowSpecificationImpl.Exclude.CURRENT_ROW;
|
||||
import static org.jooq.impl.WindowSpecificationImpl.Exclude.GROUP;
|
||||
import static org.jooq.impl.WindowSpecificationImpl.Exclude.NO_OTHERS;
|
||||
@ -76,6 +87,7 @@ import org.jooq.Context;
|
||||
import org.jooq.Field;
|
||||
import org.jooq.Keyword;
|
||||
import org.jooq.OrderField;
|
||||
// ...
|
||||
import org.jooq.SQLDialect;
|
||||
import org.jooq.WindowSpecificationExcludeStep;
|
||||
import org.jooq.WindowSpecificationFinalStep;
|
||||
@ -84,6 +96,7 @@ import org.jooq.WindowSpecificationPartitionByStep;
|
||||
import org.jooq.WindowSpecificationRowsAndStep;
|
||||
import org.jooq.conf.RenderImplicitWindowRange;
|
||||
import org.jooq.impl.Tools.BooleanDataKey;
|
||||
import org.jooq.impl.Tools.DataExtendedKey;
|
||||
|
||||
/**
|
||||
* @author Lukas Eder
|
||||
@ -96,7 +109,19 @@ final class WindowSpecificationImpl extends AbstractQueryPart implements
|
||||
WindowSpecificationExcludeStep
|
||||
{
|
||||
|
||||
private static final Set<SQLDialect> OMIT_PARTITION_BY_ONE = SQLDialect.supportedBy(CUBRID, MYSQL, SQLITE);
|
||||
private static final Set<SQLDialect> OMIT_PARTITION_BY_ONE = SQLDialect.supportedBy(CUBRID, MYSQL, SQLITE);
|
||||
|
||||
private static final Set<SQLDialect> REQUIRES_ORDER_BY_IN_LEAD_LAG = SQLDialect.supportedBy(H2, MARIADB);
|
||||
private static final Set<SQLDialect> REQUIRES_ORDER_BY_IN_NTILE = SQLDialect.supportedBy(H2);
|
||||
private static final Set<SQLDialect> REQUIRES_ORDER_BY_IN_RANK_DENSE_RANK = SQLDialect.supportedBy(H2, MARIADB);
|
||||
private static final Set<SQLDialect> REQUIRES_ORDER_BY_IN_PERCENT_RANK_CUME_DIST = SQLDialect.supportedBy(MARIADB);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
private final WindowDefinitionImpl windowDefinition;
|
||||
private final QueryPartList<Field<?>> partitionBy;
|
||||
@ -133,19 +158,34 @@ final class WindowSpecificationImpl extends AbstractQueryPart implements
|
||||
public final void accept(Context<?> ctx) {
|
||||
SortFieldList o = orderBy;
|
||||
|
||||
// [#8414] [#8593] [#11021] Some RDBMS require ORDER BY in some window functions
|
||||
if (o.isEmpty() && TRUE.equals(ctx.data(BooleanDataKey.DATA_WINDOW_FUNCTION_REQUIRES_ORDER_BY))) {
|
||||
Field<Integer> constant;
|
||||
// [#8414] [#8593] [#11021] [#11851] Some RDBMS require ORDER BY in some window functions
|
||||
AbstractWindowFunction<?> w = (AbstractWindowFunction<?>) ctx.data(DATA_WINDOW_FUNCTION);
|
||||
|
||||
if (o.isEmpty()) {
|
||||
boolean ordered =
|
||||
w instanceof Ntile && REQUIRES_ORDER_BY_IN_NTILE.contains(ctx.dialect())
|
||||
|| w instanceof PositionalWindowFunction && ((PositionalWindowFunction<?>) w).isLeadOrLag() && REQUIRES_ORDER_BY_IN_LEAD_LAG.contains(ctx.dialect())
|
||||
|| w instanceof RankingFunction && ((RankingFunction<?>) w).isRankOrDenseRank() && REQUIRES_ORDER_BY_IN_RANK_DENSE_RANK.contains(ctx.dialect())
|
||||
|| w instanceof RankingFunction && !((RankingFunction<?>) w).isRankOrDenseRank() && REQUIRES_ORDER_BY_IN_PERCENT_RANK_CUME_DIST.contains(ctx.dialect())
|
||||
|
||||
|
||||
|
||||
|
||||
;
|
||||
|
||||
if (ordered) {
|
||||
Field<Integer> constant;
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
constant = field(select(one()));
|
||||
constant = field(select(one()));
|
||||
|
||||
o = new SortFieldList();
|
||||
o.add(constant.sortDefault());
|
||||
o = new SortFieldList();
|
||||
o.add(constant.sortDefault());
|
||||
}
|
||||
}
|
||||
|
||||
boolean hasWindowDefinitions = windowDefinition != null;
|
||||
@ -155,6 +195,8 @@ final class WindowSpecificationImpl extends AbstractQueryPart implements
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
;
|
||||
|
||||
int clauses = 0;
|
||||
|
||||
Loading…
Reference in New Issue
Block a user