This is an automated email from the ASF dual-hosted git repository.

kxiao pushed a commit to branch branch-2.0-beta
in repository https://gitbox.apache.org/repos/asf/doris.git

commit 35f438ec74978baa37c578015aef3042096db73b
Author: mch_ucchi <41606806+sohardforan...@users.noreply.github.com>
AuthorDate: Fri Jun 9 18:18:56 2023 +0800

    [opt](planner)(Nereids) add switch to determine if some unfixed functions 
will be folded on fe. (#20270)
    
    add switch to determine if below functions could be folded on fe.
    - now()
    - current_date()
    - current_time()
    - unix_timestamp()
    - utc_timestamp()
    - uuid()
    - rand()
---
 .../apache/doris/analysis/ExpressionFunctions.java | 16 +++++++++++++++
 .../expression/rules/FoldConstantRuleOnFE.java     |  3 +++
 .../nereids/trees/expressions/Expression.java      |  5 -----
 .../trees/expressions/ExpressionEvaluator.java     |  2 +-
 .../doris/nereids/trees/expressions/Foldable.java  | 24 ----------------------
 .../expressions/functions/ExpressionTrait.java     |  4 ++++
 .../expressions/functions/Nondeterministic.java    | 10 ++++++++-
 .../expressions/functions/scalar/CurrentDate.java  |  3 +--
 .../expressions/functions/scalar/CurrentTime.java  |  3 +--
 .../functions/scalar/UnixTimestamp.java            | 11 +++++++++-
 .../java/org/apache/doris/qe/SessionVariable.java  | 13 ++++++++++++
 .../org/apache/doris/planner/QueryPlanTest.java    |  2 +-
 12 files changed, 59 insertions(+), 37 deletions(-)

diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/analysis/ExpressionFunctions.java 
b/fe/fe-core/src/main/java/org/apache/doris/analysis/ExpressionFunctions.java
index e39748b570..70f913e803 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/analysis/ExpressionFunctions.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/analysis/ExpressionFunctions.java
@@ -31,6 +31,7 @@ import org.apache.doris.rewrite.FEFunctions;
 import com.google.common.base.Joiner;
 import com.google.common.base.Preconditions;
 import com.google.common.collect.ImmutableMultimap;
+import com.google.common.collect.ImmutableSet;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Sets;
 import org.apache.logging.log4j.LogManager;
@@ -50,6 +51,15 @@ public enum ExpressionFunctions {
 
     private static final Logger LOG = 
LogManager.getLogger(ExpressionFunctions.class);
     private ImmutableMultimap<String, FEFunctionInvoker> functions;
+    private static final Set<String> unfixedFn = ImmutableSet.of(
+            "now",
+            "current_time",
+            "current_date",
+            "utc_timestamp",
+            "uuid",
+            "random",
+            "unix_timestamp"
+    );
 
     private ExpressionFunctions() {
         registerFunctions();
@@ -67,6 +77,12 @@ public enum ExpressionFunctions {
                 || constExpr instanceof FunctionCallExpr
                 || constExpr instanceof TimestampArithmeticExpr) {
             Function fn = constExpr.getFn();
+            if (ConnectContext.get() != null
+                    && ConnectContext.get().getSessionVariable() != null
+                    && 
!ConnectContext.get().getSessionVariable().isEnableFoldNondeterministicFn()
+                    && unfixedFn.contains(fn.getFunctionName().getFunction())) 
{
+                return constExpr;
+            }
 
             Preconditions.checkNotNull(fn, "Expr's fn can't be null.");
 
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/rules/expression/rules/FoldConstantRuleOnFE.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/rules/expression/rules/FoldConstantRuleOnFE.java
index 55e86699a9..c427ea8ec9 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/rules/expression/rules/FoldConstantRuleOnFE.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/rules/expression/rules/FoldConstantRuleOnFE.java
@@ -327,6 +327,9 @@ public class FoldConstantRuleOnFE extends 
AbstractExpressionRewriteRule {
 
     @Override
     public Expression visitBoundFunction(BoundFunction boundFunction, 
ExpressionRewriteContext context) {
+        if (!boundFunction.foldable()) {
+            return boundFunction;
+        }
         boundFunction = rewriteChildren(boundFunction, context);
         Optional<Expression> checkedExpr = preProcess(boundFunction);
         if (checkedExpr.isPresent()) {
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/Expression.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/Expression.java
index e58795e112..0d2772d768 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/Expression.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/Expression.java
@@ -20,7 +20,6 @@ package org.apache.doris.nereids.trees.expressions;
 import org.apache.doris.nereids.analyzer.Unbound;
 import org.apache.doris.nereids.exceptions.AnalysisException;
 import org.apache.doris.nereids.trees.AbstractTreeNode;
-import org.apache.doris.nereids.trees.expressions.functions.BoundFunction;
 import org.apache.doris.nereids.trees.expressions.functions.ExpressionTrait;
 import org.apache.doris.nereids.trees.expressions.literal.Literal;
 import org.apache.doris.nereids.trees.expressions.literal.NullLiteral;
@@ -140,10 +139,6 @@ public abstract class Expression extends 
AbstractTreeNode<Expression> implements
      */
     public boolean isConstant() {
         if (this instanceof LeafExpression) {
-            if (this instanceof BoundFunction) {
-                BoundFunction function = ((BoundFunction) this);
-                return function instanceof Foldable;
-            }
             return this instanceof Literal;
         } else {
             return children().stream().allMatch(Expression::isConstant);
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/ExpressionEvaluator.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/ExpressionEvaluator.java
index b6b2441c99..0e7ef81cc4 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/ExpressionEvaluator.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/ExpressionEvaluator.java
@@ -59,7 +59,7 @@ public enum ExpressionEvaluator {
      */
     public Expression eval(Expression expression) {
 
-        if (!expression.isConstant() || expression instanceof 
AggregateFunction) {
+        if (!(expression.isConstant() || expression.foldable()) || expression 
instanceof AggregateFunction) {
             return expression;
         }
 
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/Foldable.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/Foldable.java
deleted file mode 100644
index fae923dd86..0000000000
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/Foldable.java
+++ /dev/null
@@ -1,24 +0,0 @@
-// 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;
-
-/**
- * specifically for bound function can be folded to constant.
- */
-public interface Foldable {
-}
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/ExpressionTrait.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/ExpressionTrait.java
index 631a2922bc..f76e242dbb 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/ExpressionTrait.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/ExpressionTrait.java
@@ -72,4 +72,8 @@ public interface ExpressionTrait extends TreeNode<Expression> 
{
     default String toSql() throws UnboundException {
         throw new UnboundException("sql");
     }
+
+    default boolean foldable() {
+        return true;
+    }
 }
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/Nondeterministic.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/Nondeterministic.java
index 8ad8149aea..8fd6335740 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/Nondeterministic.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/Nondeterministic.java
@@ -17,6 +17,8 @@
 
 package org.apache.doris.nereids.trees.expressions.functions;
 
+import org.apache.doris.qe.ConnectContext;
+
 /**
  * Nondeterministic functions.
  *
@@ -24,5 +26,11 @@ package org.apache.doris.nereids.trees.expressions.functions;
  *
  * note: no 'uuid' function currently.
  */
-public interface Nondeterministic {
+public interface Nondeterministic extends ExpressionTrait {
+    @Override
+    default boolean foldable() {
+        return ConnectContext.get() == null
+                || ConnectContext.get().getSessionVariable() == null
+                || 
ConnectContext.get().getSessionVariable().isEnableFoldNondeterministicFn();
+    }
 }
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/CurrentDate.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/CurrentDate.java
index d4bcfbee77..bca7ffd05c 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/CurrentDate.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/CurrentDate.java
@@ -18,7 +18,6 @@
 package org.apache.doris.nereids.trees.expressions.functions.scalar;
 
 import org.apache.doris.catalog.FunctionSignature;
-import org.apache.doris.nereids.trees.expressions.Foldable;
 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.Nondeterministic;
@@ -34,7 +33,7 @@ import java.util.List;
  * ScalarFunction 'current_date'. This class is generated by GenerateFunction.
  */
 public class CurrentDate extends ScalarFunction
-        implements LeafExpression, ExplicitlyCastableSignature, 
Nondeterministic, AlwaysNotNullable, Foldable {
+        implements LeafExpression, ExplicitlyCastableSignature, 
Nondeterministic, AlwaysNotNullable {
 
     public static final List<FunctionSignature> SIGNATURES = ImmutableList.of(
             FunctionSignature.ret(DateType.INSTANCE).args()
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/CurrentTime.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/CurrentTime.java
index 9bf190879b..2e09c36d85 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/CurrentTime.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/CurrentTime.java
@@ -18,7 +18,6 @@
 package org.apache.doris.nereids.trees.expressions.functions.scalar;
 
 import org.apache.doris.catalog.FunctionSignature;
-import org.apache.doris.nereids.trees.expressions.Foldable;
 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.Nondeterministic;
@@ -34,7 +33,7 @@ import java.util.List;
  * ScalarFunction 'current_time'. This class is generated by GenerateFunction.
  */
 public class CurrentTime extends ScalarFunction
-        implements LeafExpression, ExplicitlyCastableSignature, 
Nondeterministic, AlwaysNotNullable, Foldable {
+        implements LeafExpression, ExplicitlyCastableSignature, 
Nondeterministic, AlwaysNotNullable {
 
     public static final List<FunctionSignature> SIGNATURES = ImmutableList.of(
             FunctionSignature.ret(TimeType.INSTANCE).args()
diff --git 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/UnixTimestamp.java
 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/UnixTimestamp.java
index 2c33115d5b..20958dd45a 100644
--- 
a/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/UnixTimestamp.java
+++ 
b/fe/fe-core/src/main/java/org/apache/doris/nereids/trees/expressions/functions/scalar/UnixTimestamp.java
@@ -20,6 +20,7 @@ package 
org.apache.doris.nereids.trees.expressions.functions.scalar;
 import org.apache.doris.catalog.FunctionSignature;
 import org.apache.doris.nereids.trees.expressions.Expression;
 import 
org.apache.doris.nereids.trees.expressions.functions.ExplicitlyCastableSignature;
+import org.apache.doris.nereids.trees.expressions.functions.Nondeterministic;
 import 
org.apache.doris.nereids.trees.expressions.functions.PropagateNullableOnDateLikeV2Args;
 import org.apache.doris.nereids.trees.expressions.visitor.ExpressionVisitor;
 import org.apache.doris.nereids.types.DateTimeType;
@@ -39,7 +40,7 @@ import java.util.List;
  * ScalarFunction 'unix_timestamp'. This class is generated by 
GenerateFunction.
  */
 public class UnixTimestamp extends ScalarFunction
-        implements ExplicitlyCastableSignature, 
PropagateNullableOnDateLikeV2Args {
+        implements Nondeterministic, ExplicitlyCastableSignature, 
PropagateNullableOnDateLikeV2Args {
 
     private static final List<FunctionSignature> SIGNATURES = ImmutableList.of(
             FunctionSignature.ret(IntegerType.INSTANCE).args(),
@@ -100,6 +101,14 @@ public class UnixTimestamp extends ScalarFunction
         }
     }
 
+    @Override
+    public boolean foldable() {
+        if (children.size() != 0) {
+            return true;
+        }
+        return Nondeterministic.super.foldable();
+    }
+
     @Override
     public List<FunctionSignature> getSignatures() {
         return SIGNATURES;
diff --git a/fe/fe-core/src/main/java/org/apache/doris/qe/SessionVariable.java 
b/fe/fe-core/src/main/java/org/apache/doris/qe/SessionVariable.java
index 3afbbaeb6d..34d24dfcc9 100644
--- a/fe/fe-core/src/main/java/org/apache/doris/qe/SessionVariable.java
+++ b/fe/fe-core/src/main/java/org/apache/doris/qe/SessionVariable.java
@@ -240,6 +240,8 @@ public class SessionVariable implements Serializable, 
Writable {
 
     public static final String ENABLE_DPHYP_TRACE = "enable_dphyp_trace";
 
+    public static final String ENABLE_FOLD_NONDETERMINISTIC_FN = 
"enable_fold_nondeterministic_fn";
+
     public static final String ENABLE_RUNTIME_FILTER_PRUNE =
             "enable_runtime_filter_prune";
 
@@ -911,6 +913,9 @@ public class SessionVariable implements Serializable, 
Writable {
     @VariableMgr.VarAttr(name = ENABLE_MINIDUMP)
     public boolean enableMinidump = false;
 
+    @VariableMgr.VarAttr(name = ENABLE_FOLD_NONDETERMINISTIC_FN)
+    public boolean enableFoldNondeterministicFn = true;
+
     @VariableMgr.VarAttr(name = TRACE_NEREIDS)
     public boolean traceNereids = false;
 
@@ -1703,6 +1708,14 @@ public class SessionVariable implements Serializable, 
Writable {
         this.enablePartitionTopN = enablePartitionTopN;
     }
 
+    public boolean isEnableFoldNondeterministicFn() {
+        return enableFoldNondeterministicFn;
+    }
+
+    public void setEnableFoldNondeterministicFn(boolean 
enableFoldNondeterministicFn) {
+        this.enableFoldNondeterministicFn = enableFoldNondeterministicFn;
+    }
+
     public boolean isReturnObjectDataAsBinary() {
         return returnObjectDataAsBinary;
     }
diff --git 
a/fe/fe-core/src/test/java/org/apache/doris/planner/QueryPlanTest.java 
b/fe/fe-core/src/test/java/org/apache/doris/planner/QueryPlanTest.java
index 79f2b50871..ac4373a490 100644
--- a/fe/fe-core/src/test/java/org/apache/doris/planner/QueryPlanTest.java
+++ b/fe/fe-core/src/test/java/org/apache/doris/planner/QueryPlanTest.java
@@ -855,7 +855,7 @@ public class QueryPlanTest extends TestWithFeService {
                 + "from test.test1 "
                 + "where time_col = case when date_format(now(),'%H%i')  < 123 
then date_format(date_sub("
                 + "now(),2),'%Y%m%d') else 
date_format(date_sub(now(),1),'%Y%m%d') end";
-        
Assert.assertTrue(!StringUtils.containsIgnoreCase(getSQLPlanOrErrorMsg("explain 
" + caseWhenSql),
+        
Assert.assertFalse(StringUtils.containsIgnoreCase(getSQLPlanOrErrorMsg("explain 
" + caseWhenSql),
                 "CASE WHEN"));
 
         // test 1: case when then


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscr...@doris.apache.org
For additional commands, e-mail: commits-h...@doris.apache.org

Reply via email to