-
Notifications
You must be signed in to change notification settings - Fork 2k
Labels
bugSomething isn't workingSomething isn't working
Description
Describe the bug
When a table function is called with a tuple argument, the SQL parser preserves the argument, but DataFusion drops it during planning and ContextProvider::get_table_function_source receives an empty args vector.
For example:
SELECT * FROM my_func(('a', 'b', 'c'));... will lead to a call equivalent to get_table_function_source("my_func", vec![])
To Reproduce
With datafusion-sql 53.0.0:
use std::sync::Arc;
use datafusion_common::{arrow::datatypes::DataType, config::ConfigOptions, DataFusionError};
use datafusion_expr::{AggregateUDF, Expr, ScalarUDF, TableSource, WindowUDF};
use datafusion_sql::{
planner::{ContextProvider, SqlToRel},
sqlparser::{dialect::GenericDialect, parser::Parser},
TableReference,
};
struct Dummy;
impl ContextProvider for Dummy {
fn get_table_source(
&self,
_name: TableReference,
) -> Result<Arc<dyn TableSource>, DataFusionError> {
unimplemented!()
}
fn get_table_function_source(
&self,
name: &str,
args: Vec<Expr>,
) -> Result<Arc<dyn TableSource>, DataFusionError> {
println!("table function name={name:?} args={args:#?}");
unimplemented!()
}
fn get_function_meta(&self, _name: &str) -> Option<Arc<ScalarUDF>> { None }
fn get_aggregate_meta(&self, _name: &str) -> Option<Arc<AggregateUDF>> { None }
fn get_window_meta(&self, _name: &str) -> Option<Arc<WindowUDF>> { None }
fn get_variable_type(&self, _variable_names: &[String]) -> Option<DataType> { None }
fn options(&self) -> &ConfigOptions {
static OPTIONS: std::sync::OnceLock<ConfigOptions> = std::sync::OnceLock::new();
OPTIONS.get_or_init(ConfigOptions::default)
}
fn udf_names(&self) -> Vec<String> { vec![] }
fn udaf_names(&self) -> Vec<String> { vec![] }
fn udwf_names(&self) -> Vec<String> { vec![] }
}
fn main() {
let sql = "select * from my_func(('a', 'b', 'c'))";
let dialect = GenericDialect {};
let ast = Parser::parse_sql(&dialect, sql).unwrap();
println!("ast = {:#?}", ast[0]);
let provider = Dummy;
let sql_to_rel = SqlToRel::new(&provider);
let _ = sql_to_rel.sql_statement_to_plan(ast[0].clone());
}
Cargo.toml:
[dependencies]
datafusion-common = "53.0.0"
datafusion-expr = "53.0.0"
datafusion-sql = "53.0.0"
This prints: table function name="my_func" args=[]
Expected behavior
I would expect get_table_function_source to either get a non-empty argument list, or for planning to return an error.
Additional context
It looks like the issue might be here:
datafusion/datafusion/sql/src/relation/mod.rs
Line 154 in 2b986c8
| .flat_map(|arg| { |
The flat_map will happily turn the error result into a iterable, ignoring the error.
Reactions are currently unavailable
Metadata
Metadata
Assignees
Labels
bugSomething isn't workingSomething isn't working