Skip to content

Commit bc13433

Browse files
committed
[feature][dingo-calcite] Support cte
1 parent 0ac0384 commit bc13433

35 files changed

+1123
-30
lines changed

dingo-calcite/src/main/codegen/templates/Parser.jj

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3815,14 +3815,15 @@ SqlNodeList WithList() :
38153815
{
38163816
final Span s;
38173817
final List<SqlWithItem> list = new ArrayList<SqlWithItem>();
3818+
boolean recursive = false;
38183819
}
38193820
{
3820-
<WITH> { s = span(); }
3821-
AddWithItem(list) ( <COMMA> AddWithItem(list) )*
3821+
<WITH> [ <RECURSIVE> { recursive = true; } ] { s = span(); }
3822+
AddWithItem(list, SqlLiteral.createBoolean(recursive, getPos())) ( <COMMA> AddWithItem(list, SqlLiteral.createBoolean(recursive, getPos())) )*
38223823
{ return new SqlNodeList(list, s.end(this)); }
38233824
}
38243825

3825-
void AddWithItem(List<SqlWithItem> list) :
3826+
void AddWithItem(List<SqlWithItem> list, SqlLiteral recursive) :
38263827
{
38273828
final SqlIdentifier id;
38283829
final SqlNodeList columnList;
@@ -3833,7 +3834,7 @@ void AddWithItem(List<SqlWithItem> list) :
38333834
( columnList = ParenthesizedSimpleIdentifierList() | { columnList = null; } )
38343835
<AS>
38353836
definition = ParenthesizedExpression(ExprContext.ACCEPT_QUERY)
3836-
{ list.add(new SqlWithItem(id.getParserPosition(), id, columnList, definition)); }
3837+
{ list.add(new SqlWithItem(id.getParserPosition(), id, columnList, definition, recursive)); }
38373838
}
38383839

