This is an automated email from the ASF dual-hosted git repository.
iffyio pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/datafusion-sqlparser-rs.git
The following commit(s) were added to refs/heads/main by this push:
new 62495f2f Mysql: Add support for := operator (#1779)
62495f2f is described below
commit 62495f2f0d998690495f111063a0b0a3466ffa69
Author: bar sela <[email protected]>
AuthorDate: Thu Mar 27 23:48:57 2025 +0200
Mysql: Add support for := operator (#1779)
---
src/ast/operator.rs | 4 ++
src/dialect/mod.rs | 3 +-
src/parser/mod.rs | 1 +
tests/sqlparser_mysql.rs | 104 +++++++++++++++++++++++++++++++++++++++++++++++
4 files changed, 111 insertions(+), 1 deletion(-)
diff --git a/src/ast/operator.rs b/src/ast/operator.rs
index 66a35fee..73fe9cf4 100644
--- a/src/ast/operator.rs
+++ b/src/ast/operator.rs
@@ -321,6 +321,9 @@ pub enum BinaryOperator {
/// `~=` Same as? (PostgreSQL/Redshift geometric operator)
/// See <https://www.postgresql.org/docs/9.5/functions-geometry.html>
TildeEq,
+ /// ':=' Assignment Operator
+ /// See
<https://dev.mysql.com/doc/refman/8.4/en/assignment-operators.html#operator_assign-value>
+ Assignment,
}
impl fmt::Display for BinaryOperator {
@@ -394,6 +397,7 @@ impl fmt::Display for BinaryOperator {
BinaryOperator::QuestionDoublePipe => f.write_str("?||"),
BinaryOperator::At => f.write_str("@"),
BinaryOperator::TildeEq => f.write_str("~="),
+ BinaryOperator::Assignment => f.write_str(":="),
}
}
}
diff --git a/src/dialect/mod.rs b/src/dialect/mod.rs
index 8d4557e2..79184dd7 100644
--- a/src/dialect/mod.rs
+++ b/src/dialect/mod.rs
@@ -620,7 +620,8 @@ pub trait Dialect: Debug + Any {
Token::Word(w) if w.keyword == Keyword::OPERATOR =>
Ok(p!(Between)),
Token::Word(w) if w.keyword == Keyword::DIV => Ok(p!(MulDivModOp)),
Token::Period => Ok(p!(Period)),
- Token::Eq
+ Token::Assignment
+ | Token::Eq
| Token::Lt
| Token::LtEq
| Token::Neq
diff --git a/src/parser/mod.rs b/src/parser/mod.rs
index 65d536f7..adaae286 100644
--- a/src/parser/mod.rs
+++ b/src/parser/mod.rs
@@ -3233,6 +3233,7 @@ impl<'a> Parser<'a> {
let regular_binary_operator = match &tok.token {
Token::Spaceship => Some(BinaryOperator::Spaceship),
Token::DoubleEq => Some(BinaryOperator::Eq),
+ Token::Assignment => Some(BinaryOperator::Assignment),
Token::Eq => Some(BinaryOperator::Eq),
Token::Neq => Some(BinaryOperator::NotEq),
Token::Gt => Some(BinaryOperator::Gt),
diff --git a/tests/sqlparser_mysql.rs b/tests/sqlparser_mysql.rs
index 3d318f70..1d4fd6a0 100644
--- a/tests/sqlparser_mysql.rs
+++ b/tests/sqlparser_mysql.rs
@@ -3483,3 +3483,107 @@ fn parse_match_against_with_alias() {
_ => unreachable!(),
}
}
+
+#[test]
+fn test_variable_assignment_using_colon_equal() {
+ let sql_select = "SELECT @price := price, @tax := price * 0.1 FROM
products WHERE id = 1";
+ let stmt = mysql().verified_stmt(sql_select);
+ match stmt {
+ Statement::Query(query) => {
+ let select = query.body.as_select().unwrap();
+
+ assert_eq!(
+ select.projection,
+ vec![
+ SelectItem::UnnamedExpr(Expr::BinaryOp {
+ left: Box::new(Expr::Identifier(Ident {
+ value: "@price".to_string(),
+ quote_style: None,
+ span: Span::empty(),
+ })),
+ op: BinaryOperator::Assignment,
+ right: Box::new(Expr::Identifier(Ident {
+ value: "price".to_string(),
+ quote_style: None,
+ span: Span::empty(),
+ })),
+ }),
+ SelectItem::UnnamedExpr(Expr::BinaryOp {
+ left: Box::new(Expr::Identifier(Ident {
+ value: "@tax".to_string(),
+ quote_style: None,
+ span: Span::empty(),
+ })),
+ op: BinaryOperator::Assignment,
+ right: Box::new(Expr::BinaryOp {
+ left: Box::new(Expr::Identifier(Ident {
+ value: "price".to_string(),
+ quote_style: None,
+ span: Span::empty(),
+ })),
+ op: BinaryOperator::Multiply,
+ right: Box::new(Expr::Value(
+ (test_utils::number("0.1")).with_empty_span()
+ )),
+ }),
+ }),
+ ]
+ );
+
+ assert_eq!(
+ select.selection,
+ Some(Expr::BinaryOp {
+ left: Box::new(Expr::Identifier(Ident {
+ value: "id".to_string(),
+ quote_style: None,
+ span: Span::empty(),
+ })),
+ op: BinaryOperator::Eq,
+ right:
Box::new(Expr::Value((test_utils::number("1")).with_empty_span())),
+ })
+ );
+ }
+ _ => panic!("Unexpected statement {stmt}"),
+ }
+
+ let sql_update =
+ "UPDATE products SET price = @new_price := price * 1.1 WHERE category
= 'Books'";
+ let stmt = mysql().verified_stmt(sql_update);
+
+ match stmt {
+ Statement::Update { assignments, .. } => {
+ assert_eq!(
+ assignments,
+ vec![Assignment {
+ target: AssignmentTarget::ColumnName(ObjectName(vec![
+ ObjectNamePart::Identifier(Ident {
+ value: "price".to_string(),
+ quote_style: None,
+ span: Span::empty(),
+ })
+ ])),
+ value: Expr::BinaryOp {
+ left: Box::new(Expr::Identifier(Ident {
+ value: "@new_price".to_string(),
+ quote_style: None,
+ span: Span::empty(),
+ })),
+ op: BinaryOperator::Assignment,
+ right: Box::new(Expr::BinaryOp {
+ left: Box::new(Expr::Identifier(Ident {
+ value: "price".to_string(),
+ quote_style: None,
+ span: Span::empty(),
+ })),
+ op: BinaryOperator::Multiply,
+ right: Box::new(Expr::Value(
+ (test_utils::number("1.1")).with_empty_span()
+ )),
+ }),
+ },
+ }]
+ )
+ }
+ _ => panic!("Unexpected statement {stmt}"),
+ }
+}
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]