Skip to content

Commit a40c2e9

Browse files
committed
fix: avoid internal errors for OneOf signature mismatches
Signed-off-by: yaommen <myanstu@163.com>
1 parent 57b275a commit a40c2e9

File tree

6 files changed

+72
-23
lines changed

6 files changed

+72
-23
lines changed

datafusion/expr/src/type_coercion/functions.rs

Lines changed: 59 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -325,24 +325,20 @@ fn get_valid_types_with_udf<F: UDFCoercionExt>(
325325
},
326326
TypeSignature::OneOf(signatures) => {
327327
let mut res = vec![];
328-
let mut errors = vec![];
329328
for sig in signatures {
330-
match get_valid_types_with_udf(sig, current_types, func) {
331-
Ok(valid_types) => {
332-
res.extend(valid_types);
333-
}
334-
Err(e) => {
335-
errors.push(e.to_string());
336-
}
329+
if let Ok(valid_types) =
330+
get_valid_types_with_udf(sig, current_types, func)
331+
{
332+
res.extend(valid_types);
337333
}
338334
}
339335

340-
// Every signature failed, return the joined error
336+
// Every signature failed, return a neutral planning error rather than
337+
// a branch-specific error that may not match the best overload.
341338
if res.is_empty() {
342-
return internal_err!(
343-
"Function '{}' failed to match any signature, errors: {}",
344-
func.name(),
345-
errors.join(",")
339+
return plan_err!(
340+
"Function '{}' failed to match any signature",
341+
func.name()
346342
);
347343
} else {
348344
res
@@ -1223,6 +1219,56 @@ mod tests {
12231219
Ok(())
12241220
}
12251221

1222+
#[test]
1223+
fn test_one_of_uses_generic_plan_error_instead_of_internal_error() {
1224+
let current_fields = vec![Arc::new(Field::new("t", DataType::Boolean, true))];
1225+
let signature = Signature::one_of(
1226+
vec![
1227+
Signature::coercible(
1228+
vec![Coercion::new_exact(TypeSignatureClass::Decimal)],
1229+
Volatility::Immutable,
1230+
)
1231+
.type_signature
1232+
.clone(),
1233+
Signature::coercible(
1234+
vec![Coercion::new_exact(TypeSignatureClass::Duration)],
1235+
Volatility::Immutable,
1236+
)
1237+
.type_signature
1238+
.clone(),
1239+
],
1240+
Volatility::Immutable,
1241+
);
1242+
1243+
let err = fields_with_udf(&current_fields, &MockUdf(signature)).unwrap_err();
1244+
let err = err.to_string();
1245+
1246+
assert_eq!(
1247+
err,
1248+
"Error during planning: Function 'test' failed to match any signature"
1249+
);
1250+
assert!(!err.contains("Internal error"));
1251+
assert!(!err.contains("TypeSignatureClass"));
1252+
}
1253+
1254+
#[test]
1255+
fn test_one_of_uses_generic_plan_error_for_arity_mismatch() {
1256+
let current_fields = vec![Arc::new(Field::new("t", DataType::Int32, true))];
1257+
let signature = Signature::one_of(
1258+
vec![TypeSignature::Any(2), TypeSignature::Any(3)],
1259+
Volatility::Immutable,
1260+
);
1261+
1262+
let err = fields_with_udf(&current_fields, &MockUdf(signature)).unwrap_err();
1263+
let err = err.to_string();
1264+
1265+
assert_eq!(
1266+
err,
1267+
"Error during planning: Function 'test' failed to match any signature"
1268+
);
1269+
assert!(!err.contains("Internal error"));
1270+
}
1271+
12261272
#[test]
12271273
fn test_nested_wildcard_fixed_size_lists() -> Result<()> {
12281274
let type_into = DataType::FixedSizeList(

datafusion/sqllogictest/test_files/array.slt

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7798,17 +7798,17 @@ select generate_series(arrow_cast('2021-01-01T00:00:00', 'Timestamp(Nanosecond,
77987798
[2021-01-01T00:00:00-05:00, 2021-01-01T01:29:54.500-05:00, 2021-01-01T02:59:49-05:00, 2021-01-01T04:29:43.500-05:00, 2021-01-01T05:59:38-05:00]
77997799

78007800
## mixing types for timestamps is not supported
7801-
query error DataFusion error: Error during planning: Internal error: Function 'generate_series' failed to match any signature
7801+
query error DataFusion error: Error during planning: Function 'generate_series' failed to match any signature(.|\n)*generate_series\(Timestamp\(ns, "-05:00"\), Date32, Interval\(MonthDayNano\)\)(.|\n)*Candidate functions:
78027802
select generate_series(arrow_cast('2021-01-01T00:00:00', 'Timestamp(Nanosecond, Some("-05:00"))'), DATE '2021-01-02', INTERVAL '1' HOUR);
78037803

78047804
## mixing types not allowed even if an argument is null
7805-
query error DataFusion error: Error during planning: Internal error: Function 'generate_series' failed to match any signature
7805+
query error DataFusion error: Error during planning: Function 'generate_series' failed to match any signature(.|\n)*generate_series\(Timestamp\(ns\), Date32, Null\)(.|\n)*Candidate functions:
78067806
select generate_series(TIMESTAMP '1992-09-01', DATE '1993-03-01', NULL);
78077807

7808-
query error DataFusion error: Error during planning: Internal error: Function 'generate_series' failed to match any signature
7808+
query error DataFusion error: Error during planning: Function 'generate_series' failed to match any signature(.|\n)*generate_series\(Int64, Utf8, Utf8\)(.|\n)*Candidate functions:
78097809
select generate_series(1, '2024-01-01', '2025-01-02');
78107810

7811-
query error DataFusion error: Error during planning: Internal error: Function 'generate_series' failed to match any signature
7811+
query error DataFusion error: Error during planning: Function 'generate_series' failed to match any signature(.|\n)*generate_series\(Timestamp\(ns\), Utf8, Interval\(MonthDayNano\)\)(.|\n)*Candidate functions:
78127812
select generate_series('2024-01-01'::timestamp, '2025-01-02', interval '1 day');
78137813

78147814
## should return NULL

datafusion/sqllogictest/test_files/errors.slt

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -125,13 +125,16 @@ from aggregate_test_100
125125
order by c9
126126

127127
# WindowFunction wrong signature
128-
statement error DataFusion error: Error during planning: Internal error: Function 'nth_value' failed to match any signature
128+
statement error DataFusion error: Error during planning: Function 'nth_value' failed to match any signature(.|\n)*nth_value\(Int32, Int64, Int64\)(.|\n)*Candidate functions:
129129
select
130130
c9,
131131
nth_value(c5, 2, 3) over (order by c9) as nv1
132132
from aggregate_test_100
133133
order by c9
134134

135+
query error DataFusion error: Error during planning: Function 'sum' failed to match any signature(.|\n)*sum\(Boolean\)(.|\n)*Candidate functions:
136+
select sum(bool_col) from (values (true), (false), (null)) as t(bool_col);
137+
135138

136139
# nth_value with wrong name
137140
statement error DataFusion error: Error during planning: Invalid function 'nth_vlue'.\nDid you mean 'nth_value'?

datafusion/sqllogictest/test_files/functions.slt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -208,10 +208,10 @@ SELECT substr('alphabet', NULL, 2)
208208
----
209209
NULL
210210

211-
statement error Function 'substr' failed to match any signature
211+
statement error DataFusion error: Error during planning: Function 'substr' failed to match any signature(.|\n)*Candidate functions:
212212
SELECT substr(1, 3)
213213

214-
statement error Function 'substr' failed to match any signature
214+
statement error DataFusion error: Error during planning: Function 'substr' failed to match any signature(.|\n)*Candidate functions:
215215
SELECT substr(1, 3, 4)
216216

217217
query T

datafusion/sqllogictest/test_files/named_arguments.slt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -86,7 +86,7 @@ SELECT substr("STR" => 'hello world', "start_pos" => 7);
8686

8787
# Error: wrong number of arguments
8888
# This query provides only 1 argument but substr requires 2 or 3
89-
query error Function 'substr' failed to match any signature
89+
query error DataFusion error: Error during planning: Function 'substr' failed to match any signature(.|\n)*Candidate functions:
9090
SELECT substr(str => 'hello world');
9191

9292
#############

datafusion/sqllogictest/test_files/string/string_literal.slt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -132,10 +132,10 @@ SELECT substr('Hello🌏世界', 5, 3)
132132
----
133133
o🌏世
134134

135-
statement error Function 'substr' failed to match any signature
135+
statement error DataFusion error: Error during planning: Function 'substr' failed to match any signature(.|\n)*Candidate functions:
136136
SELECT substr(1, 3)
137137

138-
statement error Function 'substr' failed to match any signature
138+
statement error DataFusion error: Error during planning: Function 'substr' failed to match any signature(.|\n)*Candidate functions:
139139
SELECT substr(1, 3, 4)
140140

141141
statement error Execution error: negative substring length not allowed

0 commit comments

Comments
 (0)