diff options
author | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-12-23 19:51:10 +0000 |
---|---|---|
committer | Daniel Baumann <daniel.baumann@progress-linux.org> | 2024-12-23 19:51:10 +0000 |
commit | a95fd7b7de8c3492d8267b2007508d579ff50848 (patch) | |
tree | f17b76df363f98cda7ec9e8327e7c78a4c7f7803 /sqlglot/parser.py | |
parent | Releasing debian version 26.0.0-1. (diff) | |
download | sqlglot-a95fd7b7de8c3492d8267b2007508d579ff50848.tar.xz sqlglot-a95fd7b7de8c3492d8267b2007508d579ff50848.zip |
Merging upstream version 26.0.1.
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'sqlglot/parser.py')
-rw-r--r-- | sqlglot/parser.py | 42 |
1 files changed, 26 insertions, 16 deletions
diff --git a/sqlglot/parser.py b/sqlglot/parser.py index 4cd3d30..6e70fa1 100644 --- a/sqlglot/parser.py +++ b/sqlglot/parser.py @@ -920,7 +920,7 @@ class Parser(metaclass=_Parser): exp.StabilityProperty, this=exp.Literal.string("IMMUTABLE") ), "DISTRIBUTED": lambda self: self._parse_distributed_property(), - "DUPLICATE": lambda self: self._parse_duplicate(), + "DUPLICATE": lambda self: self._parse_composite_key_property(exp.DuplicateKeyProperty), "DYNAMIC": lambda self: self.expression(exp.DynamicProperty), "DISTKEY": lambda self: self._parse_distkey(), "DISTSTYLE": lambda self: self._parse_property_assignment(exp.DistStyleProperty), @@ -1143,6 +1143,11 @@ class Parser(metaclass=_Parser): "TRIM": lambda self: self._parse_trim(), "TRY_CAST": lambda self: self._parse_cast(False, safe=True), "TRY_CONVERT": lambda self: self._parse_convert(False, safe=True), + "XMLELEMENT": lambda self: self.expression( + exp.XMLElement, + this=self._match_text_seq("NAME") and self._parse_id_var(), + expressions=self._match(TokenType.COMMA) and self._parse_csv(self._parse_expression), + ), } QUERY_MODIFIER_PARSERS = { @@ -2203,10 +2208,10 @@ class Parser(metaclass=_Parser): order=self._parse_order(), ) - def _parse_duplicate(self) -> exp.DuplicateKeyProperty: + def _parse_composite_key_property(self, expr_type: t.Type[E]) -> E: self._match_text_seq("KEY") - expressions = self._parse_wrapped_csv(self._parse_id_var, optional=False) - return self.expression(exp.DuplicateKeyProperty, expressions=expressions) + expressions = self._parse_wrapped_id_vars() + return self.expression(expr_type, expressions=expressions) def _parse_with_property(self) -> t.Optional[exp.Expression] | t.List[exp.Expression]: if self._match_text_seq("(", "SYSTEM_VERSIONING"): @@ -4615,14 +4620,14 @@ class Parser(metaclass=_Parser): this = exp.Literal.string(this.to_py()) elif this and this.is_string: parts = exp.INTERVAL_STRING_RE.findall(this.name) - if len(parts) == 1: - if unit: - # Unconsume the eagerly-parsed unit, since the real unit was part of the string - self._retreat(self._index - 1) + if parts and unit: + # Unconsume the eagerly-parsed unit, since the real unit was part of the string + unit = None + self._retreat(self._index - 1) + if len(parts) == 1: this = exp.Literal.string(parts[0][0]) unit = self.expression(exp.Var, this=parts[0][1].upper()) - if self.INTERVAL_SPANS and self._match_text_seq("TO"): unit = self.expression( exp.IntervalSpan, this=unit, expression=self._parse_var(any_token=True, upper=True) @@ -5351,18 +5356,21 @@ class Parser(metaclass=_Parser): functions = self.FUNCTIONS function = functions.get(upper) + known_function = function and not anonymous - alias = upper in self.FUNCTIONS_WITH_ALIASED_ARGS + alias = not known_function or upper in self.FUNCTIONS_WITH_ALIASED_ARGS args = self._parse_csv(lambda: self._parse_lambda(alias=alias)) - if alias: + if alias and known_function: args = self._kv_to_prop_eq(args) - if function and not anonymous: - if "dialect" in function.__code__.co_varnames: - func = function(args, dialect=self.dialect) + if known_function: + func_builder = t.cast(t.Callable, function) + + if "dialect" in func_builder.__code__.co_varnames: + func = func_builder(args, dialect=self.dialect) else: - func = function(args) + func = func_builder(args) func = self.validate_expression(func, args) if self.dialect.PRESERVE_ORIGINAL_NAMES: @@ -6730,7 +6738,9 @@ class Parser(metaclass=_Parser): def _parse_select_or_expression(self, alias: bool = False) -> t.Optional[exp.Expression]: return self._parse_select() or self._parse_set_operations( - self._parse_expression() if alias else self._parse_assignment() + self._parse_alias(self._parse_assignment(), explicit=True) + if alias + else self._parse_assignment() ) def _parse_ddl_select(self) -> t.Optional[exp.Expression]: |