Skip to content

Commit

Permalink
[CALCITE-5265] JDBC adapter sometimes adds unnecessary parentheses ar…
Browse files Browse the repository at this point in the history
…ound SELECT in INSERT

This closes apache#2910
  • Loading branch information
l4wei authored and libenchao committed Sep 29, 2022
1 parent 9e59a13 commit b16df01
Show file tree
Hide file tree
Showing 4 changed files with 69 additions and 30 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -396,6 +396,7 @@ public void setWindowDeclListNewline(boolean windowDeclListNewline) {

@Override public boolean inQuery() {
return (frame == null)
|| (frame.frameType == FrameTypeEnum.SELECT)
|| (frame.frameType == FrameTypeEnum.ORDER_BY)
|| (frame.frameType == FrameTypeEnum.WITH)
|| (frame.frameType == FrameTypeEnum.SETOP);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6160,7 +6160,7 @@ private void checkLiteral2(String expression, String expected) {
final String expected = "INSERT INTO \"foodmart\".\"account\" ("
+ "\"account_id\", \"account_parent\", \"account_description\", "
+ "\"account_type\", \"account_rollup\", \"Custom_Members\")\n"
+ "(SELECT \"EXPR$0\" AS \"account_id\","
+ "SELECT \"EXPR$0\" AS \"account_id\","
+ " \"EXPR$1\" AS \"account_parent\","
+ " CAST(NULL AS VARCHAR(30) CHARACTER SET \"ISO-8859-1\") "
+ "AS \"account_description\","
Expand All @@ -6169,7 +6169,7 @@ private void checkLiteral2(String expression, String expected) {
+ " CAST(NULL AS VARCHAR(255) CHARACTER SET \"ISO-8859-1\") "
+ "AS \"Custom_Members\"\n"
+ "FROM (VALUES (1, NULL, '123', '123')) "
+ "AS \"t\" (\"EXPR$0\", \"EXPR$1\", \"EXPR$2\", \"EXPR$3\"))";
+ "AS \"t\" (\"EXPR$0\", \"EXPR$1\", \"EXPR$2\", \"EXPR$3\")";
sql(query).ok(expected);
// validate
sql(expected).exec();
Expand All @@ -6189,7 +6189,7 @@ private void checkLiteral2(String expression, String expected) {
final String expected = "INSERT INTO \"foodmart\".\"account\" "
+ "(\"account_id\", \"account_parent\", \"account_description\", "
+ "\"account_type\", \"account_rollup\", \"Custom_Members\")\n"
+ "(SELECT \"product\".\"product_id\" AS \"account_id\", "
+ "SELECT \"product\".\"product_id\" AS \"account_id\", "
+ "CAST(NULL AS INTEGER) AS \"account_parent\", CAST(NULL AS VARCHAR"
+ "(30) CHARACTER SET \"ISO-8859-1\") AS \"account_description\", "
+ "CAST(\"product\".\"product_id\" AS VARCHAR CHARACTER SET "
Expand All @@ -6199,7 +6199,7 @@ private void checkLiteral2(String expression, String expected) {
+ "CAST(NULL AS VARCHAR(255) CHARACTER SET \"ISO-8859-1\") AS \"Custom_Members\"\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "INNER JOIN \"foodmart\".\"sales_fact_1997\" "
+ "ON \"product\".\"product_id\" = \"sales_fact_1997\".\"product_id\")";
+ "ON \"product\".\"product_id\" = \"sales_fact_1997\".\"product_id\"";
sql(query).ok(expected);
// validate
sql(expected).exec();
Expand Down Expand Up @@ -6367,6 +6367,44 @@ private void checkLiteral2(String expression, String expected) {
.withCalcite().ok(expectedCalciteX);
}

/** Test case for
* <a href="https://issues.apache.org/jira/browse/CALCITE-5265">[CALCITE-5265]
* JDBC adapter sometimes adds unnecessary parentheses around SELECT in INSERT</a>. */
@Test void testInsertSelect() {
final String sql = "insert into \"DEPT\" select * from \"DEPT\"";
final String expected = ""
+ "INSERT INTO \"SCOTT\".\"DEPT\" (\"DEPTNO\", \"DNAME\", \"LOC\")\n"
+ "SELECT *\n"
+ "FROM \"SCOTT\".\"DEPT\"";
sql(sql)
.schema(CalciteAssert.SchemaSpec.JDBC_SCOTT)
.ok(expected);
}

/** Test case for
* <a href="https://issues.apache.org/jira/browse/CALCITE-5265">[CALCITE-5265]
* JDBC adapter sometimes adds unnecessary parentheses around SELECT in INSERT</a>. */
@Test void testInsertUnionThenIntersect() {
final String sql = ""
+ "insert into \"DEPT\"\n"
+ "(select * from \"DEPT\" union select * from \"DEPT\")\n"
+ "intersect select * from \"DEPT\"";
final String expected = ""
+ "INSERT INTO \"SCOTT\".\"DEPT\" (\"DEPTNO\", \"DNAME\", \"LOC\")\n"
+ "SELECT *\n"
+ "FROM (SELECT *\n"
+ "FROM \"SCOTT\".\"DEPT\"\n"
+ "UNION\n"
+ "SELECT *\n"
+ "FROM \"SCOTT\".\"DEPT\")\n"
+ "INTERSECT\n"
+ "SELECT *\n"
+ "FROM \"SCOTT\".\"DEPT\"";
sql(sql)
.schema(CalciteAssert.SchemaSpec.JDBC_SCOTT)
.ok(expected);
}

@Test void testInsertValuesWithDynamicParams() {
final String sql = "insert into \"DEPT\" values (?,?,?), (?,?,?)";
final String expected = ""
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -982,11 +982,11 @@ private LockWrapper exclusiveCleanDb(Connection c) throws SQLException {
final String jdbcSql = "INSERT INTO \"foodmart\".\"expense_fact\""
+ " (\"store_id\", \"account_id\", \"exp_date\", \"time_id\","
+ " \"category_id\", \"currency_id\", \"amount\")\n"
+ "(SELECT \"store_id\", \"account_id\", \"exp_date\","
+ "SELECT \"store_id\", \"account_id\", \"exp_date\","
+ " \"time_id\" + 1 AS \"time_id\", \"category_id\","
+ " \"currency_id\", \"amount\"\n"
+ "FROM \"foodmart\".\"expense_fact\"\n"
+ "WHERE \"store_id\" = 666)";
+ "WHERE \"store_id\" = 666";
that.query(sql)
.explainContains(explain)
.planUpdateHasSql(jdbcSql, 1);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4410,8 +4410,8 @@ void checkPeriodPredicate(Checker checker) {

@Test void testInsertSelect() {
final String expected = "INSERT INTO `EMPS`\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
sql("insert into emps select * from emps")
.ok(expected)
.node(not(isDdl()));
Expand Down Expand Up @@ -4456,29 +4456,29 @@ void checkPeriodPredicate(Checker checker) {

@Test void testInsertColumnList() {
final String expected = "INSERT INTO `EMPS` (`X`, `Y`)\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
sql("insert into emps(x,y) select * from emps")
.ok(expected);
}

@Test void testInsertCaseSensitiveColumnList() {
final String expected = "INSERT INTO `emps` (`x`, `y`)\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
sql("insert into \"emps\"(\"x\",\"y\") select * from emps")
.ok(expected);
}

@Test void testInsertExtendedColumnList() {
String expected = "INSERT INTO `EMPS` EXTEND (`Z` BOOLEAN) (`X`, `Y`)\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
sql("insert into emps(z boolean)(x,y) select * from emps")
.ok(expected);
expected = "INSERT INTO `EMPS` EXTEND (`Z` BOOLEAN) (`X`, `Y`, `Z`)\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
sql("insert into emps(x, y, z boolean) select * from emps")
.withConformance(SqlConformanceEnum.LENIENT)
.ok(expected);
Expand Down Expand Up @@ -4515,13 +4515,13 @@ void checkPeriodPredicate(Checker checker) {

@Test void testInsertCaseSensitiveExtendedColumnList() {
String expected = "INSERT INTO `emps` EXTEND (`z` BOOLEAN) (`x`, `y`)\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
sql("insert into \"emps\"(\"z\" boolean)(\"x\",\"y\") select * from emps")
.ok(expected);
expected = "INSERT INTO `emps` EXTEND (`z` BOOLEAN) (`x`, `y`, `z`)\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
sql("insert into \"emps\"(\"x\", \"y\", \"z\" boolean) select * from emps")
.withConformance(SqlConformanceEnum.LENIENT)
.ok(expected);
Expand All @@ -4531,8 +4531,8 @@ void checkPeriodPredicate(Checker checker) {
final String expected = "EXPLAIN PLAN INCLUDING ATTRIBUTES"
+ " WITH IMPLEMENTATION FOR\n"
+ "INSERT INTO `EMPS1`\n"
+ "(SELECT *\n"
+ "FROM `EMPS2`)";
+ "SELECT *\n"
+ "FROM `EMPS2`";
sql("explain plan for insert into emps1 select * from emps2")
.ok(expected)
.node(not(isDdl()));
Expand All @@ -4552,8 +4552,8 @@ void checkPeriodPredicate(Checker checker) {
@Test void testUpsertSelect() {
final String sql = "upsert into emps select * from emp as e";
final String expected = "UPSERT INTO `EMPS`\n"
+ "(SELECT *\n"
+ "FROM `EMP` AS `E`)";
+ "SELECT *\n"
+ "FROM `EMP` AS `E`";
if (isReserved("UPSERT")) {
sql(sql).ok(expected);
}
Expand Down Expand Up @@ -6672,8 +6672,8 @@ public void subTestIntervalDayFailsValidation() {
}
});
final String str0 = "INSERT INTO `EMPS`\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
assertThat(str0, is(toLinux(sqlNodeVisited0.toString())));

final String sql1 = "insert into emps select empno from emps";
Expand All @@ -6685,8 +6685,8 @@ public void subTestIntervalDayFailsValidation() {
}
});
final String str1 = "INSERT INTO `EMPS`\n"
+ "(SELECT `EMPNO`\n"
+ "FROM `EMPS`)";
+ "SELECT `EMPNO`\n"
+ "FROM `EMPS`";
assertThat(str1, is(toLinux(sqlNodeVisited1.toString())));
}

Expand Down Expand Up @@ -10177,8 +10177,8 @@ protected void checkTimeUnitCodes(Map<String, TimeUnit> timeUnitCodes) {
+ "select * from emps";
final String expected = "INSERT INTO `EMPS`\n"
+ "/*+ `PROPERTIES`(`K1` = 'v1', `K2` = 'v2'), `INDEX`(`IDX0`, `IDX1`) */\n"
+ "(SELECT *\n"
+ "FROM `EMPS`)";
+ "SELECT *\n"
+ "FROM `EMPS`";
sql(sql).ok(expected);
}

Expand Down

0 comments on commit b16df01

Please sign in to comment.