[fix](nereids) hll and bitmap type can't be used as order by and group by exprs (#15471)
hll, bitmap, array and quantile state type can't be used in order by, group by and some agg exprs.
This commit is contained in:
@ -17,6 +17,7 @@
|
||||
|
||||
package org.apache.doris.nereids.rules.analysis;
|
||||
|
||||
import org.apache.doris.catalog.Type;
|
||||
import org.apache.doris.nereids.exceptions.AnalysisException;
|
||||
import org.apache.doris.nereids.rules.Rule;
|
||||
import org.apache.doris.nereids.rules.RuleType;
|
||||
@ -24,7 +25,10 @@ import org.apache.doris.nereids.trees.expressions.Expression;
|
||||
import org.apache.doris.nereids.trees.expressions.Slot;
|
||||
import org.apache.doris.nereids.trees.expressions.VirtualSlotReference;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.ExpressionTrait;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.ForbiddenMetricTypeArguments;
|
||||
import org.apache.doris.nereids.trees.plans.Plan;
|
||||
import org.apache.doris.nereids.trees.plans.logical.LogicalAggregate;
|
||||
import org.apache.doris.nereids.trees.plans.logical.LogicalSort;
|
||||
|
||||
import org.apache.commons.lang.StringUtils;
|
||||
|
||||
@ -41,6 +45,7 @@ public class CheckAfterRewrite extends OneAnalysisRuleFactory {
|
||||
public Rule build() {
|
||||
return any().then(plan -> {
|
||||
checkAllSlotReferenceFromChildren(plan);
|
||||
checkMetricTypeIsUsedCorrectly(plan);
|
||||
return null;
|
||||
}).toRule(RuleType.CHECK_ANALYSIS);
|
||||
}
|
||||
@ -79,4 +84,23 @@ public class CheckAfterRewrite extends OneAnalysisRuleFactory {
|
||||
})
|
||||
.collect(Collectors.toSet());
|
||||
}
|
||||
|
||||
private void checkMetricTypeIsUsedCorrectly(Plan plan) {
|
||||
if (plan instanceof LogicalAggregate) {
|
||||
if (((LogicalAggregate<?>) plan).getGroupByExpressions().stream()
|
||||
.anyMatch(expression -> expression.getDataType().isOnlyMetricType())
|
||||
|| ((LogicalAggregate<?>) plan).getAggregateFunctions().stream()
|
||||
.filter(aggregateFunction -> aggregateFunction instanceof ForbiddenMetricTypeArguments).anyMatch(
|
||||
aggregateFunction -> aggregateFunction.getArgumentsTypes().stream()
|
||||
.anyMatch(dataType -> dataType.isOnlyMetricType()))) {
|
||||
throw new AnalysisException(Type.OnlyMetricTypeErrorMsg);
|
||||
}
|
||||
} else if (plan instanceof LogicalSort) {
|
||||
if (((LogicalSort<?>) plan).getOrderKeys().stream().anyMatch((
|
||||
orderKey -> orderKey.getExpr().getDataType()
|
||||
.isOnlyMetricType()))) {
|
||||
throw new AnalysisException(Type.OnlyMetricTypeErrorMsg);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -0,0 +1,26 @@
|
||||
// Licensed to the Apache Software Foundation (ASF) under one
|
||||
// or more contributor license agreements. See the NOTICE file
|
||||
// distributed with this work for additional information
|
||||
// regarding copyright ownership. The ASF licenses this file
|
||||
// to you under the Apache License, Version 2.0 (the
|
||||
// "License"); you may not use this file except in compliance
|
||||
// with the License. You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing,
|
||||
// software distributed under the License is distributed on an
|
||||
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
// KIND, either express or implied. See the License for the
|
||||
// specific language governing permissions and limitations
|
||||
// under the License.
|
||||
|
||||
package org.apache.doris.nereids.trees.expressions.functions;
|
||||
|
||||
/**
|
||||
* means the function doesn't accept MetricType Arguments
|
||||
*
|
||||
* e.g. Count, Min, Max, Ndv etc
|
||||
*/
|
||||
public interface ForbiddenMetricTypeArguments {
|
||||
}
|
||||
@ -22,6 +22,7 @@ import org.apache.doris.nereids.exceptions.AnalysisException;
|
||||
import org.apache.doris.nereids.trees.expressions.Expression;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.AlwaysNotNullable;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.CustomSignature;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.ForbiddenMetricTypeArguments;
|
||||
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
|
||||
import org.apache.doris.nereids.types.BigIntType;
|
||||
import org.apache.doris.nereids.types.DataType;
|
||||
@ -32,7 +33,8 @@ import com.google.common.collect.ImmutableList;
|
||||
import java.util.List;
|
||||
|
||||
/** count agg function. */
|
||||
public class Count extends AggregateFunction implements AlwaysNotNullable, CustomSignature {
|
||||
public class Count extends AggregateFunction implements AlwaysNotNullable, CustomSignature,
|
||||
ForbiddenMetricTypeArguments {
|
||||
|
||||
private final boolean isStar;
|
||||
|
||||
|
||||
@ -20,6 +20,7 @@ package org.apache.doris.nereids.trees.expressions.functions.agg;
|
||||
import org.apache.doris.catalog.FunctionSignature;
|
||||
import org.apache.doris.nereids.trees.expressions.Expression;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.CustomSignature;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.ForbiddenMetricTypeArguments;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable;
|
||||
import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression;
|
||||
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
|
||||
@ -31,7 +32,8 @@ import com.google.common.collect.ImmutableList;
|
||||
import java.util.List;
|
||||
|
||||
/** max agg function. */
|
||||
public class Max extends AggregateFunction implements UnaryExpression, PropagateNullable, CustomSignature {
|
||||
public class Max extends AggregateFunction implements UnaryExpression, PropagateNullable, CustomSignature,
|
||||
ForbiddenMetricTypeArguments {
|
||||
public Max(Expression child) {
|
||||
super("max", child);
|
||||
}
|
||||
|
||||
@ -20,6 +20,7 @@ package org.apache.doris.nereids.trees.expressions.functions.agg;
|
||||
import org.apache.doris.catalog.FunctionSignature;
|
||||
import org.apache.doris.nereids.trees.expressions.Expression;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.CustomSignature;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.ForbiddenMetricTypeArguments;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.PropagateNullable;
|
||||
import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression;
|
||||
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
|
||||
@ -31,7 +32,8 @@ import com.google.common.collect.ImmutableList;
|
||||
import java.util.List;
|
||||
|
||||
/** min agg function. */
|
||||
public class Min extends AggregateFunction implements UnaryExpression, PropagateNullable, CustomSignature {
|
||||
public class Min extends AggregateFunction implements UnaryExpression, PropagateNullable, CustomSignature,
|
||||
ForbiddenMetricTypeArguments {
|
||||
|
||||
public Min(Expression child) {
|
||||
super("min", child);
|
||||
|
||||
@ -21,6 +21,7 @@ import org.apache.doris.catalog.FunctionSignature;
|
||||
import org.apache.doris.nereids.trees.expressions.Expression;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.AlwaysNotNullable;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.ExplicitlyCastableSignature;
|
||||
import org.apache.doris.nereids.trees.expressions.functions.ForbiddenMetricTypeArguments;
|
||||
import org.apache.doris.nereids.trees.expressions.shape.UnaryExpression;
|
||||
import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
|
||||
import org.apache.doris.nereids.types.BigIntType;
|
||||
@ -57,7 +58,7 @@ import java.util.List;
|
||||
* AggregateFunction 'ndv'. This class is generated by GenerateFunction.
|
||||
*/
|
||||
public class Ndv extends AggregateFunction
|
||||
implements UnaryExpression, ExplicitlyCastableSignature, AlwaysNotNullable {
|
||||
implements UnaryExpression, ExplicitlyCastableSignature, AlwaysNotNullable, ForbiddenMetricTypeArguments {
|
||||
|
||||
public static final List<FunctionSignature> SIGNATURES = ImmutableList.of(
|
||||
FunctionSignature.ret(BigIntType.INSTANCE).args(TinyIntType.INSTANCE),
|
||||
|
||||
@ -492,6 +492,23 @@ public abstract class DataType implements AbstractDataType {
|
||||
return this instanceof HllType;
|
||||
}
|
||||
|
||||
public boolean isQuantileState() {
|
||||
return this instanceof QuantileStateType;
|
||||
}
|
||||
|
||||
public boolean isArray() {
|
||||
return this instanceof ArrayType;
|
||||
}
|
||||
|
||||
// only metric types have the following constraint:
|
||||
// 1. don't support as key column
|
||||
// 2. don't support filter
|
||||
// 3. don't support group by
|
||||
// 4. don't support index
|
||||
public boolean isOnlyMetricType() {
|
||||
return isHll() || isBitmap() || isQuantileState() || isArray();
|
||||
}
|
||||
|
||||
public DataType promotion() {
|
||||
if (PROMOTION_MAP.containsKey(this.getClass())) {
|
||||
return PROMOTION_MAP.get(this.getClass()).get();
|
||||
|
||||
Reference in New Issue
Block a user