diff --git a/core/src/main/java/org/apache/calcite/sql/fun/SqlLibraryOperators.java b/core/src/main/java/org/apache/calcite/sql/fun/SqlLibraryOperators.java index efff32c25d6f..9960c460a6be 100644 --- a/core/src/main/java/org/apache/calcite/sql/fun/SqlLibraryOperators.java +++ b/core/src/main/java/org/apache/calcite/sql/fun/SqlLibraryOperators.java @@ -982,12 +982,12 @@ static RelDataType deriveTypeSplit(SqlOperatorBinding operatorBinding, new SqlLikeOperator("NOT ILIKE", SqlKind.LIKE, true, false); /** The regex variant of the LIKE operator. */ - @LibraryOperator(libraries = {SPARK, HIVE}) + @LibraryOperator(libraries = {SPARK, HIVE, MYSQL}) public static final SqlSpecialOperator RLIKE = new SqlLikeOperator("RLIKE", SqlKind.RLIKE, false, true); /** The regex variant of the NOT LIKE operator. */ - @LibraryOperator(libraries = {SPARK, HIVE}) + @LibraryOperator(libraries = {SPARK, HIVE, MYSQL}) public static final SqlSpecialOperator NOT_RLIKE = new SqlLikeOperator("NOT RLIKE", SqlKind.RLIKE, true, true); diff --git a/core/src/test/java/org/apache/calcite/rel/rel2sql/RelToSqlConverterTest.java b/core/src/test/java/org/apache/calcite/rel/rel2sql/RelToSqlConverterTest.java index 1add2c2aa636..16c1011e0d9c 100644 --- a/core/src/test/java/org/apache/calcite/rel/rel2sql/RelToSqlConverterTest.java +++ b/core/src/test/java/org/apache/calcite/rel/rel2sql/RelToSqlConverterTest.java @@ -5160,9 +5160,13 @@ private void checkLiteral2(String expression, String expected) { String expectedHive = "SELECT \"product_name\"\n" + "FROM \"foodmart\".\"product\"\n" + "WHERE \"product_name\" RLIKE '.+@.+\\\\..+'"; + String expectedMysql = "SELECT \"product_name\"\n" + + "FROM \"foodmart\".\"product\"\n" + + "WHERE \"product_name\" RLIKE '.+@.+\\\\..+'"; sql(query) .withLibrary(SqlLibrary.SPARK).ok(expectedSpark) - .withLibrary(SqlLibrary.HIVE).ok(expectedHive); + .withLibrary(SqlLibrary.HIVE).ok(expectedHive) + .withLibrary(SqlLibrary.MYSQL).ok(expectedMysql); } @Test void testNotRlike() { @@ -5171,7 +5175,16 @@ private void checkLiteral2(String expression, String expected) { String expected = "SELECT \"product_name\"\n" + "FROM \"foodmart\".\"product\"\n" + "WHERE \"product_name\" NOT RLIKE '.+@.+\\\\..+'"; - sql(query).withLibrary(SqlLibrary.SPARK).ok(expected); + String expectedHive = "SELECT \"product_name\"\n" + + "FROM \"foodmart\".\"product\"\n" + + "WHERE \"product_name\" NOT RLIKE '.+@.+\\\\..+'"; + String expectedMysql = "SELECT \"product_name\"\n" + + "FROM \"foodmart\".\"product\"\n" + + "WHERE \"product_name\" NOT RLIKE '.+@.+\\\\..+'"; + sql(query) + .withLibrary(SqlLibrary.SPARK).ok(expected) + .withLibrary(SqlLibrary.HIVE).ok(expectedHive) + .withLibrary(SqlLibrary.MYSQL).ok(expectedMysql); } @Test void testNotIlike() { diff --git a/site/_docs/reference.md b/site/_docs/reference.md index 4faca2f7e671..04356a29aaec 100644 --- a/site/_docs/reference.md +++ b/site/_docs/reference.md @@ -2834,8 +2834,8 @@ In the following: | b m p s | REPEAT(string, integer) | Returns a string consisting of *string* repeated of *integer* times; returns an empty string if *integer* is less than 1 | b m | REVERSE(string) | Returns *string* with the order of the characters reversed | b m p s | RIGHT(string, length) | Returns the rightmost *length* characters from the *string* -| h s | string1 RLIKE string2 | Whether *string1* matches regex pattern *string2* (similar to `LIKE`, but uses Java regex) -| h s | string1 NOT RLIKE string2 | Whether *string1* does not match regex pattern *string2* (similar to `NOT LIKE`, but uses Java regex) +| h m s | string1 RLIKE string2 | Whether *string1* matches regex pattern *string2* (similar to `LIKE`, but uses Java regex) +| h m s | string1 NOT RLIKE string2 | Whether *string1* does not match regex pattern *string2* (similar to `NOT LIKE`, but uses Java regex) | b o s | RPAD(string, length[, pattern ]) | Returns a string or bytes value that consists of *string* appended to *length* with *pattern* | b o s | RTRIM(string) | Returns *string* with all blanks removed from the end | b | SAFE_ADD(numeric1, numeric2) | Returns *numeric1* + *numeric2*, or NULL on overflow. Arguments are implicitly cast to one of the types BIGINT, DOUBLE, or DECIMAL diff --git a/testkit/src/main/java/org/apache/calcite/test/SqlOperatorTest.java b/testkit/src/main/java/org/apache/calcite/test/SqlOperatorTest.java index daf139a75c3b..f5c978d53a42 100644 --- a/testkit/src/main/java/org/apache/calcite/test/SqlOperatorTest.java +++ b/testkit/src/main/java/org/apache/calcite/test/SqlOperatorTest.java @@ -3790,9 +3790,10 @@ void checkIsNull(SqlOperatorFixture f, SqlOperator operator) { checkRlikeFunc(f, SqlLibrary.HIVE, SqlLibraryOperators.RLIKE); checkRlikeFunc(f, SqlLibrary.SPARK, SqlLibraryOperators.RLIKE); checkRlikeFunc(f, SqlLibrary.SPARK, SqlLibraryOperators.REGEXP); + checkRlikeFunc(f, SqlLibrary.MYSQL, SqlLibraryOperators.RLIKE); checkNotRlikeFunc(f.withLibrary(SqlLibrary.HIVE)); checkNotRlikeFunc(f.withLibrary(SqlLibrary.SPARK)); - checkRlikeFails(f.withLibrary(SqlLibrary.MYSQL)); + checkNotRlikeFunc(f.withLibrary(SqlLibrary.MYSQL)); checkRlikeFails(f.withLibrary(SqlLibrary.ORACLE)); f.setFor(SqlLibraryOperators.REGEXP_LIKE, VM_EXPAND);