[ https://issues.apache.org/jira/browse/CALCITE-4401?page=com.atlassian.jira.plugin.system.issuetabpanels:all-tabpanel ]
ASF GitHub Bot updated CALCITE-4401: ------------------------------------ Labels: pull-request-available (was: ) > SqlJoin toString throws RuntimeException > ---------------------------------------- > > Key: CALCITE-4401 > URL: https://issues.apache.org/jira/browse/CALCITE-4401 > Project: Calcite > Issue Type: Bug > Components: core > Affects Versions: 1.25.0, 1.26.0 > Reporter: Dominik Labuda > Assignee: Abhishek Dasgupta > Priority: Minor > Labels: pull-request-available > Fix For: 1.31.0 > > Time Spent: 10m > Remaining Estimate: 0h > > Hi, > In our project we use Kotlin along with [Strikt assertion > library|https://strikt.io/] in tests. The thing is that Strikt calls > `.toString()` method on failing asserted objects to provide users with a > nicely formatted output. > Lets say the test looks like this: > {code:java} > @Test > fun `test correct type of JOIN in the root of generated SQL without > neighboring JOINs`() { > // Generates SqlSelect that fails one of the conditions below > val rootSelect: SqlSelect = generateRootSql() > > expectThat(rootSelect.from) { > // Passes - from is a SqlJoin > val join = isA<SqlJoin>() > // Passes - joinType is FULL > join.get { joinType }.isEqualTo(JoinType.FULL) > // Fails - left is a SqlJoin, calls .toString() on > rootSelect.from to provide output info > join.get { left }.isNotA<SqlJoin>() > join.get { right }.isNotA<SqlJoin>() > } > } > {code} > This can be inherently reduced to this example: > {code:java} > fun main() { > val frameworkConfig = initSchema() > val relBuilder: RelBuilder = RelBuilder.create(frameworkConfig) > val rootRelationalNode = relBuilder > .scan("tpch", "out_tpch_vw__customer") > .project( > relBuilder.field("c_custkey"), > relBuilder.field("region_name") > ) > .scan("tpch", "out_tpch_vw__orders") > .project( > relBuilder.field("o_custkey"), > relBuilder.field("o_totalprice") > ) > .join( > JoinRelType.INNER, > relBuilder.call( > SqlStdOperatorTable.EQUALS, > relBuilder.field(2, 0, "c_custkey"), > relBuilder.field(2, 1, "o_custkey") > ) > ) > .build() > val sqlNode = RelToSqlConverter(PostgresqlSqlDialect.DEFAULT) > .visitRoot(rootRelationalNode) > .asStatement() > println("SQL:") > println(sqlNode) > println() > println("sqlNode root is SqlSelect: ${sqlNode is SqlSelect}") > // Treat sqlNode as SqlSelect > sqlNode as SqlSelect > println("sqlNode.from field is a SqlJoin: ${sqlNode.from is SqlJoin}") > println("Printing out the SqlJoin: ${sqlNode.from}") > } > {code} > Which results in: > {code:java} > SQL: > SELECT * > FROM (SELECT `c_custkey`, `region_name` > FROM `tpch`.`out_tpch_vw__customer`) AS `t` > INNER JOIN (SELECT `o_custkey`, `o_totalprice` > FROM `tpch`.`out_tpch_vw__orders`) AS `t0` ON `t`.`c_custkey` = > `t0`.`o_custkey` > sqlNode root is SqlSelect: true > sqlNode.from field is a SqlJoin: true > Exception in thread "main" java.lang.RuntimeException: No list started > at > org.apache.calcite.sql.pretty.SqlPrettyWriter.sep(SqlPrettyWriter.java:1079) > at > org.apache.calcite.sql.pretty.SqlPrettyWriter.sep(SqlPrettyWriter.java:1074) > at org.apache.calcite.sql.SqlJoin$SqlJoinOperator.unparse(SqlJoin.java:214) > at org.apache.calcite.sql.SqlDialect.unparseCall(SqlDialect.java:453) > at org.apache.calcite.sql.SqlCall.unparse(SqlCall.java:104) > at org.apache.calcite.sql.SqlNode.toSqlString(SqlNode.java:154) > at org.apache.calcite.sql.SqlNode.toString(SqlNode.java:129) > at java.base/java.lang.String.valueOf(String.java:2951) > at java.base/java.lang.StringBuilder.append(StringBuilder.java:168) > ...{code} > -- This message was sent by Atlassian Jira (v8.20.1#820001)