You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@calcite.apache.org by "Leonid Chistov (Jira)" <ji...@apache.org> on 2022/11/28 14:07:00 UTC
[jira] [Created] (CALCITE-5402) RelToSql generates invalid code if left and right side field names clash
Leonid Chistov created CALCITE-5402:
---------------------------------------
Summary: RelToSql generates invalid code if left and right side field names clash
Key: CALCITE-5402
URL: https://issues.apache.org/jira/browse/CALCITE-5402
Project: Calcite
Issue Type: Bug
Affects Versions: 1.32.0
Reporter: Leonid Chistov
Wrong SQL code is generated when left and right side of a semi-join have fields with same name.
Generated condition looks like `FIELD` = `rhs table`.`FIELD`, where left `FIELD` is resolved to be the same as `rhs table`.`FIELD` during query execution, but not a reference to an outer table of correlated subquery, as was intended.
Examples of tests that would fail if added to RelToSqlConverterTest.java:
{code:java}
@Test void testSemiJoinNameClash() {
final RelBuilder builder = relBuilder();
final RelNode root = builder
.scan("DEPT")
.project(builder.field("DEPTNO"), builder.field("DNAME"))
.scan("EMP")
.filter(
builder.call(SqlStdOperatorTable.GREATER_THAN,
builder.field("JOB"),
builder.literal((short) 10)))
.project(builder.field("DEPTNO"))
.join(
JoinRelType.SEMI, builder.equals(
builder.field(2, 0, "DEPTNO"),
builder.field(2, 1, "DEPTNO")))
.project(builder.field("DEPTNO"))
.build();
final String expectedSql = "SELECT \"DEPTNO\"\n"
+ "FROM (SELECT \"DEPTNO\", \"EMPNO\"\n"
+ "FROM \"scott\".\"EMP\"\n"
+ "WHERE EXISTS (SELECT 1\n"
+ "FROM (SELECT \"EMPNO\"\n"
+ "FROM \"scott\".\"EMP\"\n"
+ "WHERE \"JOB\" > 10) AS \"t1\"\n"
+ "WHERE \"EMP\".\"EMPNO\" = \"t1\".\"EMPNO\")) AS \"t\"";
assertThat(toSql(root), isLinux(expectedSql));
} {code}
{code:java}
@Test void testSemiJoinWithSameTable() {
final RelBuilder builder = relBuilder();
final RelNode root = builder
.scan("EMP")
.project(builder.field("DEPTNO"), builder.field("EMPNO"))
.scan("EMP")
.filter(
builder.call(SqlStdOperatorTable.GREATER_THAN,
builder.field("JOB"),
builder.literal((short) 10)))
.project(builder.field("EMPNO"))
.join(
JoinRelType.SEMI, builder.equals(
builder.field(2, 0, "EMPNO"),
builder.field(2, 1, "EMPNO")))
.project(builder.field("DEPTNO"))
.build();
final String expectedSql = "SELECT \"DEPTNO\"\n"
+ "FROM (SELECT \"DEPTNO\", \"EMPNO\"\n"
+ "FROM \"scott\".\"EMP\"\n"
+ "WHERE EXISTS (SELECT 1\n"
+ "FROM (SELECT \"EMPNO\"\n"
+ "FROM \"scott\".\"EMP\"\n"
+ "WHERE \"JOB\" > 10) AS \"t1\"\n"
+ "WHERE \"EMP\".\"EMPNO\" = \"t1\".\"EMPNO\")) AS \"t\"";
assertThat(toSql(root), isLinux(expectedSql));
} {code}
--
This message was sent by Atlassian Jira
(v8.20.10#820010)