This is an automated email from the ASF dual-hosted git repository.

alamb pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/arrow-datafusion.git


The following commit(s) were added to refs/heads/main by this push:
     new f7e55814b9 Move bit_length and chr functions to datafusion_functions 
(#9782)
f7e55814b9 is described below

commit f7e55814b9e009f310cb49c9e694a778da938a23
Author: Chojan Shang <[email protected]>
AuthorDate: Mon Mar 25 19:19:57 2024 +0800

    Move bit_length and chr functions to datafusion_functions (#9782)
    
    * Move bit_length function to datafusion_functions
    
    Signed-off-by: Chojan Shang <[email protected]>
    
    * Move chr function to datafusion_functions
    
    Signed-off-by: Chojan Shang <[email protected]>
    
    * Port error sqllogictests
    
    Signed-off-by: Chojan Shang <[email protected]>
    
    * Refactor to keep ui
    
    Signed-off-by: Chojan Shang <[email protected]>
    
    * Make clippy happy
    
    Signed-off-by: Chojan Shang <[email protected]>
    
    ---------
    
    Signed-off-by: Chojan Shang <[email protected]>
---
 datafusion/expr/src/built_in_function.rs           | 18 +---
 datafusion/expr/src/expr_fn.rs                     | 14 ----
 datafusion/functions/src/string/bit_length.rs      | 85 +++++++++++++++++++
 datafusion/functions/src/string/chr.rs             | 96 ++++++++++++++++++++++
 datafusion/functions/src/string/mod.rs             | 16 ++++
 datafusion/physical-expr/src/functions.rs          | 89 --------------------
 datafusion/physical-expr/src/string_expressions.rs | 31 +------
 datafusion/proto/proto/datafusion.proto            |  4 +-
 datafusion/proto/src/generated/pbjson.rs           |  6 --
 datafusion/proto/src/generated/prost.rs            |  8 +-
 datafusion/proto/src/logical_plan/from_proto.rs    | 10 +--
 datafusion/proto/src/logical_plan/to_proto.rs      |  2 -
 datafusion/sqllogictest/test_files/expr.slt        |  6 ++
 13 files changed, 211 insertions(+), 174 deletions(-)

diff --git a/datafusion/expr/src/built_in_function.rs 
b/datafusion/expr/src/built_in_function.rs
index b3f17ae3c2..bb0f79f8ec 100644
--- a/datafusion/expr/src/built_in_function.rs
+++ b/datafusion/expr/src/built_in_function.rs
@@ -103,12 +103,8 @@ pub enum BuiltinScalarFunction {
     Cot,
 
     // string functions
-    /// bit_length
-    BitLength,
     /// character_length
     CharacterLength,
-    /// chr
-    Chr,
     /// concat
     Concat,
     /// concat_ws
@@ -222,9 +218,7 @@ impl BuiltinScalarFunction {
             BuiltinScalarFunction::Cbrt => Volatility::Immutable,
             BuiltinScalarFunction::Cot => Volatility::Immutable,
             BuiltinScalarFunction::Trunc => Volatility::Immutable,
-            BuiltinScalarFunction::BitLength => Volatility::Immutable,
             BuiltinScalarFunction::CharacterLength => Volatility::Immutable,
-            BuiltinScalarFunction::Chr => Volatility::Immutable,
             BuiltinScalarFunction::Concat => Volatility::Immutable,
             BuiltinScalarFunction::ConcatWithSeparator => 
Volatility::Immutable,
             BuiltinScalarFunction::EndsWith => Volatility::Immutable,
@@ -263,13 +257,9 @@ impl BuiltinScalarFunction {
         // the return type of the built in function.
         // Some built-in functions' return type depends on the incoming type.
         match self {
-            BuiltinScalarFunction::BitLength => {
-                utf8_to_int_type(&input_expr_types[0], "bit_length")
-            }
             BuiltinScalarFunction::CharacterLength => {
                 utf8_to_int_type(&input_expr_types[0], "character_length")
             }
-            BuiltinScalarFunction::Chr => Ok(Utf8),
             BuiltinScalarFunction::Coalesce => {
                 // COALESCE has multiple args and they might get coerced, get 
a preview of this
                 let coerced_types = data_types(input_expr_types, 
&self.signature());
@@ -377,15 +367,11 @@ impl BuiltinScalarFunction {
             BuiltinScalarFunction::Coalesce => {
                 Signature::variadic_equal(self.volatility())
             }
-            BuiltinScalarFunction::BitLength
-            | BuiltinScalarFunction::CharacterLength
+            BuiltinScalarFunction::CharacterLength
             | BuiltinScalarFunction::InitCap
             | BuiltinScalarFunction::Reverse => {
                 Signature::uniform(1, vec![Utf8, LargeUtf8], self.volatility())
             }
-            BuiltinScalarFunction::Chr => {
-                Signature::uniform(1, vec![Int64], self.volatility())
-            }
             BuiltinScalarFunction::Lpad | BuiltinScalarFunction::Rpad => {
                 Signature::one_of(
                     vec![
@@ -599,13 +585,11 @@ impl BuiltinScalarFunction {
             BuiltinScalarFunction::Coalesce => &["coalesce"],
 
             // string functions
-            BuiltinScalarFunction::BitLength => &["bit_length"],
             BuiltinScalarFunction::CharacterLength => {
                 &["character_length", "char_length", "length"]
             }
             BuiltinScalarFunction::Concat => &["concat"],
             BuiltinScalarFunction::ConcatWithSeparator => &["concat_ws"],
-            BuiltinScalarFunction::Chr => &["chr"],
             BuiltinScalarFunction::EndsWith => &["ends_with"],
             BuiltinScalarFunction::InitCap => &["initcap"],
             BuiltinScalarFunction::Left => &["left"],
diff --git a/datafusion/expr/src/expr_fn.rs b/datafusion/expr/src/expr_fn.rs
index f75d886967..0ea946288e 100644
--- a/datafusion/expr/src/expr_fn.rs
+++ b/datafusion/expr/src/expr_fn.rs
@@ -578,24 +578,12 @@ scalar_expr!(Atan2, atan2, y x, "inverse tangent of a 
division given in the argu
 scalar_expr!(Log, log, base x, "logarithm of a `x` for a particular `base`");
 
 // string functions
-scalar_expr!(
-    BitLength,
-    bit_length,
-    string,
-    "the number of bits in the `string`"
-);
 scalar_expr!(
     CharacterLength,
     character_length,
     string,
     "the number of characters in the `string`"
 );
-scalar_expr!(
-    Chr,
-    chr,
-    code_point,
-    "converts the Unicode code point to a UTF8 character"
-);
 scalar_expr!(InitCap, initcap, string, "converts the first letter of each word 
in `string` in uppercase and the remaining characters in lowercase");
 scalar_expr!(Left, left, string n, "returns the first `n` characters in the 
`string`");
 scalar_expr!(Reverse, reverse, string, "reverses the `string`");
@@ -1044,9 +1032,7 @@ mod test {
         test_scalar_expr!(Nanvl, nanvl, x, y);
         test_scalar_expr!(Iszero, iszero, input);
 
-        test_scalar_expr!(BitLength, bit_length, string);
         test_scalar_expr!(CharacterLength, character_length, string);
-        test_scalar_expr!(Chr, chr, string);
         test_scalar_expr!(Gcd, gcd, arg_1, arg_2);
         test_scalar_expr!(Lcm, lcm, arg_1, arg_2);
         test_scalar_expr!(InitCap, initcap, string);
diff --git a/datafusion/functions/src/string/bit_length.rs 
b/datafusion/functions/src/string/bit_length.rs
new file mode 100644
index 0000000000..9f61275158
--- /dev/null
+++ b/datafusion/functions/src/string/bit_length.rs
@@ -0,0 +1,85 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+
+use arrow::compute::kernels::length::bit_length;
+use std::any::Any;
+
+use arrow::datatypes::DataType;
+
+use datafusion_common::{exec_err, Result, ScalarValue};
+use datafusion_expr::{ColumnarValue, Volatility};
+use datafusion_expr::{ScalarUDFImpl, Signature};
+
+use crate::string::common::*;
+
+#[derive(Debug)]
+pub(super) struct BitLengthFunc {
+    signature: Signature,
+}
+
+impl BitLengthFunc {
+    pub fn new() -> Self {
+        use DataType::*;
+        Self {
+            signature: Signature::uniform(
+                1,
+                vec![Utf8, LargeUtf8],
+                Volatility::Immutable,
+            ),
+        }
+    }
+}
+
+impl ScalarUDFImpl for BitLengthFunc {
+    fn as_any(&self) -> &dyn Any {
+        self
+    }
+
+    fn name(&self) -> &str {
+        "bit_length"
+    }
+
+    fn signature(&self) -> &Signature {
+        &self.signature
+    }
+
+    fn return_type(&self, arg_types: &[DataType]) -> Result<DataType> {
+        utf8_to_int_type(&arg_types[0], "bit_length")
+    }
+
+    fn invoke(&self, args: &[ColumnarValue]) -> Result<ColumnarValue> {
+        if args.len() != 1 {
+            return exec_err!(
+                "bit_length function requires 1 argument, got {}",
+                args.len()
+            );
+        }
+
+        match &args[0] {
+            ColumnarValue::Array(v) => 
Ok(ColumnarValue::Array(bit_length(v.as_ref())?)),
+            ColumnarValue::Scalar(v) => match v {
+                ScalarValue::Utf8(v) => 
Ok(ColumnarValue::Scalar(ScalarValue::Int32(
+                    v.as_ref().map(|x| (x.len() * 8) as i32),
+                ))),
+                ScalarValue::LargeUtf8(v) => Ok(ColumnarValue::Scalar(
+                    ScalarValue::Int64(v.as_ref().map(|x| (x.len() * 8) as 
i64)),
+                )),
+                _ => unreachable!(),
+            },
+        }
+    }
+}
diff --git a/datafusion/functions/src/string/chr.rs 
b/datafusion/functions/src/string/chr.rs
new file mode 100644
index 0000000000..df3b803ba6
--- /dev/null
+++ b/datafusion/functions/src/string/chr.rs
@@ -0,0 +1,96 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+
+use std::any::Any;
+use std::sync::Arc;
+
+use arrow::array::ArrayRef;
+use arrow::array::StringArray;
+use arrow::datatypes::DataType;
+use arrow::datatypes::DataType::Int64;
+use arrow::datatypes::DataType::Utf8;
+
+use datafusion_common::cast::as_int64_array;
+use datafusion_common::{exec_err, Result};
+use datafusion_expr::{ColumnarValue, Volatility};
+use datafusion_expr::{ScalarUDFImpl, Signature};
+
+use crate::string::common::*;
+
+/// Returns the character with the given code. chr(0) is disallowed because 
text data types cannot store that character.
+/// chr(65) = 'A'
+pub fn chr(args: &[ArrayRef]) -> Result<ArrayRef> {
+    let integer_array = as_int64_array(&args[0])?;
+
+    // first map is the iterator, second is for the `Option<_>`
+    let result = integer_array
+        .iter()
+        .map(|integer: Option<i64>| {
+            integer
+                .map(|integer| {
+                    if integer == 0 {
+                        exec_err!("null character not permitted.")
+                    } else {
+                        match core::char::from_u32(integer as u32) {
+                            Some(integer) => Ok(integer.to_string()),
+                            None => {
+                                exec_err!("requested character too large for 
encoding.")
+                            }
+                        }
+                    }
+                })
+                .transpose()
+        })
+        .collect::<Result<StringArray>>()?;
+
+    Ok(Arc::new(result) as ArrayRef)
+}
+
+#[derive(Debug)]
+pub(super) struct ChrFunc {
+    signature: Signature,
+}
+
+impl ChrFunc {
+    pub fn new() -> Self {
+        Self {
+            signature: Signature::uniform(1, vec![Int64], 
Volatility::Immutable),
+        }
+    }
+}
+
+impl ScalarUDFImpl for ChrFunc {
+    fn as_any(&self) -> &dyn Any {
+        self
+    }
+
+    fn name(&self) -> &str {
+        "chr"
+    }
+
+    fn signature(&self) -> &Signature {
+        &self.signature
+    }
+
+    fn return_type(&self, _arg_types: &[DataType]) -> Result<DataType> {
+        Ok(Utf8)
+    }
+
+    fn invoke(&self, args: &[ColumnarValue]) -> Result<ColumnarValue> {
+        make_scalar_function(chr, vec![])(args)
+    }
+}
diff --git a/datafusion/functions/src/string/mod.rs 
b/datafusion/functions/src/string/mod.rs
index d2b9fb2da8..81639c45f7 100644
--- a/datafusion/functions/src/string/mod.rs
+++ b/datafusion/functions/src/string/mod.rs
@@ -22,7 +22,9 @@ use std::sync::Arc;
 use datafusion_expr::ScalarUDF;
 
 mod ascii;
+mod bit_length;
 mod btrim;
+mod chr;
 mod common;
 mod levenshtein;
 mod lower;
@@ -40,7 +42,9 @@ mod uuid;
 
 // create UDFs
 make_udf_function!(ascii::AsciiFunc, ASCII, ascii);
+make_udf_function!(bit_length::BitLengthFunc, BIT_LENGTH, bit_length);
 make_udf_function!(btrim::BTrimFunc, BTRIM, btrim);
+make_udf_function!(chr::ChrFunc, CHR, chr);
 make_udf_function!(levenshtein::LevenshteinFunc, LEVENSHTEIN, levenshtein);
 make_udf_function!(ltrim::LtrimFunc, LTRIM, ltrim);
 make_udf_function!(lower::LowerFunc, LOWER, lower);
@@ -63,11 +67,21 @@ pub mod expr_fn {
         super::ascii().call(vec![arg1])
     }
 
+    #[doc = "Returns the number of bits in the `string`"]
+    pub fn bit_length(arg: Expr) -> Expr {
+        super::bit_length().call(vec![arg])
+    }
+
     #[doc = "Removes all characters, spaces by default, from both sides of a 
string"]
     pub fn btrim(args: Vec<Expr>) -> Expr {
         super::btrim().call(args)
     }
 
+    #[doc = "Converts the Unicode code point to a UTF8 character"]
+    pub fn chr(arg: Expr) -> Expr {
+        super::chr().call(vec![arg])
+    }
+
     #[doc = "Returns the Levenshtein distance between the two given strings"]
     pub fn levenshtein(arg1: Expr, arg2: Expr) -> Expr {
         super::levenshtein().call(vec![arg1, arg2])
@@ -143,7 +157,9 @@ pub mod expr_fn {
 pub fn functions() -> Vec<Arc<ScalarUDF>> {
     vec![
         ascii(),
+        bit_length(),
         btrim(),
+        chr(),
         levenshtein(),
         lower(),
         ltrim(),
diff --git a/datafusion/physical-expr/src/functions.rs 
b/datafusion/physical-expr/src/functions.rs
index 163598c2df..cd9bba63d6 100644
--- a/datafusion/physical-expr/src/functions.rs
+++ b/datafusion/physical-expr/src/functions.rs
@@ -35,7 +35,6 @@ use std::sync::Arc;
 
 use arrow::{
     array::ArrayRef,
-    compute::kernels::length::bit_length,
     datatypes::{DataType, Int32Type, Int64Type, Schema},
 };
 use arrow_array::Array;
@@ -255,18 +254,6 @@ pub fn create_physical_fun(
             Arc::new(|args| 
make_scalar_function_inner(math_expressions::cot)(args))
         }
         // string functions
-        BuiltinScalarFunction::BitLength => Arc::new(|args| match &args[0] {
-            ColumnarValue::Array(v) => 
Ok(ColumnarValue::Array(bit_length(v.as_ref())?)),
-            ColumnarValue::Scalar(v) => match v {
-                ScalarValue::Utf8(v) => 
Ok(ColumnarValue::Scalar(ScalarValue::Int32(
-                    v.as_ref().map(|x| (x.len() * 8) as i32),
-                ))),
-                ScalarValue::LargeUtf8(v) => Ok(ColumnarValue::Scalar(
-                    ScalarValue::Int64(v.as_ref().map(|x| (x.len() * 8) as 
i64)),
-                )),
-                _ => unreachable!(),
-            },
-        }),
         BuiltinScalarFunction::CharacterLength => {
             Arc::new(|args| match args[0].data_type() {
                 DataType::Utf8 => {
@@ -290,9 +277,6 @@ pub fn create_physical_fun(
                 ),
             })
         }
-        BuiltinScalarFunction::Chr => {
-            Arc::new(|args| 
make_scalar_function_inner(string_expressions::chr)(args))
-        }
         BuiltinScalarFunction::Coalesce => 
Arc::new(conditional_expressions::coalesce),
         BuiltinScalarFunction::Concat => Arc::new(string_expressions::concat),
         BuiltinScalarFunction::ConcatWithSeparator => Arc::new(|args| {
@@ -611,23 +595,6 @@ mod tests {
 
     #[test]
     fn test_functions() -> Result<()> {
-        test_function!(
-            BitLength,
-            &[lit("chars")],
-            Ok(Some(40)),
-            i32,
-            Int32,
-            Int32Array
-        );
-        test_function!(
-            BitLength,
-            &[lit("josé")],
-            Ok(Some(40)),
-            i32,
-            Int32,
-            Int32Array
-        );
-        test_function!(BitLength, &[lit("")], Ok(Some(0)), i32, Int32, 
Int32Array);
         #[cfg(feature = "unicode_expressions")]
         test_function!(
             CharacterLength,
@@ -675,62 +642,6 @@ mod tests {
             Int32,
             Int32Array
         );
-        test_function!(
-            Chr,
-            &[lit(ScalarValue::Int64(Some(128175)))],
-            Ok(Some("💯")),
-            &str,
-            Utf8,
-            StringArray
-        );
-        test_function!(
-            Chr,
-            &[lit(ScalarValue::Int64(None))],
-            Ok(None),
-            &str,
-            Utf8,
-            StringArray
-        );
-        test_function!(
-            Chr,
-            &[lit(ScalarValue::Int64(Some(120)))],
-            Ok(Some("x")),
-            &str,
-            Utf8,
-            StringArray
-        );
-        test_function!(
-            Chr,
-            &[lit(ScalarValue::Int64(Some(128175)))],
-            Ok(Some("💯")),
-            &str,
-            Utf8,
-            StringArray
-        );
-        test_function!(
-            Chr,
-            &[lit(ScalarValue::Int64(None))],
-            Ok(None),
-            &str,
-            Utf8,
-            StringArray
-        );
-        test_function!(
-            Chr,
-            &[lit(ScalarValue::Int64(Some(0)))],
-            exec_err!("null character not permitted."),
-            &str,
-            Utf8,
-            StringArray
-        );
-        test_function!(
-            Chr,
-            &[lit(ScalarValue::Int64(Some(i64::MAX)))],
-            exec_err!("requested character too large for encoding."),
-            &str,
-            Utf8,
-            StringArray
-        );
         test_function!(
             Concat,
             &[lit("aa"), lit("bb"), lit("cc"),],
diff --git a/datafusion/physical-expr/src/string_expressions.rs 
b/datafusion/physical-expr/src/string_expressions.rs
index 812b746354..2185b7c5b4 100644
--- a/datafusion/physical-expr/src/string_expressions.rs
+++ b/datafusion/physical-expr/src/string_expressions.rs
@@ -33,40 +33,11 @@ use arrow::{
 
 use datafusion_common::Result;
 use datafusion_common::{
-    cast::{as_generic_string_array, as_int64_array, as_string_array},
+    cast::{as_generic_string_array, as_string_array},
     exec_err, ScalarValue,
 };
 use datafusion_expr::ColumnarValue;
 
-/// Returns the character with the given code. chr(0) is disallowed because 
text data types cannot store that character.
-/// chr(65) = 'A'
-pub fn chr(args: &[ArrayRef]) -> Result<ArrayRef> {
-    let integer_array = as_int64_array(&args[0])?;
-
-    // first map is the iterator, second is for the `Option<_>`
-    let result = integer_array
-        .iter()
-        .map(|integer: Option<i64>| {
-            integer
-                .map(|integer| {
-                    if integer == 0 {
-                        exec_err!("null character not permitted.")
-                    } else {
-                        match core::char::from_u32(integer as u32) {
-                            Some(integer) => Ok(integer.to_string()),
-                            None => {
-                                exec_err!("requested character too large for 
encoding.")
-                            }
-                        }
-                    }
-                })
-                .transpose()
-        })
-        .collect::<Result<StringArray>>()?;
-
-    Ok(Arc::new(result) as ArrayRef)
-}
-
 /// Concatenates the text representations of all the arguments. NULL arguments 
are ignored.
 /// concat('abcde', 2, NULL, 22) = 'abcde222'
 pub fn concat(args: &[ColumnarValue]) -> Result<ColumnarValue> {
diff --git a/datafusion/proto/proto/datafusion.proto 
b/datafusion/proto/proto/datafusion.proto
index 297e355dd7..f405ecf976 100644
--- a/datafusion/proto/proto/datafusion.proto
+++ b/datafusion/proto/proto/datafusion.proto
@@ -563,10 +563,10 @@ enum ScalarFunction {
   Trunc = 19;
   // 20 was Array
   // RegexpMatch = 21;
-  BitLength = 22;
+  // 22 was BitLength
   // 23 was Btrim
   CharacterLength = 24;
-  Chr = 25;
+  // 25 was Chr
   Concat = 26;
   ConcatWithSeparator = 27;
   // 28 was DatePart
diff --git a/datafusion/proto/src/generated/pbjson.rs 
b/datafusion/proto/src/generated/pbjson.rs
index dce815f0f2..0d22ba5db7 100644
--- a/datafusion/proto/src/generated/pbjson.rs
+++ b/datafusion/proto/src/generated/pbjson.rs
@@ -22928,9 +22928,7 @@ impl serde::Serialize for ScalarFunction {
             Self::Sin => "Sin",
             Self::Sqrt => "Sqrt",
             Self::Trunc => "Trunc",
-            Self::BitLength => "BitLength",
             Self::CharacterLength => "CharacterLength",
-            Self::Chr => "Chr",
             Self::Concat => "Concat",
             Self::ConcatWithSeparator => "ConcatWithSeparator",
             Self::InitCap => "InitCap",
@@ -22990,9 +22988,7 @@ impl<'de> serde::Deserialize<'de> for ScalarFunction {
             "Sin",
             "Sqrt",
             "Trunc",
-            "BitLength",
             "CharacterLength",
-            "Chr",
             "Concat",
             "ConcatWithSeparator",
             "InitCap",
@@ -23081,9 +23077,7 @@ impl<'de> serde::Deserialize<'de> for ScalarFunction {
                     "Sin" => Ok(ScalarFunction::Sin),
                     "Sqrt" => Ok(ScalarFunction::Sqrt),
                     "Trunc" => Ok(ScalarFunction::Trunc),
-                    "BitLength" => Ok(ScalarFunction::BitLength),
                     "CharacterLength" => Ok(ScalarFunction::CharacterLength),
-                    "Chr" => Ok(ScalarFunction::Chr),
                     "Concat" => Ok(ScalarFunction::Concat),
                     "ConcatWithSeparator" => 
Ok(ScalarFunction::ConcatWithSeparator),
                     "InitCap" => Ok(ScalarFunction::InitCap),
diff --git a/datafusion/proto/src/generated/prost.rs 
b/datafusion/proto/src/generated/prost.rs
index 2292687b45..07c3fad153 100644
--- a/datafusion/proto/src/generated/prost.rs
+++ b/datafusion/proto/src/generated/prost.rs
@@ -2862,10 +2862,10 @@ pub enum ScalarFunction {
     Trunc = 19,
     /// 20 was Array
     /// RegexpMatch = 21;
-    BitLength = 22,
+    /// 22 was BitLength
     /// 23 was Btrim
     CharacterLength = 24,
-    Chr = 25,
+    /// 25 was Chr
     Concat = 26,
     ConcatWithSeparator = 27,
     /// 28 was DatePart
@@ -3001,9 +3001,7 @@ impl ScalarFunction {
             ScalarFunction::Sin => "Sin",
             ScalarFunction::Sqrt => "Sqrt",
             ScalarFunction::Trunc => "Trunc",
-            ScalarFunction::BitLength => "BitLength",
             ScalarFunction::CharacterLength => "CharacterLength",
-            ScalarFunction::Chr => "Chr",
             ScalarFunction::Concat => "Concat",
             ScalarFunction::ConcatWithSeparator => "ConcatWithSeparator",
             ScalarFunction::InitCap => "InitCap",
@@ -3057,9 +3055,7 @@ impl ScalarFunction {
             "Sin" => Some(Self::Sin),
             "Sqrt" => Some(Self::Sqrt),
             "Trunc" => Some(Self::Trunc),
-            "BitLength" => Some(Self::BitLength),
             "CharacterLength" => Some(Self::CharacterLength),
-            "Chr" => Some(Self::Chr),
             "Concat" => Some(Self::Concat),
             "ConcatWithSeparator" => Some(Self::ConcatWithSeparator),
             "InitCap" => Some(Self::InitCap),
diff --git a/datafusion/proto/src/logical_plan/from_proto.rs 
b/datafusion/proto/src/logical_plan/from_proto.rs
index b78e3ae6dc..d5eebcb698 100644
--- a/datafusion/proto/src/logical_plan/from_proto.rs
+++ b/datafusion/proto/src/logical_plan/from_proto.rs
@@ -48,8 +48,8 @@ use datafusion_expr::expr::Unnest;
 use datafusion_expr::expr::{Alias, Placeholder};
 use datafusion_expr::window_frame::{check_window_frame, 
regularize_window_order_by};
 use datafusion_expr::{
-    acosh, asinh, atan, atan2, atanh, bit_length, cbrt, ceil, 
character_length, chr,
-    coalesce, concat_expr, concat_ws_expr, cos, cosh, cot, degrees, ends_with, 
exp,
+    acosh, asinh, atan, atan2, atanh, cbrt, ceil, character_length, coalesce,
+    concat_expr, concat_ws_expr, cos, cosh, cot, degrees, ends_with, exp,
     expr::{self, InList, Sort, WindowFunction},
     factorial, find_in_set, floor, gcd, initcap, iszero, lcm, left, ln, log, 
log10, log2,
     logical_plan::{PlanType, StringifiedPlan},
@@ -458,9 +458,7 @@ impl From<&protobuf::ScalarFunction> for 
BuiltinScalarFunction {
             ScalarFunction::Concat => Self::Concat,
             ScalarFunction::Log2 => Self::Log2,
             ScalarFunction::Signum => Self::Signum,
-            ScalarFunction::BitLength => Self::BitLength,
             ScalarFunction::CharacterLength => Self::CharacterLength,
-            ScalarFunction::Chr => Self::Chr,
             ScalarFunction::ConcatWithSeparator => Self::ConcatWithSeparator,
             ScalarFunction::EndsWith => Self::EndsWith,
             ScalarFunction::InitCap => Self::InitCap,
@@ -1418,13 +1416,9 @@ pub fn parse_expr(
                 ScalarFunction::Signum => {
                     Ok(signum(parse_expr(&args[0], registry, codec)?))
                 }
-                ScalarFunction::BitLength => {
-                    Ok(bit_length(parse_expr(&args[0], registry, codec)?))
-                }
                 ScalarFunction::CharacterLength => {
                     Ok(character_length(parse_expr(&args[0], registry, 
codec)?))
                 }
-                ScalarFunction::Chr => Ok(chr(parse_expr(&args[0], registry, 
codec)?)),
                 ScalarFunction::InitCap => {
                     Ok(initcap(parse_expr(&args[0], registry, codec)?))
                 }
diff --git a/datafusion/proto/src/logical_plan/to_proto.rs 
b/datafusion/proto/src/logical_plan/to_proto.rs
index 0c0f0c6e0a..0432b54acf 100644
--- a/datafusion/proto/src/logical_plan/to_proto.rs
+++ b/datafusion/proto/src/logical_plan/to_proto.rs
@@ -1481,9 +1481,7 @@ impl TryFrom<&BuiltinScalarFunction> for 
protobuf::ScalarFunction {
             BuiltinScalarFunction::Concat => Self::Concat,
             BuiltinScalarFunction::Log2 => Self::Log2,
             BuiltinScalarFunction::Signum => Self::Signum,
-            BuiltinScalarFunction::BitLength => Self::BitLength,
             BuiltinScalarFunction::CharacterLength => Self::CharacterLength,
-            BuiltinScalarFunction::Chr => Self::Chr,
             BuiltinScalarFunction::ConcatWithSeparator => 
Self::ConcatWithSeparator,
             BuiltinScalarFunction::EndsWith => Self::EndsWith,
             BuiltinScalarFunction::InitCap => Self::InitCap,
diff --git a/datafusion/sqllogictest/test_files/expr.slt 
b/datafusion/sqllogictest/test_files/expr.slt
index 70fdc26a60..75bcbc0775 100644
--- a/datafusion/sqllogictest/test_files/expr.slt
+++ b/datafusion/sqllogictest/test_files/expr.slt
@@ -415,6 +415,12 @@ SELECT chr(CAST(NULL AS int))
 ----
 NULL
 
+statement error DataFusion error: Execution error: null character not 
permitted.
+SELECT chr(CAST(0 AS int))
+
+statement error DataFusion error: Execution error: requested character too 
large for encoding.
+SELECT chr(CAST(9223372036854775807 AS bigint))
+
 query T
 SELECT concat('a','b','c')
 ----

Reply via email to