diff --git a/spark-extension-shims-spark/src/test/scala/org/apache/auron/AuronFunctionSuite.scala b/spark-extension-shims-spark/src/test/scala/org/apache/auron/AuronFunctionSuite.scala index ef07ce3a3..1688ff617 100644 --- a/spark-extension-shims-spark/src/test/scala/org/apache/auron/AuronFunctionSuite.scala +++ b/spark-extension-shims-spark/src/test/scala/org/apache/auron/AuronFunctionSuite.scala @@ -685,4 +685,62 @@ class AuronFunctionSuite extends AuronQueryTest with BaseAuronSQLSuite { } } } + + test("ascii function") { + withTable("t1") { + sql("create table t1(c1 string) using parquet") + sql("insert into t1 values('A'), ('abc'), (''), (null)") + checkSparkAnswerAndOperator("select ascii(c1) from t1") + } + } + + test("bit_length function") { + withTable("t1") { + sql("create table t1(c1 string) using parquet") + sql("insert into t1 values('hello'), (''), (null), ('caf\\u00e9')") + checkSparkAnswerAndOperator("select bit_length(c1) from t1") + } + } + + test("chr function") { + withTable("t1") { + sql("create table t1(c1 bigint) using parquet") + sql("insert into t1 values(65), (97), (48), (null)") + checkSparkAnswerAndOperator("select chr(c1) from t1") + } + } + + test("translate function") { + withTable("t1") { + sql("create table t1(c1 string) using parquet") + sql("insert into t1 values('AaBbCc'), ('hello'), (''), (null)") + checkSparkAnswerAndOperator("select translate(c1, 'ABC', 'xyz') from t1") + } + } + + test("replace function") { + withTable("t1") { + sql("create table t1(c1 string) using parquet") + sql("insert into t1 values('hello world'), ('aaa'), (''), (null)") + checkSparkAnswerAndOperator("select replace(c1, 'world', 'spark') from t1") + checkSparkAnswerAndOperator("select replace(c1, 'a', '') from t1") + } + } + + test("date_trunc function") { + withSQLConf(SQLConf.SESSION_LOCAL_TIMEZONE.key -> "UTC") { + withTable("t1") { + sql("create table t1(c1 timestamp) using parquet") + sql("""insert into t1 values + | (timestamp'2024-03-15 14:30:45'), + | (timestamp'2024-12-31 23:59:59'), + | (null) + |""".stripMargin) + checkSparkAnswerAndOperator("select date_trunc('year', c1) from t1") + checkSparkAnswerAndOperator("select date_trunc('month', c1) from t1") + checkSparkAnswerAndOperator("select date_trunc('day', c1) from t1") + checkSparkAnswerAndOperator("select date_trunc('hour', c1) from t1") + } + } + } } diff --git a/spark-extension/src/main/scala/org/apache/spark/sql/auron/NativeConverters.scala b/spark-extension/src/main/scala/org/apache/spark/sql/auron/NativeConverters.scala index 68007c837..dbe31519e 100644 --- a/spark-extension/src/main/scala/org/apache/spark/sql/auron/NativeConverters.scala +++ b/spark-extension/src/main/scala/org/apache/spark/sql/auron/NativeConverters.scala @@ -891,6 +891,17 @@ object NativeConverters extends Logging { buildScalarFunction(pb.ScalarFunction.FindInSet, e.children, e.dataType) case e: Abs if e.dataType.isInstanceOf[FloatType] || e.dataType.isInstanceOf[DoubleType] => buildScalarFunction(pb.ScalarFunction.Abs, e.children, e.dataType) + case e: Ascii => buildScalarFunction(pb.ScalarFunction.Ascii, e.children, e.dataType) + case e: BitLength => + buildScalarFunction(pb.ScalarFunction.BitLength, e.children, e.dataType) + case e: Chr => buildScalarFunction(pb.ScalarFunction.Chr, e.children, e.dataType) + case e: StringTranslate => + buildScalarFunction(pb.ScalarFunction.Translate, e.children, e.dataType) + case e: StringReplace => + buildScalarFunction(pb.ScalarFunction.Replace, e.children, e.dataType) + case e: TruncTimestamp => + buildScalarFunction(pb.ScalarFunction.DateTrunc, e.children, e.dataType) + case e: OctetLength => buildScalarFunction(pb.ScalarFunction.OctetLength, e.children, e.dataType) case Length(arg) if arg.dataType == StringType =>