diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2023-08-10 09:23:46 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2023-08-10 09:23:46 +0000 |
commit | 5dde903f4f6659e384287a3e508b9f369c5a2ba3 (patch) | |
tree | 05cd2920d82f0023f6ac695dbb6eaeef64608401 /sqlglot/parser.py | |
parent | Adding upstream version 17.9.1. (diff) | |
download | sqlglot-5dde903f4f6659e384287a3e508b9f369c5a2ba3.tar.xz sqlglot-5dde903f4f6659e384287a3e508b9f369c5a2ba3.zip |
Adding upstream version 17.11.0.upstream/17.11.0
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'sqlglot/parser.py')
-rw-r--r-- | sqlglot/parser.py | 58 |
1 files changed, 38 insertions, 20 deletions
diff --git a/sqlglot/parser.py b/sqlglot/parser.py index f714c8d..35a1744 100644 --- a/sqlglot/parser.py +++ b/sqlglot/parser.py @@ -248,7 +248,6 @@ class Parser(metaclass=_Parser): TokenType.FILTER, TokenType.FORMAT, TokenType.FULL, - TokenType.IF, TokenType.IS, TokenType.ISNULL, TokenType.INTERVAL, @@ -708,14 +707,10 @@ class Parser(metaclass=_Parser): SCHEMA_UNNAMED_CONSTRAINTS = {"CHECK", "FOREIGN KEY", "LIKE", "PRIMARY KEY", "UNIQUE"} NO_PAREN_FUNCTION_PARSERS = { - TokenType.ANY: lambda self: self.expression(exp.Any, this=self._parse_bitwise()), - TokenType.CASE: lambda self: self._parse_case(), - TokenType.IF: lambda self: self._parse_if(), - TokenType.NEXT_VALUE_FOR: lambda self: self.expression( - exp.NextValueFor, - this=self._parse_column(), - order=self._match(TokenType.OVER) and self._parse_wrapped(self._parse_order), - ), + "ANY": lambda self: self.expression(exp.Any, this=self._parse_bitwise()), + "CASE": lambda self: self._parse_case(), + "IF": lambda self: self._parse_if(), + "NEXT": lambda self: self._parse_next_value_for(), } FUNCTIONS_WITH_ALIASED_ARGS = {"STRUCT"} @@ -1162,7 +1157,7 @@ class Parser(metaclass=_Parser): def _parse_exists(self, not_: bool = False) -> t.Optional[bool]: return ( - self._match(TokenType.IF) + self._match_text_seq("IF") and (not not_ or self._match(TokenType.NOT)) and self._match(TokenType.EXISTS) ) @@ -1935,6 +1930,9 @@ class Parser(metaclass=_Parser): # https://prestodb.io/docs/current/sql/values.html return self.expression(exp.Tuple, expressions=[self._parse_conjunction()]) + def _parse_projections(self) -> t.List[t.Optional[exp.Expression]]: + return self._parse_expressions() + def _parse_select( self, nested: bool = False, table: bool = False, parse_subquery_alias: bool = True ) -> t.Optional[exp.Expression]: @@ -1974,14 +1972,14 @@ class Parser(metaclass=_Parser): self.raise_error("Cannot specify both ALL and DISTINCT after SELECT") limit = self._parse_limit(top=True) - expressions = self._parse_expressions() + projections = self._parse_projections() this = self.expression( exp.Select, kind=kind, hint=hint, distinct=distinct, - expressions=expressions, + expressions=projections, limit=limit, ) this.comments = comments @@ -3021,8 +3019,12 @@ class Parser(metaclass=_Parser): while True: if self._match_set(self.BITWISE): this = self.expression( - self.BITWISE[self._prev.token_type], this=this, expression=self._parse_term() + self.BITWISE[self._prev.token_type], + this=this, + expression=self._parse_term(), ) + elif self._match(TokenType.DQMARK): + this = self.expression(exp.Coalesce, this=this, expressions=self._parse_term()) elif self._match_pair(TokenType.LT, TokenType.LT): this = self.expression( exp.BitwiseLeftShift, this=this, expression=self._parse_term() @@ -3322,9 +3324,13 @@ class Parser(metaclass=_Parser): return None token_type = self._curr.token_type + this = self._curr.text + upper = this.upper() - if optional_parens and self._match_set(self.NO_PAREN_FUNCTION_PARSERS): - return self.NO_PAREN_FUNCTION_PARSERS[token_type](self) + parser = self.NO_PAREN_FUNCTION_PARSERS.get(upper) + if optional_parens and parser: + self._advance() + return parser(self) if not self._next or self._next.token_type != TokenType.L_PAREN: if optional_parens and token_type in self.NO_PAREN_FUNCTIONS: @@ -3336,12 +3342,9 @@ class Parser(metaclass=_Parser): if token_type not in self.FUNC_TOKENS: return None - this = self._curr.text - upper = this.upper() self._advance(2) parser = self.FUNCTION_PARSERS.get(upper) - if parser and not anonymous: this = parser(self) else: @@ -3368,7 +3371,7 @@ class Parser(metaclass=_Parser): else: this = self.expression(exp.Anonymous, this=this, expressions=args) - self._match(TokenType.R_PAREN, expression=this) + self._match_r_paren(this) return self._parse_window(this) def _parse_function_parameter(self) -> t.Optional[exp.Expression]: @@ -3703,7 +3706,11 @@ class Parser(metaclass=_Parser): self.expression(exp.Slice, expression=self._parse_conjunction()) ] else: - expressions = self._parse_csv(lambda: self._parse_slice(self._parse_conjunction())) + expressions = self._parse_csv( + lambda: self._parse_slice( + self._parse_alias(self._parse_conjunction(), explicit=True) + ) + ) # https://duckdb.org/docs/sql/data_types/struct.html#creating-structs if bracket_kind == TokenType.L_BRACE: @@ -3770,6 +3777,17 @@ class Parser(metaclass=_Parser): return self._parse_window(this) + def _parse_next_value_for(self) -> t.Optional[exp.Expression]: + if not self._match_text_seq("VALUE", "FOR"): + self._retreat(self._index - 1) + return None + + return self.expression( + exp.NextValueFor, + this=self._parse_column(), + order=self._match(TokenType.OVER) and self._parse_wrapped(self._parse_order), + ) + def _parse_extract(self) -> exp.Extract: this = self._parse_function() or self._parse_var() or self._parse_type() |