diff --git a/datafusion/physical-expr/src/window/lead_lag.rs b/datafusion/physical-expr/src/window/lead_lag.rs index d22660d41ebd..5cd11c039082 100644 --- a/datafusion/physical-expr/src/window/lead_lag.rs +++ b/datafusion/physical-expr/src/window/lead_lag.rs @@ -21,10 +21,11 @@ use crate::window::BuiltInWindowFunctionExpr; use crate::PhysicalExpr; use arrow::array::ArrayRef; -use arrow::compute::cast; +use arrow::compute::{cast, cast_with_options, CastOptions}; use arrow::datatypes::{DataType, Field}; -use datafusion_common::ScalarValue; -use datafusion_common::{internal_err, DataFusionError, Result}; +use datafusion_common::{internal_err, ScalarValue}; +use datafusion_common::{DataFusionError, Result}; +use datafusion_expr::type_coercion::binary::comparison_coercion; use datafusion_expr::PartitionEvaluator; use std::any::Any; use std::cmp::min; @@ -235,11 +236,28 @@ fn get_default_value( default_value: Option<&ScalarValue>, dtype: &DataType, ) -> Result { - if let Some(value) = default_value { - if let ScalarValue::Int64(Some(val)) = value { - ScalarValue::try_from_string(val.to_string(), dtype) + if let Some(default_value) = default_value { + let default_value_type = default_value.data_type(); + + if comparison_coercion(&default_value_type, dtype).is_some() { + ScalarValue::try_from_array( + &cast_with_options( + &default_value.to_array()?, + dtype, + &CastOptions { + safe: false, + format_options: Default::default(), + }, + )?, + 0, + ) } else { - internal_err!("Expects default value to have Int64 type") + internal_err!( + "Cannot coerce default value {:?} {} to {:?}", + default_value, + default_value_type, + dtype + ) } } else { Ok(ScalarValue::try_from(dtype)?) diff --git a/datafusion/sqllogictest/test_files/window.slt b/datafusion/sqllogictest/test_files/window.slt index 1ef0ba0d10e3..5a9b8382613f 100644 --- a/datafusion/sqllogictest/test_files/window.slt +++ b/datafusion/sqllogictest/test_files/window.slt @@ -1153,6 +1153,26 @@ SELECT 141680161 63044568 63044568 225513085 225513085 145294611 141047417 141047417 243203849 243203849 +# can coerce given default value to lag/lead value type +query PP +SELECT + LAG(c9::timestamp, 99999999, '2000-11-22T16:17:06.624Z') OVER(ORDER BY c9) as lag_default_coerced, + LEAD(c9::timestamp, 99999999, '2023-11-22T16:17:06.624Z') OVER(ORDER BY c9) as lead_default_coerced + FROM aggregate_test_100 + LIMIT 1 +---- +2000-11-22T16:17:06.624 2023-11-22T16:17:06.624 + +# cannot coerce given default value to lag value type +query error +SELECT + LAG(c9, 99999999, '2000-11-22T16:17:06.624Z') OVER(ORDER BY c9) + FROM aggregate_test_100 + LIMIT 1 +---- +DataFusion error: Arrow error: Cast error: Cannot cast string '2000-11-22T16:17:06.624Z' to value of UInt64 type + + #fn test_window_frame_first_value_last_value_aggregate query IIII SELECT