Skip to content

Commit de5542f

Browse files
MohamedAbdeen21ayman-sigma
authored andcommitted
Add GLOBAL context/modifier to SET statements (apache#1767)
1 parent 7c3f6e0 commit de5542f

File tree

7 files changed

+72
-39
lines changed

7 files changed

+72
-39
lines changed

src/ast/mod.rs

+12-7
Original file line numberDiff line numberDiff line change
@@ -2647,7 +2647,7 @@ pub enum Set {
26472647
/// SQL Standard-style
26482648
/// SET a = 1;
26492649
SingleAssignment {
2650-
local: bool,
2650+
scope: ContextModifier,
26512651
hivevar: bool,
26522652
variable: ObjectName,
26532653
values: Vec<Expr>,
@@ -2729,7 +2729,7 @@ impl Display for Set {
27292729
role_name,
27302730
} => {
27312731
let role_name = role_name.clone().unwrap_or_else(|| Ident::new("NONE"));
2732-
write!(f, "SET{context_modifier} ROLE {role_name}")
2732+
write!(f, "SET {context_modifier}ROLE {role_name}")
27332733
}
27342734
Self::SetSessionParam(kind) => write!(f, "SET {kind}"),
27352735
Self::SetTransaction {
@@ -2776,15 +2776,15 @@ impl Display for Set {
27762776
Ok(())
27772777
}
27782778
Set::SingleAssignment {
2779-
local,
2779+
scope,
27802780
hivevar,
27812781
variable,
27822782
values,
27832783
} => {
27842784
write!(
27852785
f,
27862786
"SET {}{}{} = {}",
2787-
if *local { "LOCAL " } else { "" },
2787+
scope,
27882788
if *hivevar { "HIVEVAR:" } else { "" },
27892789
variable,
27902790
display_comma_separated(values)
@@ -7973,7 +7973,7 @@ impl fmt::Display for FlushLocation {
79737973
}
79747974
}
79757975

7976-
/// Optional context modifier for statements that can be or `LOCAL`, or `SESSION`.
7976+
/// Optional context modifier for statements that can be or `LOCAL`, `GLOBAL`, or `SESSION`.
79777977
#[derive(Debug, Copy, Clone, PartialEq, PartialOrd, Eq, Ord, Hash)]
79787978
#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
79797979
#[cfg_attr(feature = "visitor", derive(Visit, VisitMut))]
@@ -7984,6 +7984,8 @@ pub enum ContextModifier {
79847984
Local,
79857985
/// `SESSION` identifier
79867986
Session,
7987+
/// `GLOBAL` identifier
7988+
Global,
79877989
}
79887990

79897991
impl fmt::Display for ContextModifier {
@@ -7993,10 +7995,13 @@ impl fmt::Display for ContextModifier {
79937995
write!(f, "")
79947996
}
79957997
Self::Local => {
7996-
write!(f, " LOCAL")
7998+
write!(f, "LOCAL ")
79977999
}
79988000
Self::Session => {
7999-
write!(f, " SESSION")
8001+
write!(f, "SESSION ")
8002+
}
8003+
Self::Global => {
8004+
write!(f, "GLOBAL ")
80008005
}
80018006
}
80028007
}

src/parser/mod.rs

+19-10
Original file line numberDiff line numberDiff line change
@@ -1819,6 +1819,15 @@ impl<'a> Parser<'a> {
18191819
})
18201820
}
18211821

1822+
fn keyword_to_modifier(k: Option<Keyword>) -> ContextModifier {
1823+
match k {
1824+
Some(Keyword::LOCAL) => ContextModifier::Local,
1825+
Some(Keyword::GLOBAL) => ContextModifier::Global,
1826+
Some(Keyword::SESSION) => ContextModifier::Session,
1827+
_ => ContextModifier::None,
1828+
}
1829+
}
1830+
18221831
/// Check if the root is an identifier and all fields are identifiers.
18231832
fn is_all_ident(root: &Expr, fields: &[AccessExpr]) -> bool {
18241833
if !matches!(root, Expr::Identifier(_)) {
@@ -11148,11 +11157,7 @@ impl<'a> Parser<'a> {
1114811157
/// Parse a `SET ROLE` statement. Expects SET to be consumed already.
1114911158
fn parse_set_role(&mut self, modifier: Option<Keyword>) -> Result<Statement, ParserError> {
1115011159
self.expect_keyword_is(Keyword::ROLE)?;
11151-
let context_modifier = match modifier {
11152-
Some(Keyword::LOCAL) => ContextModifier::Local,
11153-
Some(Keyword::SESSION) => ContextModifier::Session,
11154-
_ => ContextModifier::None,
11155-
};
11160+
let context_modifier = Self::keyword_to_modifier(modifier);
1115611161

1115711162
let role_name = if self.parse_keyword(Keyword::NONE) {
1115811163
None
@@ -11224,8 +11229,12 @@ impl<'a> Parser<'a> {
1122411229
}
1122511230

1122611231
fn parse_set(&mut self) -> Result<Statement, ParserError> {
11227-
let modifier =
11228-
self.parse_one_of_keywords(&[Keyword::SESSION, Keyword::LOCAL, Keyword::HIVEVAR]);
11232+
let modifier = self.parse_one_of_keywords(&[
11233+
Keyword::SESSION,
11234+
Keyword::LOCAL,
11235+
Keyword::HIVEVAR,
11236+
Keyword::GLOBAL,
11237+
]);
1122911238

1123011239
if let Some(Keyword::HIVEVAR) = modifier {
1123111240
self.expect_token(&Token::Colon)?;
@@ -11241,7 +11250,7 @@ impl<'a> Parser<'a> {
1124111250
{
1124211251
if self.consume_token(&Token::Eq) || self.parse_keyword(Keyword::TO) {
1124311252
return Ok(Set::SingleAssignment {
11244-
local: modifier == Some(Keyword::LOCAL),
11253+
scope: Self::keyword_to_modifier(modifier),
1124511254
hivevar: modifier == Some(Keyword::HIVEVAR),
1124611255
variable: ObjectName::from(vec!["TIMEZONE".into()]),
1124711256
values: self.parse_set_values(false)?,
@@ -11331,7 +11340,7 @@ impl<'a> Parser<'a> {
1133111340
}?;
1133211341

1133311342
Ok(Set::SingleAssignment {
11334-
local: modifier == Some(Keyword::LOCAL),
11343+
scope: Self::keyword_to_modifier(modifier),
1133511344
hivevar: modifier == Some(Keyword::HIVEVAR),
1133611345
variable,
1133711346
values,
@@ -11359,7 +11368,7 @@ impl<'a> Parser<'a> {
1135911368
if self.consume_token(&Token::Eq) || self.parse_keyword(Keyword::TO) {
1136011369
let stmt = match variables {
1136111370
OneOrManyWithParens::One(var) => Set::SingleAssignment {
11362-
local: modifier == Some(Keyword::LOCAL),
11371+
scope: Self::keyword_to_modifier(modifier),
1136311372
hivevar: modifier == Some(Keyword::HIVEVAR),
1136411373
variable: var,
1136511374
values: self.parse_set_values(false)?,

tests/sqlparser_common.rs

+26-6
Original file line numberDiff line numberDiff line change
@@ -8628,12 +8628,12 @@ fn parse_set_transaction() {
86288628
fn parse_set_variable() {
86298629
match verified_stmt("SET SOMETHING = '1'") {
86308630
Statement::Set(Set::SingleAssignment {
8631-
local,
8631+
scope,
86328632
hivevar,
86338633
variable,
86348634
values,
86358635
}) => {
8636-
assert!(!local);
8636+
assert_eq!(scope, ContextModifier::None);
86378637
assert!(!hivevar);
86388638
assert_eq!(variable, ObjectName::from(vec!["SOMETHING".into()]));
86398639
assert_eq!(
@@ -8646,6 +8646,26 @@ fn parse_set_variable() {
86468646
_ => unreachable!(),
86478647
}
86488648

8649+
match verified_stmt("SET GLOBAL VARIABLE = 'Value'") {
8650+
Statement::Set(Set::SingleAssignment {
8651+
scope,
8652+
hivevar,
8653+
variable,
8654+
values,
8655+
}) => {
8656+
assert_eq!(scope, ContextModifier::Global);
8657+
assert!(!hivevar);
8658+
assert_eq!(variable, ObjectName::from(vec!["VARIABLE".into()]));
8659+
assert_eq!(
8660+
values,
8661+
vec![Expr::Value(
8662+
(Value::SingleQuotedString("Value".into())).with_empty_span()
8663+
)]
8664+
);
8665+
}
8666+
_ => unreachable!(),
8667+
}
8668+
86498669
let multi_variable_dialects = all_dialects_where(|d| d.supports_parenthesized_set_variables());
86508670
let sql = r#"SET (a, b, c) = (1, 2, 3)"#;
86518671
match multi_variable_dialects.verified_stmt(sql) {
@@ -8720,12 +8740,12 @@ fn parse_set_variable() {
87208740
fn parse_set_role_as_variable() {
87218741
match verified_stmt("SET role = 'foobar'") {
87228742
Statement::Set(Set::SingleAssignment {
8723-
local,
8743+
scope,
87248744
hivevar,
87258745
variable,
87268746
values,
87278747
}) => {
8728-
assert!(!local);
8748+
assert_eq!(scope, ContextModifier::None);
87298749
assert!(!hivevar);
87308750
assert_eq!(variable, ObjectName::from(vec!["role".into()]));
87318751
assert_eq!(
@@ -8767,12 +8787,12 @@ fn parse_double_colon_cast_at_timezone() {
87678787
fn parse_set_time_zone() {
87688788
match verified_stmt("SET TIMEZONE = 'UTC'") {
87698789
Statement::Set(Set::SingleAssignment {
8770-
local,
8790+
scope,
87718791
hivevar,
87728792
variable,
87738793
values,
87748794
}) => {
8775-
assert!(!local);
8795+
assert_eq!(scope, ContextModifier::None);
87768796
assert!(!hivevar);
87778797
assert_eq!(variable, ObjectName::from(vec!["TIMEZONE".into()]));
87788798
assert_eq!(

tests/sqlparser_hive.rs

+5-4
Original file line numberDiff line numberDiff line change
@@ -21,9 +21,10 @@
2121
//! is also tested (on the inputs it can handle).
2222
2323
use sqlparser::ast::{
24-
ClusteredBy, CommentDef, CreateFunction, CreateFunctionBody, CreateFunctionUsing, CreateTable,
25-
Expr, Function, FunctionArgumentList, FunctionArguments, Ident, ObjectName, OrderByExpr,
26-
OrderByOptions, SelectItem, Set, Statement, TableFactor, UnaryOperator, Use, Value,
24+
ClusteredBy, CommentDef, ContextModifier, CreateFunction, CreateFunctionBody,
25+
CreateFunctionUsing, CreateTable, Expr, Function, FunctionArgumentList, FunctionArguments,
26+
Ident, ObjectName, OrderByExpr, OrderByOptions, SelectItem, Set, Statement, TableFactor,
27+
UnaryOperator, Use, Value,
2728
};
2829
use sqlparser::dialect::{GenericDialect, HiveDialect, MsSqlDialect};
2930
use sqlparser::parser::ParserError;
@@ -369,7 +370,7 @@ fn set_statement_with_minus() {
369370
assert_eq!(
370371
hive().verified_stmt("SET hive.tez.java.opts = -Xmx4g"),
371372
Statement::Set(Set::SingleAssignment {
372-
local: false,
373+
scope: ContextModifier::None,
373374
hivevar: false,
374375
variable: ObjectName::from(vec![
375376
Ident::new("hive"),

tests/sqlparser_mssql.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -1251,7 +1251,7 @@ fn parse_mssql_declare() {
12511251
}]
12521252
},
12531253
Statement::Set(Set::SingleAssignment {
1254-
local: false,
1254+
scope: ContextModifier::None,
12551255
hivevar: false,
12561256
variable: ObjectName::from(vec![Ident::new("@bar")]),
12571257
values: vec![Expr::Value(

tests/sqlparser_mysql.rs

+1-1
Original file line numberDiff line numberDiff line change
@@ -618,7 +618,7 @@ fn parse_set_variables() {
618618
assert_eq!(
619619
mysql_and_generic().verified_stmt("SET LOCAL autocommit = 1"),
620620
Statement::Set(Set::SingleAssignment {
621-
local: true,
621+
scope: ContextModifier::Local,
622622
hivevar: false,
623623
variable: ObjectName::from(vec!["autocommit".into()]),
624624
values: vec![Expr::value(number("1"))],

tests/sqlparser_postgres.rs

+8-10
Original file line numberDiff line numberDiff line change
@@ -988,8 +988,7 @@ fn parse_create_schema_if_not_exists() {
988988
Statement::CreateSchema {
989989
if_not_exists: true,
990990
schema_name,
991-
options: _,
992-
default_collate_spec: _,
991+
..
993992
} => assert_eq!("schema_name", schema_name.to_string()),
994993
_ => unreachable!(),
995994
}
@@ -1433,7 +1432,7 @@ fn parse_set() {
14331432
assert_eq!(
14341433
stmt,
14351434
Statement::Set(Set::SingleAssignment {
1436-
local: false,
1435+
scope: ContextModifier::None,
14371436
hivevar: false,
14381437
variable: ObjectName::from(vec![Ident::new("a")]),
14391438
values: vec![Expr::Identifier(Ident {
@@ -1448,7 +1447,7 @@ fn parse_set() {
14481447
assert_eq!(
14491448
stmt,
14501449
Statement::Set(Set::SingleAssignment {
1451-
local: false,
1450+
scope: ContextModifier::None,
14521451
hivevar: false,
14531452
variable: ObjectName::from(vec![Ident::new("a")]),
14541453
values: vec![Expr::Value(
@@ -1461,7 +1460,7 @@ fn parse_set() {
14611460
assert_eq!(
14621461
stmt,
14631462
Statement::Set(Set::SingleAssignment {
1464-
local: false,
1463+
scope: ContextModifier::None,
14651464
hivevar: false,
14661465
variable: ObjectName::from(vec![Ident::new("a")]),
14671466
values: vec![Expr::value(number("0"))],
@@ -1472,7 +1471,7 @@ fn parse_set() {
14721471
assert_eq!(
14731472
stmt,
14741473
Statement::Set(Set::SingleAssignment {
1475-
local: false,
1474+
scope: ContextModifier::None,
14761475
hivevar: false,
14771476
variable: ObjectName::from(vec![Ident::new("a")]),
14781477
values: vec![Expr::Identifier(Ident::new("DEFAULT"))],
@@ -1483,7 +1482,7 @@ fn parse_set() {
14831482
assert_eq!(
14841483
stmt,
14851484
Statement::Set(Set::SingleAssignment {
1486-
local: true,
1485+
scope: ContextModifier::Local,
14871486
hivevar: false,
14881487
variable: ObjectName::from(vec![Ident::new("a")]),
14891488
values: vec![Expr::Identifier("b".into())],
@@ -1494,7 +1493,7 @@ fn parse_set() {
14941493
assert_eq!(
14951494
stmt,
14961495
Statement::Set(Set::SingleAssignment {
1497-
local: false,
1496+
scope: ContextModifier::None,
14981497
hivevar: false,
14991498
variable: ObjectName::from(vec![Ident::new("a"), Ident::new("b"), Ident::new("c")]),
15001499
values: vec![Expr::Identifier(Ident {
@@ -1512,7 +1511,7 @@ fn parse_set() {
15121511
assert_eq!(
15131512
stmt,
15141513
Statement::Set(Set::SingleAssignment {
1515-
local: false,
1514+
scope: ContextModifier::None,
15161515
hivevar: false,
15171516
variable: ObjectName::from(vec![
15181517
Ident::new("hive"),
@@ -1526,7 +1525,6 @@ fn parse_set() {
15261525
);
15271526

15281527
pg_and_generic().one_statement_parses_to("SET a TO b", "SET a = b");
1529-
pg_and_generic().one_statement_parses_to("SET SESSION a = b", "SET a = b");
15301528

15311529
assert_eq!(
15321530
pg_and_generic().parse_sql_statements("SET"),

0 commit comments

Comments
 (0)