38393840
/**

dingo-calcite/src/main/java/io/dingodb/calcite/meta/DingoCostModelV1.java

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,9 @@ public static synchronized DingoCostModelV1 getCostModel() {
6161

6262
public static double getScanAvgRowSize(LogicalDingoTableScan tableScan) {
6363
DingoTable dingoTable = tableScan.getTable().unwrap(DingoTable.class);
64-
assert dingoTable != null;
64+
if (dingoTable == null) {
65+
return 0;
66+
}
6567
String schemaName = dingoTable.getNames().get(1);
6668
//List<Column> selectionCdList = getSelectionCdList(tableScan, dingoTable);
6769
return getAvgRowSize(

dingo-calcite/src/main/java/io/dingodb/calcite/rel/DingoRel.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@
2020
import io.dingodb.calcite.traits.DingoRelStreamingDef;
2121
import io.dingodb.calcite.visitor.DingoRelVisitor;
2222
import org.apache.calcite.plan.RelTraitSet;
23+
import org.apache.calcite.plan.volcano.RelSubset;
2324
import org.apache.calcite.rel.PhysicalNode;
2425
import org.apache.calcite.rel.RelNode;
2526
import org.apache.calcite.util.Pair;
@@ -31,6 +32,10 @@
3132

3233
public interface DingoRel extends PhysicalNode {
3334
static DingoRel dingo(RelNode rel) {
35+
if (rel instanceof RelSubset) {
36+
RelSubset relSubset = (RelSubset) rel;
37+
return (DingoRel) relSubset.getBest();
38+
}
3439
return (DingoRel) rel;
3540
}
3641

Lines changed: 47 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
/*
2+
* Copyright 2021 DataCanvas
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package io.dingodb.calcite.rel;
18+
19+
import io.dingodb.calcite.visitor.DingoRelVisitor;
20+
import org.apache.calcite.plan.RelOptCluster;
21+
import org.apache.calcite.plan.RelOptTable;
22+
import org.apache.calcite.plan.RelTraitSet;
23+
import org.apache.calcite.rel.RelNode;
24+
import org.apache.calcite.rel.core.RepeatUnion;
25+
import org.checkerframework.checker.nullness.qual.NonNull;
26+
import org.checkerframework.checker.nullness.qual.Nullable;
27+
28+
import java.util.List;
29+
30+
public class DingoRepeatUnion extends RepeatUnion implements DingoRel {
31+
public DingoRepeatUnion(
32+
RelOptCluster cluster, RelTraitSet traitSet, RelNode seed, RelNode iterative, boolean all,
33+
int iterationLimit, @Nullable RelOptTable transientTable) {
34+
super(cluster, traitSet, seed, iterative, all, iterationLimit, transientTable);
35+
}
36+
37+
@Override
38+
public RelNode copy(RelTraitSet traitSet, List<RelNode> inputs) {
39+
return new DingoRepeatUnion(getCluster(), traitSet,
40+
getSeedRel(), getIterativeRel(), all, iterationLimit, transientTable);
41+
}
42+
43+
@Override
44+
public <T> T accept(@NonNull DingoRelVisitor<T> visitor) {
45+
return visitor.visit(this);
46+
}
47+
}
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
/*
2+
* Copyright 2021 DataCanvas
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package io.dingodb.calcite.rel;
18+
19+
import io.dingodb.calcite.traits.DingoConvention;
20+
import io.dingodb.calcite.visitor.DingoRelVisitor;
21+
import io.dingodb.calcite.visitor.function.DingoTableSpoolVisitFun;
22+
import lombok.Getter;
23+
import org.apache.calcite.plan.RelOptCluster;
24+
import org.apache.calcite.plan.RelOptTable;
25+
import org.apache.calcite.plan.RelTraitSet;
26+
import org.apache.calcite.rel.RelCollationTraitDef;
27+
import org.apache.calcite.rel.RelDistributionTraitDef;
28+
import org.apache.calcite.rel.RelNode;
29+
import org.apache.calcite.rel.core.Spool;
30+
import org.apache.calcite.rel.core.TableSpool;
31+
import org.apache.calcite.rel.metadata.RelMetadataQuery;
32+
import org.apache.calcite.schema.impl.ListTransientTable;
33+
import org.checkerframework.checker.nullness.qual.NonNull;
34+
35+
public class DingoTableSpool extends TableSpool implements DingoRel {
36+
@Getter
37+
private ListTransientTable listTransientTable;
38+
39+
public DingoTableSpool(
40+
RelOptCluster cluster, RelTraitSet traitSet, RelNode input, Type readType,
41+
Type writeType, RelOptTable table, ListTransientTable listTransientTable
42+
) {
43+
super(cluster, traitSet, input, readType, writeType, table);
44+
this.listTransientTable = listTransientTable;
45+
}
46+
47+
public static DingoTableSpool create(RelNode input, Type readType,
48+
Type writeType, RelOptTable table) {
49+
RelOptCluster cluster = input.getCluster();
50+
RelMetadataQuery mq = cluster.getMetadataQuery();
51+
RelTraitSet traitSet = cluster.traitSetOf(DingoConvention.INSTANCE)
52+
.replaceIfs(RelCollationTraitDef.INSTANCE,
53+
() -> mq.collations(input))
54+
.replaceIf(RelDistributionTraitDef.INSTANCE,
55+
() -> mq.distribution(input));
56+
ListTransientTable tmp = table.unwrap(ListTransientTable.class);
57+
return new DingoTableSpool(cluster, traitSet, input, readType, writeType, table, tmp);
58+
}
59+
60+
@Override
61+
public <T> T accept(@NonNull DingoRelVisitor<T> visitor) {
62+
return visitor.visit(this);
63+
}
64+
65+
@Override
66+
protected Spool copy(RelTraitSet relTraitSet, RelNode relNode, Type type, Type type1) {
67+
return null;
68+
}
69+
}
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
/*
2+
* Copyright 2021 DataCanvas
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package io.dingodb.calcite.rel;
18+
19+
import io.dingodb.calcite.visitor.DingoRelVisitor;
20+
import io.dingodb.common.type.TupleMapping;
21+
import lombok.Getter;
22+
import org.apache.calcite.plan.RelOptCluster;
23+
import org.apache.calcite.plan.RelOptTable;
24+
import org.apache.calcite.plan.RelTraitSet;
25+
import org.apache.calcite.rel.hint.RelHint;
26+
import org.apache.calcite.rex.RexNode;
27+
import org.apache.calcite.schema.impl.ListTransientTable;
28+
import org.checkerframework.checker.nullness.qual.NonNull;
29+
import org.checkerframework.checker.nullness.qual.Nullable;
30+
31+
import java.util.List;
32+
33+
public class DingoTransientTableScan extends LogicalDingoTableScan implements DingoRel {
34+
@Getter
35+
ListTransientTable transientTable;
36+
37+
public DingoTransientTableScan(
38+
RelOptCluster cluster, RelTraitSet traitSet, List<RelHint> hints, RelOptTable table,
39+
@Nullable RexNode filter, @Nullable TupleMapping selection, ListTransientTable transientTable
40+
) {
41+
super(cluster, traitSet, hints, table, filter, selection);
42+
this.transientTable = transientTable;
43+
}
44+
45+
@Override
46+
public <T> T accept(@NonNull DingoRelVisitor<T> visitor) {
47+
return visitor.visit(this);
48+
}
49+
}

dingo-calcite/src/main/java/io/dingodb/calcite/rel/LogicalDingoTableScan.java

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -124,11 +124,10 @@ public LogicalDingoTableScan(
124124
this.groupSets = groupSets;
125125
this.pushDown = pushDown;
126126
DingoTable dingoTable = table.unwrap(DingoTable.class);
127-
assert dingoTable != null;
128127
this.realSelection = selection;
129128
this.forDml = forDml;
130129
// If the columns of the table contain hide and delete, the data shows that they need to be deleted
131-
if (selection != null) {
130+
if (selection != null && dingoTable != null) {
132131
int fieldCount = dingoTable.getTable().getColumns().size();
133132
if (forDml) {
134133
int[] mappingTmp = selection.getMappings();
@@ -149,7 +148,7 @@ public LogicalDingoTableScan(
149148
}
150149
this.selection = TupleMapping.of(mappingList);
151150
}
152-
} else {
151+
} else if (dingoTable != null) {
153152
List<Integer> mapping = dingoTable.getTable()
154153
.getColumns()
155154
.stream()

dingo-calcite/src/main/java/io/dingodb/calcite/rule/DingoRules.java

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,8 @@
1818

1919
import com.google.common.collect.ImmutableList;
2020
import io.dingodb.calcite.rule.dingo.DingoPhysicalRules;
21+
import io.dingodb.calcite.rule.dingo.DingoRepeatUnionRule;
2122
import io.dingodb.calcite.rule.dingo.DingoWindowRule;
22-
import org.apache.calcite.config.CalciteSystemProperty;
2323
import org.apache.calcite.plan.RelOptRule;
2424
import org.apache.calcite.plan.volcano.AbstractConverter;
2525
import org.apache.calcite.rel.core.Correlate;
@@ -202,18 +202,23 @@ public final class DingoRules {
202202
public static final DingoWindowRule DINGO_WINDOW_RULE =
203203
DingoWindowRule.DEFAULT.toRule(DingoWindowRule.class);
204204

205+
public static final DingoRepeatUnionRule DINGO_REPEAT_UNION_RULE =
206+
DingoRepeatUnionRule.DEFAULT.toRule(DingoRepeatUnionRule.class);
207+
208+
public static final DingoTableSpoolRule DINGO_TABLE_SPOOL_RULE = DingoTableSpoolRule.DEFAULT_CONFIG
209+
.toRule(DingoTableSpoolRule.class);
210+
211+
public static final DingoTableScanForSpoolRule DINGO_TABLE_SCAN_FOR_SPOOL_RULE
212+
= DingoTableScanForSpoolRule.DEFAULT.toRule(DingoTableScanForSpoolRule.class);
213+
205214
public static final List<RelOptRule> BASE_RULES = ImmutableList.of(
206215
CoreRules.AGGREGATE_STAR_TABLE,
207216
CoreRules.AGGREGATE_PROJECT_STAR_TABLE,
208-
CalciteSystemProperty.COMMUTE.value()
209-
? CoreRules.JOIN_ASSOCIATE
210-
: CoreRules.PROJECT_MERGE,
211217
CoreRules.FILTER_SCAN,
212218
CoreRules.PROJECT_FILTER_TRANSPOSE,
213219
CoreRules.FILTER_PROJECT_TRANSPOSE,
214220
CoreRules.FILTER_INTO_JOIN,
215221
CoreRules.JOIN_PUSH_EXPRESSIONS,
216-
CoreRules.AGGREGATE_EXPAND_DISTINCT_AGGREGATES,
217222
CoreRules.AGGREGATE_EXPAND_WITHIN_DISTINCT,
218223
CoreRules.AGGREGATE_CASE_TO_FILTER,
219224
CoreRules.AGGREGATE_REDUCE_FUNCTIONS,
@@ -238,7 +243,7 @@ public final class DingoRules {
238243
CoreRules.PROJECT_TO_SEMI_JOIN,
239244
CoreRules.JOIN_ON_UNIQUE_TO_SEMI_JOIN,
240245
CoreRules.JOIN_TO_SEMI_JOIN,
241-
CoreRules.AGGREGATE_REMOVE,
246+
//CoreRules.AGGREGATE_REMOVE,
242247
CoreRules.UNION_TO_DISTINCT,
243248
CoreRules.PROJECT_REMOVE,
244249
CoreRules.PROJECT_AGGREGATE_MERGE,
@@ -337,7 +342,10 @@ public final class DingoRules {
337342
DINGO_DOCUMENT_PROJECT_RULE,
338343
DINGO_DOCUMENT_FILTER_RULE,
339344
DOCUMENT_INDEX_RANGE_SCAN_RULE,
340-
DINGO_WINDOW_RULE
345+
DINGO_WINDOW_RULE,
346+
DINGO_REPEAT_UNION_RULE,
347+
DINGO_TABLE_SPOOL_RULE,
348+
DINGO_TABLE_SCAN_FOR_SPOOL_RULE
341349
);
342350

343351
private DingoRules() {
Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
/*
2+
* Copyright 2021 DataCanvas
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package io.dingodb.calcite.rule;
18+
19+
import io.dingodb.calcite.DingoTable;
20+
import io.dingodb.calcite.rel.DingoInfoSchemaScan;
21+
import io.dingodb.calcite.rel.DingoTableScan;
22+
import io.dingodb.calcite.rel.DingoTransientTableScan;
23+
import io.dingodb.calcite.traits.DingoConvention;
24+
import io.dingodb.calcite.traits.DingoRelStreaming;
25+
import org.apache.calcite.plan.Convention;
26+
import org.apache.calcite.plan.RelTraitSet;
27+
import org.apache.calcite.rel.RelNode;
28+
import org.apache.calcite.rel.convert.ConverterRule;
29+
import org.apache.calcite.rel.logical.LogicalTableScan;
30+
import org.apache.calcite.schema.impl.ListTransientTable;
31+
import org.checkerframework.checker.nullness.qual.Nullable;
32+
33+
import java.util.List;
34+
35+
public class DingoTableScanForSpoolRule extends ConverterRule {
36+
public static final Config DEFAULT = Config.INSTANCE
37+
.withConversion(
38+
LogicalTableScan.class,
39+
Convention.NONE,
40+
DingoConvention.INSTANCE,
41+
"DingoTableScanForSpoolRule"
42+
)
43+
.withRuleFactory(DingoTableScanForSpoolRule::new);
44+
45+
public DingoTableScanForSpoolRule(Config config) {
46+
super(config);
47+
}
48+
49+
@Override
50+
public @Nullable RelNode convert(RelNode relNode) {
51+
LogicalTableScan scan = (LogicalTableScan) relNode;
52+
RelTraitSet traits = scan.getTraitSet()
53+
.replace(DingoConvention.INSTANCE)
54+
.replace(DingoRelStreaming.of(scan.getTable()));
55+
List<String> fullNameList = scan.getTable().getQualifiedName();
56+
if (fullNameList.size() >= 2 && DingoTableScanRule.metaSchemaSet.contains(fullNameList.get(1))) {
57+
DingoTable dingoTable = scan.getTable().unwrap(DingoTable.class);
58+
if (dingoTable != null && "SYSTEM VIEW".equals(dingoTable.getTable().getTableType())) {
59+
return new DingoInfoSchemaScan(
60+
scan.getCluster(),
61+
traits,
62+
scan.getHints(),
63+
scan.getTable(),
64+
null,
65+
null
66+
);
67+
}
68+
}
69+
ListTransientTable transientTable = scan.getTable().unwrap(ListTransientTable.class);
70+
if (transientTable != null) {
71+
return new DingoTransientTableScan(scan.getCluster(), traits, scan.getHints(),
72+
scan.getTable(), null, null, transientTable);
73+
}
74+
return new DingoTableScan(
75+
scan.getCluster(),
76+
traits,
77+
scan.getHints(),
78+
scan.getTable(),
79+
null,
80+
null, // selection
81+
null,
82+
null,
83+
null,
84+
false,
85+
false
86+
);
87+
}
88+
}

0 commit comments

Comments
 (0)