Skip to content

Commit a907231

Browse files
Allow quoted aliases after BigQuery numeric hyphen segments
1 parent 36bc9a7 commit a907231

3 files changed

Lines changed: 26 additions & 13 deletions

File tree

‎fuzz/fuzz_seeds/bigquery_2620_hyphen_numeric_boundary.sql‎

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,4 +2,5 @@ SELECT * FROM project-1.dataset-2.table-3 WHERE x = 1;
22
SELECT * FROM foo-1;
33
SELECT * FROM (SELECT 1 FROM foo-1);
44
SELECT * FROM foo-1, bar-2;
5-
CREATE TABLE t-1 (a INT64)
5+
CREATE TABLE t-1 (a INT64);
6+
SELECT * FROM foo-1`x`;

‎src/parser/mod.rs‎

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14419,6 +14419,8 @@ impl<'a> Parser<'a> {
1441914419
/// with a digit. Subsequent segments are either must either be valid identifiers or
1442014420
/// integers, e.g. foo-123 is allowed, but foo-123a is not.
1442114421
///
14422+
/// A quoted alias may immediately follow the identifier.
14423+
///
1442214424
/// [BigQuery-lexical](https://cloud.google.com/bigquery/docs/reference/standard-sql/lexical)
1442314425
///
1442414426
/// Return a tuple of the identifier and a boolean indicating it ends with a period.
@@ -14474,10 +14476,16 @@ impl<'a> Parser<'a> {
1447414476
}
1447514477
}
1447614478

14477-
// A word or number butted onto a trailing number glues into it, as in `foo-123a`.
14479+
// An unquoted word or number can extend a trailing number, as in `foo-123a`.
1447814480
if requires_whitespace {
1447914481
let token = self.peek_token_no_skip();
14480-
if matches!(token.token, Token::Word(_) | Token::Number(_, false)) {
14482+
if matches!(
14483+
token.token,
14484+
Token::Word(Word {
14485+
quote_style: None,
14486+
..
14487+
}) | Token::Number(_, false)
14488+
) {
1448114489
return self
1448214490
.expected("whitespace following hyphenated identifier", token);
1448314491
}

‎tests/sqlparser_bigquery.rs‎

Lines changed: 14 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1770,16 +1770,6 @@ fn parse_hyphenated_identifier_after_numeric_segment() {
17701770
),
17711771
err
17721772
);
1773-
1774-
let err = bigquery()
1775-
.parse_sql_statements("SELECT * FROM foo-1`x`")
1776-
.unwrap_err();
1777-
assert_eq!(
1778-
ParserError::ParserError(
1779-
"Expected: whitespace following hyphenated identifier, found: `x`".to_string(),
1780-
),
1781-
err
1782-
);
17831773
}
17841774

17851775
#[test]
@@ -3036,3 +3026,17 @@ fn test_byte_and_raw_string_quote_escaping() {
30363026
err
30373027
);
30383028
}
3029+
3030+
#[test]
3031+
fn parse_table_identifier_with_adjacent_quoted_alias() {
3032+
for table in ["foo", "foo-bar", "foo-1"] {
3033+
let sql = format!("SELECT * FROM {table}`x`");
3034+
let canonical = format!("SELECT * FROM {table} `x`");
3035+
let select = bigquery().verified_only_select_with_canonical(&sql, canonical.as_str());
3036+
let TableFactor::Table { name, alias, .. } = &select.from[0].relation else {
3037+
panic!("Expected a table");
3038+
};
3039+
assert_eq!(name, &ObjectName::from(vec![Ident::new(table)]));
3040+
assert_eq!(alias.as_ref().unwrap().name, Ident::with_quote('`', "x"));
3041+
}
3042+
}

0 commit comments

Comments
 (0)