Skip to content

Commit

Permalink
feat: Support EscapedStringLiteral, update sqlparser to 0.44.0 (a…
Browse files Browse the repository at this point in the history
…pache#9268)

* feat: upgrade sqlparser from 0.43.0 to 0.44.0

* chore: update Cargo.lock
  • Loading branch information
JasonLi-cn authored Mar 4, 2024
1 parent 608b615 commit 2651437
Show file tree
Hide file tree
Showing 6 changed files with 62 additions and 28 deletions.
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -99,7 +99,7 @@ parquet = { version = "50.0.0", default-features = false, features = ["arrow", "
rand = "0.8"
rstest = "0.18.0"
serde_json = "1"
sqlparser = { version = "0.43.0", features = ["visitor"] }
sqlparser = { version = "0.44.0", features = ["visitor"] }
tempfile = "3"
thiserror = "1.0.44"
tokio = { version = "1.36", features = ["macros", "rt", "sync"] }
Expand Down
42 changes: 21 additions & 21 deletions datafusion-cli/Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions datafusion/sql/src/expr/function.rs
Original file line number Diff line number Diff line change
Expand Up @@ -258,10 +258,12 @@ impl<'a, S: ContextProvider> SqlToRel<'a, S> {
FunctionArg::Named {
name: _,
arg: FunctionArgExpr::Expr(arg),
operator: _,
} => self.sql_expr_to_logical_expr(arg, schema, planner_context),
FunctionArg::Named {
name: _,
arg: FunctionArgExpr::Wildcard,
operator: _,
} => Ok(Expr::Wildcard { qualifier: None }),
FunctionArg::Unnamed(FunctionArgExpr::Expr(arg)) => {
self.sql_expr_to_logical_expr(arg, schema, planner_context)
Expand Down
1 change: 1 addition & 0 deletions datafusion/sql/src/expr/value.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,7 @@ impl<'a, S: ContextProvider> SqlToRel<'a, S> {
plan_err!("Invalid HexStringLiteral '{s}'")
}
}
Value::EscapedStringLiteral(s) => Ok(lit(s)),
_ => plan_err!("Unsupported Value '{value:?}'"),
}
}
Expand Down
18 changes: 12 additions & 6 deletions datafusion/sql/src/statement.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,10 +52,10 @@ use datafusion_expr::{
};
use sqlparser::ast;
use sqlparser::ast::{
Assignment, ColumnDef, CreateTableOptions, Expr as SQLExpr, Expr, Ident, ObjectName,
ObjectType, Query, SchemaName, SetExpr, ShowCreateObject, ShowStatementFilter,
Statement, TableConstraint, TableFactor, TableWithJoins, TransactionMode,
UnaryOperator, Value,
Assignment, ColumnDef, CreateTableOptions, DescribeAlias, Expr as SQLExpr, Expr,
FromTable, Ident, ObjectName, ObjectType, Query, SchemaName, SetExpr,
ShowCreateObject, ShowStatementFilter, Statement, TableConstraint, TableFactor,
TableWithJoins, TransactionMode, UnaryOperator, Value,
};
use sqlparser::parser::ParserError::ParserError;

Expand Down Expand Up @@ -177,7 +177,8 @@ impl<'a, S: ContextProvider> SqlToRel<'a, S> {
let sql = Some(statement.to_string());
match statement {
Statement::ExplainTable {
describe_alias: true, // only parse 'DESCRIBE table_name' and not 'EXPLAIN table_name'
describe_alias: DescribeAlias::Describe, // only parse 'DESCRIBE table_name' and not 'EXPLAIN table_name'
hive_format: _,
table_name,
} => self.describe_table_to_plan(table_name),
Statement::Explain {
Expand Down Expand Up @@ -630,7 +631,12 @@ impl<'a, S: ContextProvider> SqlToRel<'a, S> {
}
}

fn get_delete_target(&self, mut from: Vec<TableWithJoins>) -> Result<ObjectName> {
fn get_delete_target(&self, from: FromTable) -> Result<ObjectName> {
let mut from = match from {
FromTable::WithFromKeyword(v) => v,
FromTable::WithoutKeyword(v) => v,
};

if from.len() != 1 {
return not_impl_err!(
"DELETE FROM only supports single table, got {}: {from:?}",
Expand Down
25 changes: 25 additions & 0 deletions datafusion/sql/tests/sql_integration.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4423,6 +4423,31 @@ fn test_field_not_found_window_function() {
quick_test(qualified_sql, expected);
}

#[test]
fn test_parse_escaped_string_literal_value() {
let sql = r"SELECT length('\r\n') AS len";
let expected = "Projection: character_length(Utf8(\"\\r\\n\")) AS len\
\n EmptyRelation";
quick_test(sql, expected);

let sql = r"SELECT length(E'\r\n') AS len";
let expected = "Projection: character_length(Utf8(\"\r\n\")) AS len\
\n EmptyRelation";
quick_test(sql, expected);

let sql = r"SELECT length(E'\445') AS len, E'\x4B' AS hex, E'\u0001' AS unicode";
let expected =
"Projection: character_length(Utf8(\"%\")) AS len, Utf8(\"\u{004b}\") AS hex, Utf8(\"\u{0001}\") AS unicode\
\n EmptyRelation";
quick_test(sql, expected);

let sql = r"SELECT length(E'\000') AS len";
assert_eq!(
logical_plan(sql).unwrap_err().strip_backtrace(),
"SQL error: TokenizerError(\"Unterminated encoded string literal at Line: 1, Column 15\")"
)
}

fn assert_field_not_found(err: DataFusionError, name: &str) {
match err {
DataFusionError::SchemaError { .. } => {
Expand Down

0 comments on commit 2651437

Please sign in to comment.