Skip to content

Commit

Permalink
[CALCITE-6213] The default behavior of NullCollation in Presto is LAST
Browse files Browse the repository at this point in the history
  • Loading branch information
YiwenWu authored and macroguo-ghy committed Jan 24, 2024
1 parent 0a0fd87 commit aca7f02
Show file tree
Hide file tree
Showing 3 changed files with 99 additions and 5 deletions.
2 changes: 1 addition & 1 deletion core/src/main/java/org/apache/calcite/sql/SqlDialect.java
Original file line number Diff line number Diff line change
Expand Up @@ -1351,7 +1351,7 @@ public enum DatabaseProduct {
INTERBASE("Interbase", null, NullCollation.HIGH),
PHOENIX("Phoenix", "\"", NullCollation.HIGH),
POSTGRESQL("PostgreSQL", "\"", NullCollation.HIGH),
PRESTO("Presto", "\"", NullCollation.LOW),
PRESTO("Presto", "\"", NullCollation.LAST),
NETEZZA("Netezza", "\"", NullCollation.HIGH),
INFOBRIGHT("Infobright", "`", NullCollation.HIGH),
NEOVIEW("Neoview", null, NullCollation.HIGH),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ public class PrestoSqlDialect extends SqlDialect {
.withDatabaseProduct(DatabaseProduct.PRESTO)
.withIdentifierQuoteString("\"")
.withUnquotedCasing(Casing.UNCHANGED)
.withNullCollation(NullCollation.LOW);
.withNullCollation(NullCollation.LAST);

public static final SqlDialect DEFAULT = new PrestoSqlDialect(DEFAULT_CONTEXT);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -973,8 +973,7 @@ private static String toSql(RelNode root, SqlDialect dialect,
final String expectedPresto = "SELECT \"product_class_id\", COUNT(*) AS \"C\"\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "GROUP BY ROLLUP(\"product_class_id\")\n"
+ "ORDER BY \"product_class_id\" IS NULL, \"product_class_id\", "
+ "COUNT(*) IS NULL, 2";
+ "ORDER BY \"product_class_id\", 2";
sql(query)
.ok(expected)
.withMysql().ok(expectedMysql)
Expand Down Expand Up @@ -2081,7 +2080,7 @@ private SqlDialect nonOrdinalDialect() {
final String prestoExpected = "SELECT \"product_id\", COUNT(*) AS \"c\"\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "GROUP BY \"product_id\"\n"
+ "ORDER BY COUNT(*) IS NULL, 2";
+ "ORDER BY 2";
sql(query)
.ok(ordinalExpected)
.dialect(nonOrdinalDialect())
Expand Down Expand Up @@ -7726,6 +7725,101 @@ private void checkLiteral2(String expression, String expected) {
sql(query).withSpark().withLibrary(SqlLibrary.SPARK).ok(expectedSql);
}

/** Test case for
* <a href="https://issues.apache.org/jira/browse/CALCITE-6213">[CALCITE-6213]
* The default behavior of NullCollation in Presto is LAST </a>.
*/
@Test void testNullCollation() {
final String query = "select * from \"product\" order by \"brand_name\"";
final String expected = "SELECT *\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "ORDER BY \"brand_name\"";
final String sparkExpected = "SELECT *\n"
+ "FROM foodmart.product\n"
+ "ORDER BY brand_name NULLS LAST";
sql(query)
.withPresto().ok(expected)
.withSpark().ok(sparkExpected);
}

@Test void testNullCollationAsc() {
final String query = "select * from \"product\" order by \"brand_name\" asc";
final String expected = "SELECT *\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "ORDER BY \"brand_name\"";
final String sparkExpected = "SELECT *\n"
+ "FROM foodmart.product\n"
+ "ORDER BY brand_name NULLS LAST";
sql(query)
.withPresto().ok(expected)
.withSpark().ok(sparkExpected);
}

@Test void testNullCollationAscNullLast() {
final String query = "select * from \"product\" order by \"brand_name\" asc nulls last";
final String expected = "SELECT *\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "ORDER BY \"brand_name\"";
final String sparkExpected = "SELECT *\n"
+ "FROM foodmart.product\n"
+ "ORDER BY brand_name NULLS LAST";
sql(query)
.withPresto().ok(expected)
.withSpark().ok(sparkExpected);
}

@Test void testNullCollationAscNullFirst() {
final String query = "select * from \"product\" order by \"brand_name\" asc nulls first";
final String expected = "SELECT *\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "ORDER BY \"brand_name\" IS NULL DESC, \"brand_name\"";
final String sparkExpected = "SELECT *\n"
+ "FROM foodmart.product\n"
+ "ORDER BY brand_name";
sql(query)
.withPresto().ok(expected)
.withSpark().ok(sparkExpected);
}

@Test void testNullCollationDesc() {
final String query = "select * from \"product\" order by \"brand_name\" desc";
final String expected = "SELECT *\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "ORDER BY \"brand_name\" IS NULL DESC, \"brand_name\" DESC";
final String sparkExpected = "SELECT *\n"
+ "FROM foodmart.product\n"
+ "ORDER BY brand_name DESC NULLS FIRST";
sql(query)
.withPresto().ok(expected)
.withSpark().ok(sparkExpected);
}

@Test void testNullCollationDescLast() {
final String query = "select * from \"product\" order by \"brand_name\" desc nulls last";
final String expected = "SELECT *\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "ORDER BY \"brand_name\" DESC";
final String sparkExpected = "SELECT *\n"
+ "FROM foodmart.product\n"
+ "ORDER BY brand_name DESC";
sql(query)
.withPresto().ok(expected)
.withSpark().ok(sparkExpected);
}

@Test void testNullCollationDescFirst() {
final String query = "select * from \"product\" order by \"brand_name\" desc nulls first";
final String expected = "SELECT *\n"
+ "FROM \"foodmart\".\"product\"\n"
+ "ORDER BY \"brand_name\" IS NULL DESC, \"brand_name\" DESC";
final String sparkExpected = "SELECT *\n"
+ "FROM foodmart.product\n"
+ "ORDER BY brand_name DESC NULLS FIRST";
sql(query)
.withPresto().ok(expected)
.withSpark().ok(sparkExpected);
}

/** Fluid interface to run tests. */
static class Sql {
private final CalciteAssert.SchemaSpec schemaSpec;
Expand Down

0 comments on commit aca7f02

Please sign in to comment.