Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -61,11 +61,13 @@ public CompoundPredicate(Operator op, Expr e1, Expr e2) {
if (e2 != null) {
children.add(e2);
}
printSqlInParens = true;
}

protected CompoundPredicate(CompoundPredicate other) {
super(other);
op = other.op;
printSqlInParens = true;
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,6 @@
import org.apache.doris.analysis.Analyzer;
import org.apache.doris.analysis.BinaryPredicate;
import org.apache.doris.analysis.BoolLiteral;
import org.apache.doris.analysis.CompoundPredicate;
import org.apache.doris.analysis.CompoundPredicate.Operator;
import org.apache.doris.analysis.DateLiteral;
import org.apache.doris.analysis.Expr;
import org.apache.doris.analysis.ExprSubstitutionMap;
Expand Down Expand Up @@ -321,36 +319,6 @@ private static boolean containsFunctionCallExpr(Expr expr) {
}

public static String conjunctExprToString(TOdbcTableType tableType, Expr expr, TableIf tbl) {
if (expr instanceof CompoundPredicate) {
StringBuilder result = new StringBuilder();
CompoundPredicate compoundPredicate = (CompoundPredicate) expr;

// If the operator is 'NOT', prepend 'NOT' to the start of the string
if (compoundPredicate.getOp() == Operator.NOT) {
result.append("NOT ");
}

// Iterate through all children of the CompoundPredicate
for (Expr child : compoundPredicate.getChildren()) {
// Recursively call conjunctExprToString for each child and append to the result
result.append(conjunctExprToString(tableType, child, tbl));

// If the operator is not 'NOT', append the operator after each child expression
if (!(compoundPredicate.getOp() == Operator.NOT)) {
result.append(" ").append(compoundPredicate.getOp().toString()).append(" ");
}
}

// For operators other than 'NOT', remove the extra appended operator at the end
// This is necessary for operators like 'AND' or 'OR' that appear between child expressions
if (!(compoundPredicate.getOp() == Operator.NOT)) {
result.setLength(result.length() - compoundPredicate.getOp().toString().length() - 2);
}

// Return the processed string trimmed of any extra spaces
return result.toString().trim();
}

if (expr.contains(DateLiteral.class) && expr instanceof BinaryPredicate) {
ArrayList<Expr> children = expr.getChildren();
String filter = children.get(0).toExternalSql(TableType.JDBC_EXTERNAL_TABLE, tbl);
Expand All @@ -367,7 +335,7 @@ public static String conjunctExprToString(TOdbcTableType tableType, Expr expr, T
return filter;
}

// only for old planner
// Only for old planner
if (expr.contains(BoolLiteral.class) && "1".equals(expr.getStringValue()) && expr.getChildren().isEmpty()) {
return "1 = 1";
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -93,15 +93,15 @@ public void testNormal() throws UserException {
stmt = new CancelExportStmt(null, compoundAndPredicate);
stmt.analyze(analyzer);
Assertions.assertEquals(
"CANCEL EXPORT FROM testDb WHERE (`label` = 'doris_test_label') AND (`state` = 'PENDING')",
"CANCEL EXPORT FROM testDb WHERE ((`label` = 'doris_test_label') AND (`state` = 'PENDING'))",
stmt.toString());

CompoundPredicate compoundOrPredicate = new CompoundPredicate(Operator.OR, labelBinaryPredicate,
stateBinaryPredicate);
stmt = new CancelExportStmt(null, compoundOrPredicate);
stmt.analyze(analyzer);
Assertions.assertEquals(
"CANCEL EXPORT FROM testDb WHERE (`label` = 'doris_test_label') OR (`state` = 'PENDING')",
"CANCEL EXPORT FROM testDb WHERE ((`label` = 'doris_test_label') OR (`state` = 'PENDING'))",
stmt.toString());
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -94,15 +94,15 @@ public void testNormal() throws UserException {
stmt = new CancelLoadStmt(null, compoundAndPredicate);
stmt.analyze(analyzer);
Assertions.assertEquals(
"CANCEL LOAD FROM testDb WHERE (`label` = 'doris_test_label') AND (`state` = 'LOADING')",
"CANCEL LOAD FROM testDb WHERE ((`label` = 'doris_test_label') AND (`state` = 'LOADING'))",
stmt.toString());

CompoundPredicate compoundOrPredicate = new CompoundPredicate(Operator.OR, labelBinaryPredicate,
stateBinaryPredicate);
stmt = new CancelLoadStmt(null, compoundOrPredicate);
stmt.analyze(analyzer);
Assertions.assertEquals(
"CANCEL LOAD FROM testDb WHERE (`label` = 'doris_test_label') OR (`state` = 'LOADING')",
"CANCEL LOAD FROM testDb WHERE ((`label` = 'doris_test_label') OR (`state` = 'LOADING'))",
stmt.toString());

// test match
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -301,9 +301,9 @@ public void testDeduplicateOrs() throws Exception {
String commonExpr2 = "`t3`.`k3` = `t1`.`k3`";
String commonExpr3 = "`t1`.`k1` = `t5`.`k1`";
String commonExpr4 = "t5`.`k2` = 'United States'";
String betweenExpanded1 = "(CAST(CAST(`t1`.`k4` AS decimalv3(12,2)) AS int) >= 100) AND (CAST(CAST(`t1`.`k4` AS decimalv3(12,2)) AS int) <= 150)";
String betweenExpanded2 = "(CAST(CAST(`t1`.`k4` AS decimalv3(12,2)) AS int) >= 50) AND (CAST(CAST(`t1`.`k4` AS decimalv3(12,2)) AS int) <= 100)";
String betweenExpanded3 = "(`t1`.`k4` >= 50) AND (`t1`.`k4` <= 250)";
String betweenExpanded1 = "(CAST(CAST(`t1`.`k4` AS decimalv3(12,2)) AS int) >= 100)) AND (CAST(CAST(`t1`.`k4` AS decimalv3(12,2)) AS int) <= 150))";
String betweenExpanded2 = "(CAST(CAST(`t1`.`k4` AS decimalv3(12,2)) AS int) >= 50)) AND (CAST(CAST(`t1`.`k4` AS decimalv3(12,2)) AS int) <= 100))";
String betweenExpanded3 = "(`t1`.`k4` >= 50)) AND (`t1`.`k4` <= 250)";

String rewrittenSql = stmt.toSql();
Assert.assertTrue(rewrittenSql.contains(commonExpr1));
Expand Down Expand Up @@ -347,17 +347,17 @@ public void testDeduplicateOrs() throws Exception {
SelectStmt stmt2 = (SelectStmt) UtFrameUtils.parseAndAnalyzeStmt(sql2, ctx);
stmt2.rewriteExprs(new Analyzer(ctx.getEnv(), ctx).getExprRewriter());
String fragment3 =
"((((`t1`.`k4` >= 50) AND (`t1`.`k4` <= 300)) AND `t2`.`k2` IN ('United States', 'United States1') "
"(((((`t1`.`k4` >= 50) AND (`t1`.`k4` <= 300)) AND `t2`.`k2` IN ('United States', 'United States1')) "
+ "AND `t2`.`k3` IN ('CO', 'IL', 'MN', 'OH', 'MT', 'NM', 'TX', 'MO', 'MI')) "
+ "AND (`t1`.`k1` = `t2`.`k3`) AND (`t2`.`k2` = 'United States') "
+ "AND `t2`.`k3` IN ('CO', 'IL', 'MN') AND (`t1`.`k4` >= 100) AND (`t1`.`k4` <= 200) "
+ "AND (((((((`t1`.`k1` = `t2`.`k3`) AND (`t2`.`k2` = 'United States')) "
+ "AND `t2`.`k3` IN ('CO', 'IL', 'MN')) AND (`t1`.`k4` >= 100)) AND (`t1`.`k4` <= 200)) "
+ "OR "
+ "(`t1`.`k1` = `t2`.`k1`) AND (`t2`.`k2` = 'United States1') "
+ "AND `t2`.`k3` IN ('OH', 'MT', 'NM') AND (`t1`.`k4` >= 150) AND (`t1`.`k4` <= 300) "
+ "(((((`t1`.`k1` = `t2`.`k1`) AND (`t2`.`k2` = 'United States1')) "
+ "AND `t2`.`k3` IN ('OH', 'MT', 'NM')) AND (`t1`.`k4` >= 150)) AND (`t1`.`k4` <= 300))) "
+ "OR "
+ "(`t1`.`k1` = `t2`.`k1`) AND (`t2`.`k2` = 'United States') "
+ "AND `t2`.`k3` IN ('TX', 'MO', 'MI') "
+ "AND (`t1`.`k4` >= 50) AND (`t1`.`k4` <= 250))";
+ "(((((`t1`.`k1` = `t2`.`k1`) AND (`t2`.`k2` = 'United States')) "
+ "AND `t2`.`k3` IN ('TX', 'MO', 'MI')) "
+ "AND (`t1`.`k4` >= 50)) AND (`t1`.`k4` <= 250))))";
Assert.assertTrue(stmt2.toSql().contains(fragment3));

String sql3 = "select\n"
Expand Down Expand Up @@ -417,7 +417,7 @@ public void testDeduplicateOrs() throws Exception {
SelectStmt stmt7 = (SelectStmt) UtFrameUtils.parseAndAnalyzeStmt(sql7, ctx);
stmt7.rewriteExprs(new Analyzer(ctx.getEnv(), ctx).getExprRewriter());
Assert.assertTrue(stmt7.toSql()
.contains("`t2`.`k1` IS NOT NULL OR `t1`.`k1` IS NOT NULL AND `t1`.`k2` IS NOT NULL"));
.contains("`t2`.`k1` IS NOT NULL OR (`t1`.`k1` IS NOT NULL AND `t1`.`k2` IS NOT NULL)"));

String sql8 = "select\n"
+ " avg(t1.k4)\n"
Expand All @@ -429,13 +429,13 @@ public void testDeduplicateOrs() throws Exception {
SelectStmt stmt8 = (SelectStmt) UtFrameUtils.parseAndAnalyzeStmt(sql8, ctx);
stmt8.rewriteExprs(new Analyzer(ctx.getEnv(), ctx).getExprRewriter());
Assert.assertTrue(stmt8.toSql()
.contains("`t2`.`k1` IS NOT NULL AND `t1`.`k1` IS NOT NULL AND `t1`.`k1` IS NOT NULL"));
.contains("(`t2`.`k1` IS NOT NULL AND `t1`.`k1` IS NOT NULL) AND `t1`.`k1` IS NOT NULL"));

String sql9 = "select * from db1.tbl1 where (k1='shutdown' and k4<1) or (k1='switchOff' and k4>=1)";
SelectStmt stmt9 = (SelectStmt) UtFrameUtils.parseAndAnalyzeStmt(sql9, ctx);
stmt9.rewriteExprs(new Analyzer(ctx.getEnv(), ctx).getExprRewriter());
Assert.assertTrue(
stmt9.toSql().contains("(`k1` = 'shutdown') AND (`k4` < 1) OR (`k1` = 'switchOff') AND (`k4` >= 1)"));
stmt9.toSql().contains("((`k1` = 'shutdown') AND (`k4` < 1)) OR ((`k1` = 'switchOff') AND (`k4` >= 1))"));
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -98,14 +98,14 @@ public ProcNodeInterface open(String path) throws AnalysisException {
List<OrderByElement> orderBy = Arrays.asList(
new OrderByElement(new SlotRef(tableName, "TableName"), false, false));
ShowBuildIndexStmt stmt1 = new ShowBuildIndexStmt(null, where, orderBy, new LimitElement(1, 100));
Assertions.assertEquals(stmt1.toSql(), "SHOW BUILD INDEX WHERE (`a`.`b`.`c`.`createtime` > '%.b.%') "
+ "AND (`a`.`b`.`c`.`tablename` = '%.b.%') ORDER BY `a`.`b`.`c`.`TableName` DESC NULLS LAST "
Assertions.assertEquals(stmt1.toSql(), "SHOW BUILD INDEX WHERE ((`a`.`b`.`c`.`createtime` > '%.b.%') "
+ "AND (`a`.`b`.`c`.`tablename` = '%.b.%')) ORDER BY `a`.`b`.`c`.`TableName` DESC NULLS LAST "
+ "LIMIT 1, 100");

stmt1.analyze(analyzer);
Assertions.assertEquals(stmt1.toSql(), "SHOW BUILD INDEX FROM `testDb` WHERE "
+ "(`a`.`b`.`c`.`createtime` > CAST('%.b.%' AS datetimev2(0))) "
+ "AND (`a`.`b`.`c`.`tablename` = '%.b.%') "
+ "((`a`.`b`.`c`.`createtime` > CAST('%.b.%' AS datetimev2(0))) "
+ "AND (`a`.`b`.`c`.`tablename` = '%.b.%')) "
+ "ORDER BY `a`.`b`.`c`.`TableName` DESC NULLS LAST LIMIT 1, 100");

Assertions.assertEquals(stmt1.getFilterMap().size(), 2);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ public void testPipesAsConcatMode() {
if (!(expr instanceof CompoundPredicate)) {
Assert.fail();
}
Assert.assertEquals("'a' OR 'b' OR 'c'", expr.toSql());
Assert.assertEquals("(('a' OR 'b') OR 'c')", expr.toSql());
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2234,15 +2234,15 @@ public void testRewriteOrToIn() throws Exception {

sql = "SELECT /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where (query_time = 1 or query_time = 2) and query_time in (3, 4)";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains("PREDICATES: `query_time` IN (1, 2) AND `query_time` IN (3, 4)\n"));
Assert.assertTrue(explainString.contains("PREDICATES: (`query_time` IN (1, 2) AND `query_time` IN (3, 4))\n"));

sql = "SELECT /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where (query_time = 1 or query_time = 2 or scan_bytes = 2) and scan_bytes in (2, 3)";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains("PREDICATES: `query_time` IN (1, 2) OR (`scan_bytes` = 2) AND `scan_bytes` IN (2, 3)\n"));
Assert.assertTrue(explainString.contains("PREDICATES: ((`query_time` IN (1, 2) OR (`scan_bytes` = 2)) AND `scan_bytes` IN (2, 3))\n"));

sql = "SELECT /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where (query_time = 1 or query_time = 2) and (scan_bytes = 2 or scan_bytes = 3)";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains("PREDICATES: `query_time` IN (1, 2) AND `scan_bytes` IN (2, 3)\n"));
Assert.assertTrue(explainString.contains("PREDICATES: (`query_time` IN (1, 2) AND `scan_bytes` IN (2, 3))\n"));

sql = "SELECT /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where query_time = 1 or query_time = 2 or query_time = 3 or query_time = 1";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Expand All @@ -2255,22 +2255,22 @@ public void testRewriteOrToIn() throws Exception {
connectContext.getSessionVariable().setRewriteOrToInPredicateThreshold(100);
sql = "SELECT /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where query_time = 1 or query_time = 2 or query_time in (3, 4)";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains("PREDICATES: (`query_time` = 1) OR (`query_time` = 2) OR `query_time` IN (3, 4)\n"));
Assert.assertTrue(explainString.contains("PREDICATES: (((`query_time` = 1) OR (`query_time` = 2)) OR `query_time` IN (3, 4))\n"));
connectContext.getSessionVariable().setRewriteOrToInPredicateThreshold(2);

sql = "SELECT /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where (query_time = 1 or query_time = 2) and query_time in (3, 4)";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains("PREDICATES: `query_time` IN (1, 2) AND `query_time` IN (3, 4)\n"));
Assert.assertTrue(explainString.contains("PREDICATES: (`query_time` IN (1, 2) AND `query_time` IN (3, 4))\n"));

//test we can handle `!=` and `not in`
sql = "select /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where (query_time = 1 or query_time = 2 or query_time!= 3 or query_time not in (5, 6))";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains("PREDICATES: `query_time` IN (1, 2) OR (`query_time` != 3) OR `query_time` NOT IN (5, 6)\n"));
Assert.assertTrue(explainString.contains("PREDICATES: (`query_time` IN (1, 2) OR ((`query_time` != 3) OR `query_time` NOT IN (5, 6)))\n"));

//test we can handle merge 2 or more columns
sql = "select /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where (query_time = 1 or query_time = 2 or scan_rows = 3 or scan_rows = 4)";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains("PREDICATES: `query_time` IN (1, 2) OR `scan_rows` IN (3, 4)"));
Assert.assertTrue(explainString.contains("PREDICATES: (`query_time` IN (1, 2) OR `scan_rows` IN (3, 4))"));

//merge in-pred or in-pred
sql = "select /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where (query_time = 1 or query_time = 2 or query_time = 3 or query_time = 4)";
Expand All @@ -2285,16 +2285,15 @@ public void testRewriteOrToIn() throws Exception {
+ " or (db not in ('x', 'y')) ";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains(
"PREDICATES: (`query_id` = `client_ip`) "
+ "AND (`stmt_id` IN (1, 2, 3) OR (`user` = 'abc') AND `state` IN ('a', 'b', 'c', 'd')) "
+ "OR (`db` NOT IN ('x', 'y'))\n"));
"PREDICATES: (((`query_id` = `client_ip`) AND (`stmt_id` IN (1, 2, 3) OR ((`user` = 'abc') "
+ "AND `state` IN ('a', 'b', 'c', 'd')))) OR (`db` NOT IN ('x', 'y')))\n"));

//ExtractCommonFactorsRule may generate more expr, test the rewriteOrToIn applied on generated exprs
sql = "select /*+ SET_VAR(enable_nereids_planner=false) */ * from test1 where (stmt_id=1 and state='a') or (stmt_id=2 and state='b')";
explainString = UtFrameUtils.getSQLPlanOrErrorMsg(connectContext, "EXPLAIN " + sql);
Assert.assertTrue(explainString.contains(
"PREDICATES: `state` IN ('a', 'b') AND `stmt_id` IN (1, 2) AND"
+ " (`stmt_id` = 1) AND (`state` = 'a') OR (`stmt_id` = 2) AND (`state` = 'b')\n"
"PREDICATES: ((`state` IN ('a', 'b') AND `stmt_id` IN (1, 2)) AND (((`stmt_id` = 1) AND "
+ "(`state` = 'a')) OR ((`stmt_id` = 2) AND (`state` = 'b'))))\n"
));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -270,7 +270,7 @@ public void testMergeFilter() throws Exception {
createPolicy("CREATE ROW POLICY test_row_policy4 ON test.table1 AS PERMISSIVE TO test_policy USING (k2 = 1)");
String queryStr = "EXPLAIN select /*+ SET_VAR(enable_nereids_planner=false) */ * from test.table1";
String explainString = getSQLPlanOrErrorMsg(queryStr);
Assertions.assertTrue(explainString.contains("(`k1` = 1) AND (`k2` = 1) AND (`k2` = 2) OR (`k2` = 1)"));
Assertions.assertTrue(explainString.contains("(((`k1` = 1) AND (`k2` = 1)) AND ((`k2` = 2) OR (`k2` = 1)))"));
dropPolicy("DROP ROW POLICY test_row_policy1 ON test.table1");
dropPolicy("DROP ROW POLICY test_row_policy2 ON test.table1");
dropPolicy("DROP ROW POLICY test_row_policy3 ON test.table1");
Expand Down Expand Up @@ -318,13 +318,13 @@ public void testComplexSqlNereidsPlanner() throws Exception {
createPolicy("CREATE ROW POLICY test_row_policy1 ON test.table1 AS RESTRICTIVE TO test_policy USING (k1 = 1)");
createPolicy("CREATE ROW POLICY test_row_policy2 ON test.table1 AS RESTRICTIVE TO test_policy USING (k2 = 1)");
String joinSql = "select * from table1 join table2 on table1.k1=table2.k1";
Assertions.assertTrue(getSQLPlanOrErrorMsg(joinSql).contains("PREDICATES: (k1 = 1) AND (k2 = 1)"));
Assertions.assertTrue(getSQLPlanOrErrorMsg(joinSql).contains("PREDICATES: ((k1 = 1) AND (k2 = 1))"));
String unionSql = "select * from table1 union select * from table2";
Assertions.assertTrue(getSQLPlanOrErrorMsg(unionSql).contains("PREDICATES: (k1 = 1) AND (k2 = 1)"));
Assertions.assertTrue(getSQLPlanOrErrorMsg(unionSql).contains("PREDICATES: ((k1 = 1) AND (k2 = 1))"));
String subQuerySql = "select * from table2 where k1 in (select k1 from table1)";
Assertions.assertTrue(getSQLPlanOrErrorMsg(subQuerySql).contains("PREDICATES: (k1 = 1) AND (k2 = 1)"));
Assertions.assertTrue(getSQLPlanOrErrorMsg(subQuerySql).contains("PREDICATES: ((k1 = 1) AND (k2 = 1))"));
String aliasSql = "select * from table1 t1 join table2 t2 on t1.k1=t2.k1";
Assertions.assertTrue(getSQLPlanOrErrorMsg(aliasSql).contains("PREDICATES: (k1 = 1) AND (k2 = 1)"));
Assertions.assertTrue(getSQLPlanOrErrorMsg(aliasSql).contains("PREDICATES: ((k1 = 1) AND (k2 = 1))"));
dropPolicy("DROP ROW POLICY test_row_policy1 ON test.table1");
dropPolicy("DROP ROW POLICY test_row_policy2 ON test.table1");
}
Expand Down
Loading