Skip to content
Closed
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 @@ -554,31 +554,23 @@ private Object toJson(RexNode node) {
final RexCall call = (RexCall) node;
map = jsonBuilder().map();
map.put("op", toJson(call.getOperator()));
map.put("type", toJson(call.getType()));
final List<@Nullable Object> list = jsonBuilder().list();
for (RexNode operand : call.getOperands()) {
list.add(toJson(operand));
}
map.put("operands", list);
switch (node.getKind()) {
case CAST:
map.put("type", toJson(node.getType()));
break;
default:
break;
}
if (call.getOperator() instanceof SqlFunction) {
if (((SqlFunction) call.getOperator()).getFunctionType().isUserDefined()) {
SqlOperator op = call.getOperator();
map.put("class", op.getClass().getName());
map.put("type", toJson(node.getType()));
map.put("deterministic", op.isDeterministic());
map.put("dynamic", op.isDynamicFunction());
}
}
if (call instanceof RexOver) {
RexOver over = (RexOver) call;
map.put("distinct", over.isDistinct());
map.put("type", toJson(node.getType()));
map.put("window", toJson(over.getWindow()));
}
return map;
Expand Down
59 changes: 50 additions & 9 deletions core/src/test/java/org/apache/calcite/plan/RelWriterTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,10 @@ class RelWriterTest {
+ " \"kind\": \"EQUALS\",\n"
+ " \"syntax\": \"BINARY\"\n"
+ " },\n"
+ " \"type\": {\n"
+ " \"type\": \"BOOLEAN\",\n"
+ " \"nullable\": false\n"
+ " },\n"
+ " \"operands\": [\n"
+ " {\n"
+ " \"input\": 1,\n"
Expand Down Expand Up @@ -288,17 +292,17 @@ class RelWriterTest {
+ " \"kind\": \"COUNT\",\n"
+ " \"syntax\": \"FUNCTION_STAR\"\n"
+ " },\n"
+ " \"type\": {\n"
+ " \"type\": \"BIGINT\",\n"
+ " \"nullable\": false\n"
+ " },\n"
+ " \"operands\": [\n"
+ " {\n"
+ " \"input\": 0,\n"
+ " \"name\": \"$0\"\n"
+ " }\n"
+ " ],\n"
+ " \"distinct\": false,\n"
+ " \"type\": {\n"
+ " \"type\": \"BIGINT\",\n"
+ " \"nullable\": false\n"
+ " },\n"
+ " \"window\": {\n"
+ " \"partition\": [\n"
+ " {\n"
Expand Down Expand Up @@ -330,17 +334,17 @@ class RelWriterTest {
+ " \"kind\": \"SUM\",\n"
+ " \"syntax\": \"FUNCTION\"\n"
+ " },\n"
+ " \"type\": {\n"
+ " \"type\": \"BIGINT\",\n"
+ " \"nullable\": false\n"
+ " },\n"
+ " \"operands\": [\n"
+ " {\n"
+ " \"input\": 0,\n"
+ " \"name\": \"$0\"\n"
+ " }\n"
+ " ],\n"
+ " \"distinct\": false,\n"
+ " \"type\": {\n"
+ " \"type\": \"BIGINT\",\n"
+ " \"nullable\": false\n"
+ " },\n"
+ " \"window\": {\n"
+ " \"partition\": [\n"
+ " {\n"
Expand Down Expand Up @@ -779,7 +783,8 @@ private void assertThatReadExpressionResult(String json, Matcher<String> matcher
throw TestUtil.rethrow(e);
}
final RelJson relJson = RelJson.create()
.withInputTranslator(RelWriterTest::translateInput);
.withInputTranslator(RelWriterTest::translateInput)
.withLibraryOperatorTable();
final RexNode e = relJson.toRex(cluster, o);
assertThat(e.toString(), is(matcher));
}
Expand Down Expand Up @@ -945,6 +950,42 @@ void testAggregateWithAlias(SqlExplainFormat format) {
assertThat(result, isLinux(expected));
}

/** Test case for
* <a href="https://issues.apache.org/jira/browse/CALCITE-5607">[CALCITE-5607]</a>
* <p>Before the fix, RelJson.toRex would throw an ArrayIndexOutOfBounds error
* when deserialization.
* */
@Test void testDeserializeMinusDateOperator() {
final FrameworkConfig config = RelBuilderTest.config().build();
final RelBuilder builder = RelBuilder.create(config);
final RexBuilder rb = builder.getRexBuilder();
final RelDataTypeFactory typeFactory = rb.getTypeFactory();
final SqlIntervalQualifier qualifier =
new SqlIntervalQualifier(TimeUnit.MONTH, null, SqlParserPos.ZERO);
final RexNode op1 = rb.makeTimestampLiteral(new TimestampString("2012-12-03 12:34:44"), 0);
final RexNode op2 = rb.makeTimestampLiteral(new TimestampString("2014-12-23 12:34:44"), 0);
final RelDataType intervalType =
typeFactory.createTypeWithNullability(
typeFactory.createSqlIntervalType(qualifier),
op1.getType().isNullable() || op2.getType().isNullable());
final RelNode rel = builder
.scan("EMP")
.project(builder.field("JOB"),
rb.makeCall(intervalType,
SqlStdOperatorTable.MINUS_DATE,
ImmutableList.of(op2, op1))
).build();
final RelJsonWriter jsonWriter =
new RelJsonWriter(new JsonBuilder(), RelJson::withLibraryOperatorTable);
rel.explain(jsonWriter);
String relJson = jsonWriter.asString();
String result = deserializeAndDumpToTextFormat(getSchema(rel), relJson);
final String expected =
"LogicalProject(JOB=[$2], $f1=[-(2014-12-23 12:34:44, 2012-12-03 12:34:44)])\n"
+ " LogicalTableScan(table=[[scott, EMP]])\n";
assertThat(result, isLinux(expected));
}

@Test void testAggregateWithoutAlias() {
final FrameworkConfig config = RelBuilderTest.config().build();
final RelBuilder builder = RelBuilder.create(config);
Expand Down