Edit on GitHub

Expressions

Every AST node in SQLGlot is represented by a subclass of Expression.

This module contains the implementation of all supported Expression types. Additionally, it exposes a number of helper functions, which are mainly used to programmatically build SQL expressions, such as select.


   1"""
   2## Expressions
   3
   4Every AST node in SQLGlot is represented by a subclass of `Expression`.
   5
   6This module contains the implementation of all supported `Expression` types. Additionally,
   7it exposes a number of helper functions, which are mainly used to programmatically build
   8SQL expressions, such as `sqlglot.expressions.select`.
   9
  10----
  11"""
  12
  13from __future__ import annotations
  14
  15import datetime
  16import math
  17import numbers
  18import re
  19import textwrap
  20import typing as t
  21from collections import deque
  22from copy import deepcopy
  23from enum import auto
  24from functools import reduce
  25
  26from sqlglot.errors import ErrorLevel, ParseError
  27from sqlglot.helper import (
  28    AutoName,
  29    camel_to_snake_case,
  30    ensure_collection,
  31    ensure_list,
  32    is_int,
  33    seq_get,
  34    subclasses,
  35)
  36from sqlglot.tokens import Token
  37
  38if t.TYPE_CHECKING:
  39    from sqlglot._typing import E, Lit
  40    from sqlglot.dialects.dialect import DialectType
  41
  42    Q = t.TypeVar("Q", bound="Query")
  43
  44
  45class _Expression(type):
  46    def __new__(cls, clsname, bases, attrs):
  47        klass = super().__new__(cls, clsname, bases, attrs)
  48
  49        # When an Expression class is created, its key is automatically set to be
  50        # the lowercase version of the class' name.
  51        klass.key = clsname.lower()
  52
  53        # This is so that docstrings are not inherited in pdoc
  54        klass.__doc__ = klass.__doc__ or ""
  55
  56        return klass
  57
  58
  59SQLGLOT_META = "sqlglot.meta"
  60TABLE_PARTS = ("this", "db", "catalog")
  61COLUMN_PARTS = ("this", "table", "db", "catalog")
  62
  63
  64class Expression(metaclass=_Expression):
  65    """
  66    The base class for all expressions in a syntax tree. Each Expression encapsulates any necessary
  67    context, such as its child expressions, their names (arg keys), and whether a given child expression
  68    is optional or not.
  69
  70    Attributes:
  71        key: a unique key for each class in the Expression hierarchy. This is useful for hashing
  72            and representing expressions as strings.
  73        arg_types: determines the arguments (child nodes) supported by an expression. It maps
  74            arg keys to booleans that indicate whether the corresponding args are optional.
  75        parent: a reference to the parent expression (or None, in case of root expressions).
  76        arg_key: the arg key an expression is associated with, i.e. the name its parent expression
  77            uses to refer to it.
  78        index: the index of an expression if it is inside of a list argument in its parent.
  79        comments: a list of comments that are associated with a given expression. This is used in
  80            order to preserve comments when transpiling SQL code.
  81        type: the `sqlglot.expressions.DataType` type of an expression. This is inferred by the
  82            optimizer, in order to enable some transformations that require type information.
  83        meta: a dictionary that can be used to store useful metadata for a given expression.
  84
  85    Example:
  86        >>> class Foo(Expression):
  87        ...     arg_types = {"this": True, "expression": False}
  88
  89        The above definition informs us that Foo is an Expression that requires an argument called
  90        "this" and may also optionally receive an argument called "expression".
  91
  92    Args:
  93        args: a mapping used for retrieving the arguments of an expression, given their arg keys.
  94    """
  95
  96    key = "expression"
  97    arg_types = {"this": True}
  98    __slots__ = ("args", "parent", "arg_key", "index", "comments", "_type", "_meta", "_hash")
  99
 100    def __init__(self, **args: t.Any):
 101        self.args: t.Dict[str, t.Any] = args
 102        self.parent: t.Optional[Expression] = None
 103        self.arg_key: t.Optional[str] = None
 104        self.index: t.Optional[int] = None
 105        self.comments: t.Optional[t.List[str]] = None
 106        self._type: t.Optional[DataType] = None
 107        self._meta: t.Optional[t.Dict[str, t.Any]] = None
 108        self._hash: t.Optional[int] = None
 109
 110        for arg_key, value in self.args.items():
 111            self._set_parent(arg_key, value)
 112
 113    def __eq__(self, other) -> bool:
 114        return type(self) is type(other) and hash(self) == hash(other)
 115
 116    @property
 117    def hashable_args(self) -> t.Any:
 118        return frozenset(
 119            (k, tuple(_norm_arg(a) for a in v) if type(v) is list else _norm_arg(v))
 120            for k, v in self.args.items()
 121            if not (v is None or v is False or (type(v) is list and not v))
 122        )
 123
 124    def __hash__(self) -> int:
 125        if self._hash is not None:
 126            return self._hash
 127
 128        return hash((self.__class__, self.hashable_args))
 129
 130    @property
 131    def this(self) -> t.Any:
 132        """
 133        Retrieves the argument with key "this".
 134        """
 135        return self.args.get("this")
 136
 137    @property
 138    def expression(self) -> t.Any:
 139        """
 140        Retrieves the argument with key "expression".
 141        """
 142        return self.args.get("expression")
 143
 144    @property
 145    def expressions(self) -> t.List[t.Any]:
 146        """
 147        Retrieves the argument with key "expressions".
 148        """
 149        return self.args.get("expressions") or []
 150
 151    def text(self, key) -> str:
 152        """
 153        Returns a textual representation of the argument corresponding to "key". This can only be used
 154        for args that are strings or leaf Expression instances, such as identifiers and literals.
 155        """
 156        field = self.args.get(key)
 157        if isinstance(field, str):
 158            return field
 159        if isinstance(field, (Identifier, Literal, Var)):
 160            return field.this
 161        if isinstance(field, (Star, Null)):
 162            return field.name
 163        return ""
 164
 165    @property
 166    def is_string(self) -> bool:
 167        """
 168        Checks whether a Literal expression is a string.
 169        """
 170        return isinstance(self, Literal) and self.args["is_string"]
 171
 172    @property
 173    def is_number(self) -> bool:
 174        """
 175        Checks whether a Literal expression is a number.
 176        """
 177        return isinstance(self, Literal) and not self.args["is_string"]
 178
 179    @property
 180    def is_negative(self) -> bool:
 181        """
 182        Checks whether an expression is negative.
 183
 184        Handles both exp.Neg and Literal numbers with "-" which come from optimizer.simplify.
 185        """
 186        return isinstance(self, Neg) or (self.is_number and self.this.startswith("-"))
 187
 188    @property
 189    def is_int(self) -> bool:
 190        """
 191        Checks whether a Literal expression is an integer.
 192        """
 193        return self.is_number and is_int(self.name)
 194
 195    @property
 196    def is_star(self) -> bool:
 197        """Checks whether an expression is a star."""
 198        return isinstance(self, Star) or (isinstance(self, Column) and isinstance(self.this, Star))
 199
 200    @property
 201    def alias(self) -> str:
 202        """
 203        Returns the alias of the expression, or an empty string if it's not aliased.
 204        """
 205        if isinstance(self.args.get("alias"), TableAlias):
 206            return self.args["alias"].name
 207        return self.text("alias")
 208
 209    @property
 210    def alias_column_names(self) -> t.List[str]:
 211        table_alias = self.args.get("alias")
 212        if not table_alias:
 213            return []
 214        return [c.name for c in table_alias.args.get("columns") or []]
 215
 216    @property
 217    def name(self) -> str:
 218        return self.text("this")
 219
 220    @property
 221    def alias_or_name(self) -> str:
 222        return self.alias or self.name
 223
 224    @property
 225    def output_name(self) -> str:
 226        """
 227        Name of the output column if this expression is a selection.
 228
 229        If the Expression has no output name, an empty string is returned.
 230
 231        Example:
 232            >>> from sqlglot import parse_one
 233            >>> parse_one("SELECT a").expressions[0].output_name
 234            'a'
 235            >>> parse_one("SELECT b AS c").expressions[0].output_name
 236            'c'
 237            >>> parse_one("SELECT 1 + 2").expressions[0].output_name
 238            ''
 239        """
 240        return ""
 241
 242    @property
 243    def type(self) -> t.Optional[DataType]:
 244        return self._type
 245
 246    @type.setter
 247    def type(self, dtype: t.Optional[DataType | DataType.Type | str]) -> None:
 248        if dtype and not isinstance(dtype, DataType):
 249            dtype = DataType.build(dtype)
 250        self._type = dtype  # type: ignore
 251
 252    def is_type(self, *dtypes) -> bool:
 253        return self.type is not None and self.type.is_type(*dtypes)
 254
 255    def is_leaf(self) -> bool:
 256        return not any(isinstance(v, (Expression, list)) for v in self.args.values())
 257
 258    @property
 259    def meta(self) -> t.Dict[str, t.Any]:
 260        if self._meta is None:
 261            self._meta = {}
 262        return self._meta
 263
 264    def __deepcopy__(self, memo):
 265        root = self.__class__()
 266        stack = [(self, root)]
 267
 268        while stack:
 269            node, copy = stack.pop()
 270
 271            if node.comments is not None:
 272                copy.comments = deepcopy(node.comments)
 273            if node._type is not None:
 274                copy._type = deepcopy(node._type)
 275            if node._meta is not None:
 276                copy._meta = deepcopy(node._meta)
 277            if node._hash is not None:
 278                copy._hash = node._hash
 279
 280            for k, vs in node.args.items():
 281                if hasattr(vs, "parent"):
 282                    stack.append((vs, vs.__class__()))
 283                    copy.set(k, stack[-1][-1])
 284                elif type(vs) is list:
 285                    copy.args[k] = []
 286
 287                    for v in vs:
 288                        if hasattr(v, "parent"):
 289                            stack.append((v, v.__class__()))
 290                            copy.append(k, stack[-1][-1])
 291                        else:
 292                            copy.append(k, v)
 293                else:
 294                    copy.args[k] = vs
 295
 296        return root
 297
 298    def copy(self):
 299        """
 300        Returns a deep copy of the expression.
 301        """
 302        return deepcopy(self)
 303
 304    def add_comments(self, comments: t.Optional[t.List[str]] = None) -> None:
 305        if self.comments is None:
 306            self.comments = []
 307
 308        if comments:
 309            for comment in comments:
 310                _, *meta = comment.split(SQLGLOT_META)
 311                if meta:
 312                    for kv in "".join(meta).split(","):
 313                        k, *v = kv.split("=")
 314                        value = v[0].strip() if v else True
 315                        self.meta[k.strip()] = value
 316                self.comments.append(comment)
 317
 318    def pop_comments(self) -> t.List[str]:
 319        comments = self.comments or []
 320        self.comments = None
 321        return comments
 322
 323    def append(self, arg_key: str, value: t.Any) -> None:
 324        """
 325        Appends value to arg_key if it's a list or sets it as a new list.
 326
 327        Args:
 328            arg_key (str): name of the list expression arg
 329            value (Any): value to append to the list
 330        """
 331        if type(self.args.get(arg_key)) is not list:
 332            self.args[arg_key] = []
 333        self._set_parent(arg_key, value)
 334        values = self.args[arg_key]
 335        if hasattr(value, "parent"):
 336            value.index = len(values)
 337        values.append(value)
 338
 339    def set(self, arg_key: str, value: t.Any, index: t.Optional[int] = None) -> None:
 340        """
 341        Sets arg_key to value.
 342
 343        Args:
 344            arg_key: name of the expression arg.
 345            value: value to set the arg to.
 346            index: if the arg is a list, this specifies what position to add the value in it.
 347        """
 348        if index is not None:
 349            expressions = self.args.get(arg_key) or []
 350
 351            if seq_get(expressions, index) is None:
 352                return
 353            if value is None:
 354                expressions.pop(index)
 355                for v in expressions[index:]:
 356                    v.index = v.index - 1
 357                return
 358
 359            if isinstance(value, list):
 360                expressions.pop(index)
 361                expressions[index:index] = value
 362            else:
 363                expressions[index] = value
 364
 365            value = expressions
 366        elif value is None:
 367            self.args.pop(arg_key, None)
 368            return
 369
 370        self.args[arg_key] = value
 371        self._set_parent(arg_key, value, index)
 372
 373    def _set_parent(self, arg_key: str, value: t.Any, index: t.Optional[int] = None) -> None:
 374        if hasattr(value, "parent"):
 375            value.parent = self
 376            value.arg_key = arg_key
 377            value.index = index
 378        elif type(value) is list:
 379            for index, v in enumerate(value):
 380                if hasattr(v, "parent"):
 381                    v.parent = self
 382                    v.arg_key = arg_key
 383                    v.index = index
 384
 385    @property
 386    def depth(self) -> int:
 387        """
 388        Returns the depth of this tree.
 389        """
 390        if self.parent:
 391            return self.parent.depth + 1
 392        return 0
 393
 394    def iter_expressions(self, reverse: bool = False) -> t.Iterator[Expression]:
 395        """Yields the key and expression for all arguments, exploding list args."""
 396        # remove tuple when python 3.7 is deprecated
 397        for vs in reversed(tuple(self.args.values())) if reverse else self.args.values():
 398            if type(vs) is list:
 399                for v in reversed(vs) if reverse else vs:
 400                    if hasattr(v, "parent"):
 401                        yield v
 402            else:
 403                if hasattr(vs, "parent"):
 404                    yield vs
 405
 406    def find(self, *expression_types: t.Type[E], bfs: bool = True) -> t.Optional[E]:
 407        """
 408        Returns the first node in this tree which matches at least one of
 409        the specified types.
 410
 411        Args:
 412            expression_types: the expression type(s) to match.
 413            bfs: whether to search the AST using the BFS algorithm (DFS is used if false).
 414
 415        Returns:
 416            The node which matches the criteria or None if no such node was found.
 417        """
 418        return next(self.find_all(*expression_types, bfs=bfs), None)
 419
 420    def find_all(self, *expression_types: t.Type[E], bfs: bool = True) -> t.Iterator[E]:
 421        """
 422        Returns a generator object which visits all nodes in this tree and only
 423        yields those that match at least one of the specified expression types.
 424
 425        Args:
 426            expression_types: the expression type(s) to match.
 427            bfs: whether to search the AST using the BFS algorithm (DFS is used if false).
 428
 429        Returns:
 430            The generator object.
 431        """
 432        for expression in self.walk(bfs=bfs):
 433            if isinstance(expression, expression_types):
 434                yield expression
 435
 436    def find_ancestor(self, *expression_types: t.Type[E]) -> t.Optional[E]:
 437        """
 438        Returns a nearest parent matching expression_types.
 439
 440        Args:
 441            expression_types: the expression type(s) to match.
 442
 443        Returns:
 444            The parent node.
 445        """
 446        ancestor = self.parent
 447        while ancestor and not isinstance(ancestor, expression_types):
 448            ancestor = ancestor.parent
 449        return ancestor  # type: ignore
 450
 451    @property
 452    def parent_select(self) -> t.Optional[Select]:
 453        """
 454        Returns the parent select statement.
 455        """
 456        return self.find_ancestor(Select)
 457
 458    @property
 459    def same_parent(self) -> bool:
 460        """Returns if the parent is the same class as itself."""
 461        return type(self.parent) is self.__class__
 462
 463    def root(self) -> Expression:
 464        """
 465        Returns the root expression of this tree.
 466        """
 467        expression = self
 468        while expression.parent:
 469            expression = expression.parent
 470        return expression
 471
 472    def walk(
 473        self, bfs: bool = True, prune: t.Optional[t.Callable[[Expression], bool]] = None
 474    ) -> t.Iterator[Expression]:
 475        """
 476        Returns a generator object which visits all nodes in this tree.
 477
 478        Args:
 479            bfs: if set to True the BFS traversal order will be applied,
 480                otherwise the DFS traversal will be used instead.
 481            prune: callable that returns True if the generator should stop traversing
 482                this branch of the tree.
 483
 484        Returns:
 485            the generator object.
 486        """
 487        if bfs:
 488            yield from self.bfs(prune=prune)
 489        else:
 490            yield from self.dfs(prune=prune)
 491
 492    def dfs(
 493        self, prune: t.Optional[t.Callable[[Expression], bool]] = None
 494    ) -> t.Iterator[Expression]:
 495        """
 496        Returns a generator object which visits all nodes in this tree in
 497        the DFS (Depth-first) order.
 498
 499        Returns:
 500            The generator object.
 501        """
 502        stack = [self]
 503
 504        while stack:
 505            node = stack.pop()
 506
 507            yield node
 508
 509            if prune and prune(node):
 510                continue
 511
 512            for v in node.iter_expressions(reverse=True):
 513                stack.append(v)
 514
 515    def bfs(
 516        self, prune: t.Optional[t.Callable[[Expression], bool]] = None
 517    ) -> t.Iterator[Expression]:
 518        """
 519        Returns a generator object which visits all nodes in this tree in
 520        the BFS (Breadth-first) order.
 521
 522        Returns:
 523            The generator object.
 524        """
 525        queue = deque([self])
 526
 527        while queue:
 528            node = queue.popleft()
 529
 530            yield node
 531
 532            if prune and prune(node):
 533                continue
 534
 535            for v in node.iter_expressions():
 536                queue.append(v)
 537
 538    def unnest(self):
 539        """
 540        Returns the first non parenthesis child or self.
 541        """
 542        expression = self
 543        while type(expression) is Paren:
 544            expression = expression.this
 545        return expression
 546
 547    def unalias(self):
 548        """
 549        Returns the inner expression if this is an Alias.
 550        """
 551        if isinstance(self, Alias):
 552            return self.this
 553        return self
 554
 555    def unnest_operands(self):
 556        """
 557        Returns unnested operands as a tuple.
 558        """
 559        return tuple(arg.unnest() for arg in self.iter_expressions())
 560
 561    def flatten(self, unnest=True):
 562        """
 563        Returns a generator which yields child nodes whose parents are the same class.
 564
 565        A AND B AND C -> [A, B, C]
 566        """
 567        for node in self.dfs(prune=lambda n: n.parent and type(n) is not self.__class__):
 568            if type(node) is not self.__class__:
 569                yield node.unnest() if unnest and not isinstance(node, Subquery) else node
 570
 571    def __str__(self) -> str:
 572        return self.sql()
 573
 574    def __repr__(self) -> str:
 575        return _to_s(self)
 576
 577    def to_s(self) -> str:
 578        """
 579        Same as __repr__, but includes additional information which can be useful
 580        for debugging, like empty or missing args and the AST nodes' object IDs.
 581        """
 582        return _to_s(self, verbose=True)
 583
 584    def sql(self, dialect: DialectType = None, **opts) -> str:
 585        """
 586        Returns SQL string representation of this tree.
 587
 588        Args:
 589            dialect: the dialect of the output SQL string (eg. "spark", "hive", "presto", "mysql").
 590            opts: other `sqlglot.generator.Generator` options.
 591
 592        Returns:
 593            The SQL string.
 594        """
 595        from sqlglot.dialects import Dialect
 596
 597        return Dialect.get_or_raise(dialect).generate(self, **opts)
 598
 599    def transform(self, fun: t.Callable, *args: t.Any, copy: bool = True, **kwargs) -> Expression:
 600        """
 601        Visits all tree nodes (excluding already transformed ones)
 602        and applies the given transformation function to each node.
 603
 604        Args:
 605            fun: a function which takes a node as an argument and returns a
 606                new transformed node or the same node without modifications. If the function
 607                returns None, then the corresponding node will be removed from the syntax tree.
 608            copy: if set to True a new tree instance is constructed, otherwise the tree is
 609                modified in place.
 610
 611        Returns:
 612            The transformed tree.
 613        """
 614        root = None
 615        new_node = None
 616
 617        for node in (self.copy() if copy else self).dfs(prune=lambda n: n is not new_node):
 618            parent, arg_key, index = node.parent, node.arg_key, node.index
 619            new_node = fun(node, *args, **kwargs)
 620
 621            if not root:
 622                root = new_node
 623            elif new_node is not node:
 624                parent.set(arg_key, new_node, index)
 625
 626        assert root
 627        return root.assert_is(Expression)
 628
 629    @t.overload
 630    def replace(self, expression: E) -> E: ...
 631
 632    @t.overload
 633    def replace(self, expression: None) -> None: ...
 634
 635    def replace(self, expression):
 636        """
 637        Swap out this expression with a new expression.
 638
 639        For example::
 640
 641            >>> tree = Select().select("x").from_("tbl")
 642            >>> tree.find(Column).replace(column("y"))
 643            Column(
 644              this=Identifier(this=y, quoted=False))
 645            >>> tree.sql()
 646            'SELECT y FROM tbl'
 647
 648        Args:
 649            expression: new node
 650
 651        Returns:
 652            The new expression or expressions.
 653        """
 654        parent = self.parent
 655
 656        if not parent or parent is expression:
 657            return expression
 658
 659        key = self.arg_key
 660        value = parent.args.get(key)
 661
 662        if type(expression) is list and isinstance(value, Expression):
 663            # We are trying to replace an Expression with a list, so it's assumed that
 664            # the intention was to really replace the parent of this expression.
 665            value.parent.replace(expression)
 666        else:
 667            parent.set(key, expression, self.index)
 668
 669        if expression is not self:
 670            self.parent = None
 671            self.arg_key = None
 672            self.index = None
 673
 674        return expression
 675
 676    def pop(self: E) -> E:
 677        """
 678        Remove this expression from its AST.
 679
 680        Returns:
 681            The popped expression.
 682        """
 683        self.replace(None)
 684        return self
 685
 686    def assert_is(self, type_: t.Type[E]) -> E:
 687        """
 688        Assert that this `Expression` is an instance of `type_`.
 689
 690        If it is NOT an instance of `type_`, this raises an assertion error.
 691        Otherwise, this returns this expression.
 692
 693        Examples:
 694            This is useful for type security in chained expressions:
 695
 696            >>> import sqlglot
 697            >>> sqlglot.parse_one("SELECT x from y").assert_is(Select).select("z").sql()
 698            'SELECT x, z FROM y'
 699        """
 700        if not isinstance(self, type_):
 701            raise AssertionError(f"{self} is not {type_}.")
 702        return self
 703
 704    def error_messages(self, args: t.Optional[t.Sequence] = None) -> t.List[str]:
 705        """
 706        Checks if this expression is valid (e.g. all mandatory args are set).
 707
 708        Args:
 709            args: a sequence of values that were used to instantiate a Func expression. This is used
 710                to check that the provided arguments don't exceed the function argument limit.
 711
 712        Returns:
 713            A list of error messages for all possible errors that were found.
 714        """
 715        errors: t.List[str] = []
 716
 717        for k in self.args:
 718            if k not in self.arg_types:
 719                errors.append(f"Unexpected keyword: '{k}' for {self.__class__}")
 720        for k, mandatory in self.arg_types.items():
 721            v = self.args.get(k)
 722            if mandatory and (v is None or (isinstance(v, list) and not v)):
 723                errors.append(f"Required keyword: '{k}' missing for {self.__class__}")
 724
 725        if (
 726            args
 727            and isinstance(self, Func)
 728            and len(args) > len(self.arg_types)
 729            and not self.is_var_len_args
 730        ):
 731            errors.append(
 732                f"The number of provided arguments ({len(args)}) is greater than "
 733                f"the maximum number of supported arguments ({len(self.arg_types)})"
 734            )
 735
 736        return errors
 737
 738    def dump(self):
 739        """
 740        Dump this Expression to a JSON-serializable dict.
 741        """
 742        from sqlglot.serde import dump
 743
 744        return dump(self)
 745
 746    @classmethod
 747    def load(cls, obj):
 748        """
 749        Load a dict (as returned by `Expression.dump`) into an Expression instance.
 750        """
 751        from sqlglot.serde import load
 752
 753        return load(obj)
 754
 755    def and_(
 756        self,
 757        *expressions: t.Optional[ExpOrStr],
 758        dialect: DialectType = None,
 759        copy: bool = True,
 760        **opts,
 761    ) -> Condition:
 762        """
 763        AND this condition with one or multiple expressions.
 764
 765        Example:
 766            >>> condition("x=1").and_("y=1").sql()
 767            'x = 1 AND y = 1'
 768
 769        Args:
 770            *expressions: the SQL code strings to parse.
 771                If an `Expression` instance is passed, it will be used as-is.
 772            dialect: the dialect used to parse the input expression.
 773            copy: whether to copy the involved expressions (only applies to Expressions).
 774            opts: other options to use to parse the input expressions.
 775
 776        Returns:
 777            The new And condition.
 778        """
 779        return and_(self, *expressions, dialect=dialect, copy=copy, **opts)
 780
 781    def or_(
 782        self,
 783        *expressions: t.Optional[ExpOrStr],
 784        dialect: DialectType = None,
 785        copy: bool = True,
 786        **opts,
 787    ) -> Condition:
 788        """
 789        OR this condition with one or multiple expressions.
 790
 791        Example:
 792            >>> condition("x=1").or_("y=1").sql()
 793            'x = 1 OR y = 1'
 794
 795        Args:
 796            *expressions: the SQL code strings to parse.
 797                If an `Expression` instance is passed, it will be used as-is.
 798            dialect: the dialect used to parse the input expression.
 799            copy: whether to copy the involved expressions (only applies to Expressions).
 800            opts: other options to use to parse the input expressions.
 801
 802        Returns:
 803            The new Or condition.
 804        """
 805        return or_(self, *expressions, dialect=dialect, copy=copy, **opts)
 806
 807    def not_(self, copy: bool = True):
 808        """
 809        Wrap this condition with NOT.
 810
 811        Example:
 812            >>> condition("x=1").not_().sql()
 813            'NOT x = 1'
 814
 815        Args:
 816            copy: whether to copy this object.
 817
 818        Returns:
 819            The new Not instance.
 820        """
 821        return not_(self, copy=copy)
 822
 823    def as_(
 824        self,
 825        alias: str | Identifier,
 826        quoted: t.Optional[bool] = None,
 827        dialect: DialectType = None,
 828        copy: bool = True,
 829        **opts,
 830    ) -> Alias:
 831        return alias_(self, alias, quoted=quoted, dialect=dialect, copy=copy, **opts)
 832
 833    def _binop(self, klass: t.Type[E], other: t.Any, reverse: bool = False) -> E:
 834        this = self.copy()
 835        other = convert(other, copy=True)
 836        if not isinstance(this, klass) and not isinstance(other, klass):
 837            this = _wrap(this, Binary)
 838            other = _wrap(other, Binary)
 839        if reverse:
 840            return klass(this=other, expression=this)
 841        return klass(this=this, expression=other)
 842
 843    def __getitem__(self, other: ExpOrStr | t.Tuple[ExpOrStr]) -> Bracket:
 844        return Bracket(
 845            this=self.copy(), expressions=[convert(e, copy=True) for e in ensure_list(other)]
 846        )
 847
 848    def __iter__(self) -> t.Iterator:
 849        if "expressions" in self.arg_types:
 850            return iter(self.args.get("expressions") or [])
 851        # We define this because __getitem__ converts Expression into an iterable, which is
 852        # problematic because one can hit infinite loops if they do "for x in some_expr: ..."
 853        # See: https://peps.python.org/pep-0234/
 854        raise TypeError(f"'{self.__class__.__name__}' object is not iterable")
 855
 856    def isin(
 857        self,
 858        *expressions: t.Any,
 859        query: t.Optional[ExpOrStr] = None,
 860        unnest: t.Optional[ExpOrStr] | t.Collection[ExpOrStr] = None,
 861        copy: bool = True,
 862        **opts,
 863    ) -> In:
 864        subquery = maybe_parse(query, copy=copy, **opts) if query else None
 865        if subquery and not isinstance(subquery, Subquery):
 866            subquery = subquery.subquery(copy=False)
 867
 868        return In(
 869            this=maybe_copy(self, copy),
 870            expressions=[convert(e, copy=copy) for e in expressions],
 871            query=subquery,
 872            unnest=(
 873                Unnest(
 874                    expressions=[
 875                        maybe_parse(t.cast(ExpOrStr, e), copy=copy, **opts)
 876                        for e in ensure_list(unnest)
 877                    ]
 878                )
 879                if unnest
 880                else None
 881            ),
 882        )
 883
 884    def between(self, low: t.Any, high: t.Any, copy: bool = True, **opts) -> Between:
 885        return Between(
 886            this=maybe_copy(self, copy),
 887            low=convert(low, copy=copy, **opts),
 888            high=convert(high, copy=copy, **opts),
 889        )
 890
 891    def is_(self, other: ExpOrStr) -> Is:
 892        return self._binop(Is, other)
 893
 894    def like(self, other: ExpOrStr) -> Like:
 895        return self._binop(Like, other)
 896
 897    def ilike(self, other: ExpOrStr) -> ILike:
 898        return self._binop(ILike, other)
 899
 900    def eq(self, other: t.Any) -> EQ:
 901        return self._binop(EQ, other)
 902
 903    def neq(self, other: t.Any) -> NEQ:
 904        return self._binop(NEQ, other)
 905
 906    def rlike(self, other: ExpOrStr) -> RegexpLike:
 907        return self._binop(RegexpLike, other)
 908
 909    def div(self, other: ExpOrStr, typed: bool = False, safe: bool = False) -> Div:
 910        div = self._binop(Div, other)
 911        div.args["typed"] = typed
 912        div.args["safe"] = safe
 913        return div
 914
 915    def asc(self, nulls_first: bool = True) -> Ordered:
 916        return Ordered(this=self.copy(), nulls_first=nulls_first)
 917
 918    def desc(self, nulls_first: bool = False) -> Ordered:
 919        return Ordered(this=self.copy(), desc=True, nulls_first=nulls_first)
 920
 921    def __lt__(self, other: t.Any) -> LT:
 922        return self._binop(LT, other)
 923
 924    def __le__(self, other: t.Any) -> LTE:
 925        return self._binop(LTE, other)
 926
 927    def __gt__(self, other: t.Any) -> GT:
 928        return self._binop(GT, other)
 929
 930    def __ge__(self, other: t.Any) -> GTE:
 931        return self._binop(GTE, other)
 932
 933    def __add__(self, other: t.Any) -> Add:
 934        return self._binop(Add, other)
 935
 936    def __radd__(self, other: t.Any) -> Add:
 937        return self._binop(Add, other, reverse=True)
 938
 939    def __sub__(self, other: t.Any) -> Sub:
 940        return self._binop(Sub, other)
 941
 942    def __rsub__(self, other: t.Any) -> Sub:
 943        return self._binop(Sub, other, reverse=True)
 944
 945    def __mul__(self, other: t.Any) -> Mul:
 946        return self._binop(Mul, other)
 947
 948    def __rmul__(self, other: t.Any) -> Mul:
 949        return self._binop(Mul, other, reverse=True)
 950
 951    def __truediv__(self, other: t.Any) -> Div:
 952        return self._binop(Div, other)
 953
 954    def __rtruediv__(self, other: t.Any) -> Div:
 955        return self._binop(Div, other, reverse=True)
 956
 957    def __floordiv__(self, other: t.Any) -> IntDiv:
 958        return self._binop(IntDiv, other)
 959
 960    def __rfloordiv__(self, other: t.Any) -> IntDiv:
 961        return self._binop(IntDiv, other, reverse=True)
 962
 963    def __mod__(self, other: t.Any) -> Mod:
 964        return self._binop(Mod, other)
 965
 966    def __rmod__(self, other: t.Any) -> Mod:
 967        return self._binop(Mod, other, reverse=True)
 968
 969    def __pow__(self, other: t.Any) -> Pow:
 970        return self._binop(Pow, other)
 971
 972    def __rpow__(self, other: t.Any) -> Pow:
 973        return self._binop(Pow, other, reverse=True)
 974
 975    def __and__(self, other: t.Any) -> And:
 976        return self._binop(And, other)
 977
 978    def __rand__(self, other: t.Any) -> And:
 979        return self._binop(And, other, reverse=True)
 980
 981    def __or__(self, other: t.Any) -> Or:
 982        return self._binop(Or, other)
 983
 984    def __ror__(self, other: t.Any) -> Or:
 985        return self._binop(Or, other, reverse=True)
 986
 987    def __neg__(self) -> Neg:
 988        return Neg(this=_wrap(self.copy(), Binary))
 989
 990    def __invert__(self) -> Not:
 991        return not_(self.copy())
 992
 993
 994IntoType = t.Union[
 995    str,
 996    t.Type[Expression],
 997    t.Collection[t.Union[str, t.Type[Expression]]],
 998]
 999ExpOrStr = t.Union[str, Expression]
1000
1001
1002class Condition(Expression):
1003    """Logical conditions like x AND y, or simply x"""
1004
1005
1006class Predicate(Condition):
1007    """Relationships like x = y, x > 1, x >= y."""
1008
1009
1010class DerivedTable(Expression):
1011    @property
1012    def selects(self) -> t.List[Expression]:
1013        return self.this.selects if isinstance(self.this, Query) else []
1014
1015    @property
1016    def named_selects(self) -> t.List[str]:
1017        return [select.output_name for select in self.selects]
1018
1019
1020class Query(Expression):
1021    def subquery(self, alias: t.Optional[ExpOrStr] = None, copy: bool = True) -> Subquery:
1022        """
1023        Returns a `Subquery` that wraps around this query.
1024
1025        Example:
1026            >>> subquery = Select().select("x").from_("tbl").subquery()
1027            >>> Select().select("x").from_(subquery).sql()
1028            'SELECT x FROM (SELECT x FROM tbl)'
1029
1030        Args:
1031            alias: an optional alias for the subquery.
1032            copy: if `False`, modify this expression instance in-place.
1033        """
1034        instance = maybe_copy(self, copy)
1035        if not isinstance(alias, Expression):
1036            alias = TableAlias(this=to_identifier(alias)) if alias else None
1037
1038        return Subquery(this=instance, alias=alias)
1039
1040    def limit(
1041        self: Q, expression: ExpOrStr | int, dialect: DialectType = None, copy: bool = True, **opts
1042    ) -> Q:
1043        """
1044        Adds a LIMIT clause to this query.
1045
1046        Example:
1047            >>> select("1").union(select("1")).limit(1).sql()
1048            'SELECT 1 UNION SELECT 1 LIMIT 1'
1049
1050        Args:
1051            expression: the SQL code string to parse.
1052                This can also be an integer.
1053                If a `Limit` instance is passed, it will be used as-is.
1054                If another `Expression` instance is passed, it will be wrapped in a `Limit`.
1055            dialect: the dialect used to parse the input expression.
1056            copy: if `False`, modify this expression instance in-place.
1057            opts: other options to use to parse the input expressions.
1058
1059        Returns:
1060            A limited Select expression.
1061        """
1062        return _apply_builder(
1063            expression=expression,
1064            instance=self,
1065            arg="limit",
1066            into=Limit,
1067            prefix="LIMIT",
1068            dialect=dialect,
1069            copy=copy,
1070            into_arg="expression",
1071            **opts,
1072        )
1073
1074    def offset(
1075        self: Q, expression: ExpOrStr | int, dialect: DialectType = None, copy: bool = True, **opts
1076    ) -> Q:
1077        """
1078        Set the OFFSET expression.
1079
1080        Example:
1081            >>> Select().from_("tbl").select("x").offset(10).sql()
1082            'SELECT x FROM tbl OFFSET 10'
1083
1084        Args:
1085            expression: the SQL code string to parse.
1086                This can also be an integer.
1087                If a `Offset` instance is passed, this is used as-is.
1088                If another `Expression` instance is passed, it will be wrapped in a `Offset`.
1089            dialect: the dialect used to parse the input expression.
1090            copy: if `False`, modify this expression instance in-place.
1091            opts: other options to use to parse the input expressions.
1092
1093        Returns:
1094            The modified Select expression.
1095        """
1096        return _apply_builder(
1097            expression=expression,
1098            instance=self,
1099            arg="offset",
1100            into=Offset,
1101            prefix="OFFSET",
1102            dialect=dialect,
1103            copy=copy,
1104            into_arg="expression",
1105            **opts,
1106        )
1107
1108    def order_by(
1109        self: Q,
1110        *expressions: t.Optional[ExpOrStr],
1111        append: bool = True,
1112        dialect: DialectType = None,
1113        copy: bool = True,
1114        **opts,
1115    ) -> Q:
1116        """
1117        Set the ORDER BY expression.
1118
1119        Example:
1120            >>> Select().from_("tbl").select("x").order_by("x DESC").sql()
1121            'SELECT x FROM tbl ORDER BY x DESC'
1122
1123        Args:
1124            *expressions: the SQL code strings to parse.
1125                If a `Group` instance is passed, this is used as-is.
1126                If another `Expression` instance is passed, it will be wrapped in a `Order`.
1127            append: if `True`, add to any existing expressions.
1128                Otherwise, this flattens all the `Order` expression into a single expression.
1129            dialect: the dialect used to parse the input expression.
1130            copy: if `False`, modify this expression instance in-place.
1131            opts: other options to use to parse the input expressions.
1132
1133        Returns:
1134            The modified Select expression.
1135        """
1136        return _apply_child_list_builder(
1137            *expressions,
1138            instance=self,
1139            arg="order",
1140            append=append,
1141            copy=copy,
1142            prefix="ORDER BY",
1143            into=Order,
1144            dialect=dialect,
1145            **opts,
1146        )
1147
1148    @property
1149    def ctes(self) -> t.List[CTE]:
1150        """Returns a list of all the CTEs attached to this query."""
1151        with_ = self.args.get("with")
1152        return with_.expressions if with_ else []
1153
1154    @property
1155    def selects(self) -> t.List[Expression]:
1156        """Returns the query's projections."""
1157        raise NotImplementedError("Query objects must implement `selects`")
1158
1159    @property
1160    def named_selects(self) -> t.List[str]:
1161        """Returns the output names of the query's projections."""
1162        raise NotImplementedError("Query objects must implement `named_selects`")
1163
1164    def select(
1165        self: Q,
1166        *expressions: t.Optional[ExpOrStr],
1167        append: bool = True,
1168        dialect: DialectType = None,
1169        copy: bool = True,
1170        **opts,
1171    ) -> Q:
1172        """
1173        Append to or set the SELECT expressions.
1174
1175        Example:
1176            >>> Select().select("x", "y").sql()
1177            'SELECT x, y'
1178
1179        Args:
1180            *expressions: the SQL code strings to parse.
1181                If an `Expression` instance is passed, it will be used as-is.
1182            append: if `True`, add to any existing expressions.
1183                Otherwise, this resets the expressions.
1184            dialect: the dialect used to parse the input expressions.
1185            copy: if `False`, modify this expression instance in-place.
1186            opts: other options to use to parse the input expressions.
1187
1188        Returns:
1189            The modified Query expression.
1190        """
1191        raise NotImplementedError("Query objects must implement `select`")
1192
1193    def with_(
1194        self: Q,
1195        alias: ExpOrStr,
1196        as_: ExpOrStr,
1197        recursive: t.Optional[bool] = None,
1198        append: bool = True,
1199        dialect: DialectType = None,
1200        copy: bool = True,
1201        **opts,
1202    ) -> Q:
1203        """
1204        Append to or set the common table expressions.
1205
1206        Example:
1207            >>> Select().with_("tbl2", as_="SELECT * FROM tbl").select("x").from_("tbl2").sql()
1208            'WITH tbl2 AS (SELECT * FROM tbl) SELECT x FROM tbl2'
1209
1210        Args:
1211            alias: the SQL code string to parse as the table name.
1212                If an `Expression` instance is passed, this is used as-is.
1213            as_: the SQL code string to parse as the table expression.
1214                If an `Expression` instance is passed, it will be used as-is.
1215            recursive: set the RECURSIVE part of the expression. Defaults to `False`.
1216            append: if `True`, add to any existing expressions.
1217                Otherwise, this resets the expressions.
1218            dialect: the dialect used to parse the input expression.
1219            copy: if `False`, modify this expression instance in-place.
1220            opts: other options to use to parse the input expressions.
1221
1222        Returns:
1223            The modified expression.
1224        """
1225        return _apply_cte_builder(
1226            self, alias, as_, recursive=recursive, append=append, dialect=dialect, copy=copy, **opts
1227        )
1228
1229    def union(
1230        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1231    ) -> Union:
1232        """
1233        Builds a UNION expression.
1234
1235        Example:
1236            >>> import sqlglot
1237            >>> sqlglot.parse_one("SELECT * FROM foo").union("SELECT * FROM bla").sql()
1238            'SELECT * FROM foo UNION SELECT * FROM bla'
1239
1240        Args:
1241            expression: the SQL code string.
1242                If an `Expression` instance is passed, it will be used as-is.
1243            distinct: set the DISTINCT flag if and only if this is true.
1244            dialect: the dialect used to parse the input expression.
1245            opts: other options to use to parse the input expressions.
1246
1247        Returns:
1248            The new Union expression.
1249        """
1250        return union(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)
1251
1252    def intersect(
1253        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1254    ) -> Intersect:
1255        """
1256        Builds an INTERSECT expression.
1257
1258        Example:
1259            >>> import sqlglot
1260            >>> sqlglot.parse_one("SELECT * FROM foo").intersect("SELECT * FROM bla").sql()
1261            'SELECT * FROM foo INTERSECT SELECT * FROM bla'
1262
1263        Args:
1264            expression: the SQL code string.
1265                If an `Expression` instance is passed, it will be used as-is.
1266            distinct: set the DISTINCT flag if and only if this is true.
1267            dialect: the dialect used to parse the input expression.
1268            opts: other options to use to parse the input expressions.
1269
1270        Returns:
1271            The new Intersect expression.
1272        """
1273        return intersect(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)
1274
1275    def except_(
1276        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1277    ) -> Except:
1278        """
1279        Builds an EXCEPT expression.
1280
1281        Example:
1282            >>> import sqlglot
1283            >>> sqlglot.parse_one("SELECT * FROM foo").except_("SELECT * FROM bla").sql()
1284            'SELECT * FROM foo EXCEPT SELECT * FROM bla'
1285
1286        Args:
1287            expression: the SQL code string.
1288                If an `Expression` instance is passed, it will be used as-is.
1289            distinct: set the DISTINCT flag if and only if this is true.
1290            dialect: the dialect used to parse the input expression.
1291            opts: other options to use to parse the input expressions.
1292
1293        Returns:
1294            The new Except expression.
1295        """
1296        return except_(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)
1297
1298
1299class UDTF(DerivedTable):
1300    @property
1301    def selects(self) -> t.List[Expression]:
1302        alias = self.args.get("alias")
1303        return alias.columns if alias else []
1304
1305
1306class Cache(Expression):
1307    arg_types = {
1308        "this": True,
1309        "lazy": False,
1310        "options": False,
1311        "expression": False,
1312    }
1313
1314
1315class Uncache(Expression):
1316    arg_types = {"this": True, "exists": False}
1317
1318
1319class Refresh(Expression):
1320    pass
1321
1322
1323class DDL(Expression):
1324    @property
1325    def ctes(self) -> t.List[CTE]:
1326        """Returns a list of all the CTEs attached to this statement."""
1327        with_ = self.args.get("with")
1328        return with_.expressions if with_ else []
1329
1330    @property
1331    def selects(self) -> t.List[Expression]:
1332        """If this statement contains a query (e.g. a CTAS), this returns the query's projections."""
1333        return self.expression.selects if isinstance(self.expression, Query) else []
1334
1335    @property
1336    def named_selects(self) -> t.List[str]:
1337        """
1338        If this statement contains a query (e.g. a CTAS), this returns the output
1339        names of the query's projections.
1340        """
1341        return self.expression.named_selects if isinstance(self.expression, Query) else []
1342
1343
1344class DML(Expression):
1345    def returning(
1346        self,
1347        expression: ExpOrStr,
1348        dialect: DialectType = None,
1349        copy: bool = True,
1350        **opts,
1351    ) -> DML:
1352        """
1353        Set the RETURNING expression. Not supported by all dialects.
1354
1355        Example:
1356            >>> delete("tbl").returning("*", dialect="postgres").sql()
1357            'DELETE FROM tbl RETURNING *'
1358
1359        Args:
1360            expression: the SQL code strings to parse.
1361                If an `Expression` instance is passed, it will be used as-is.
1362            dialect: the dialect used to parse the input expressions.
1363            copy: if `False`, modify this expression instance in-place.
1364            opts: other options to use to parse the input expressions.
1365
1366        Returns:
1367            Delete: the modified expression.
1368        """
1369        return _apply_builder(
1370            expression=expression,
1371            instance=self,
1372            arg="returning",
1373            prefix="RETURNING",
1374            dialect=dialect,
1375            copy=copy,
1376            into=Returning,
1377            **opts,
1378        )
1379
1380
1381class Create(DDL):
1382    arg_types = {
1383        "with": False,
1384        "this": True,
1385        "kind": True,
1386        "expression": False,
1387        "exists": False,
1388        "properties": False,
1389        "replace": False,
1390        "unique": False,
1391        "indexes": False,
1392        "no_schema_binding": False,
1393        "begin": False,
1394        "end": False,
1395        "clone": False,
1396    }
1397
1398    @property
1399    def kind(self) -> t.Optional[str]:
1400        kind = self.args.get("kind")
1401        return kind and kind.upper()
1402
1403
1404class SequenceProperties(Expression):
1405    arg_types = {
1406        "increment": False,
1407        "minvalue": False,
1408        "maxvalue": False,
1409        "cache": False,
1410        "start": False,
1411        "owned": False,
1412        "options": False,
1413    }
1414
1415
1416class TruncateTable(Expression):
1417    arg_types = {
1418        "expressions": True,
1419        "is_database": False,
1420        "exists": False,
1421        "only": False,
1422        "cluster": False,
1423        "identity": False,
1424        "option": False,
1425        "partition": False,
1426    }
1427
1428
1429# https://docs.snowflake.com/en/sql-reference/sql/create-clone
1430# https://cloud.google.com/bigquery/docs/reference/standard-sql/data-definition-language#create_table_clone_statement
1431# https://cloud.google.com/bigquery/docs/reference/standard-sql/data-definition-language#create_table_copy
1432class Clone(Expression):
1433    arg_types = {"this": True, "shallow": False, "copy": False}
1434
1435
1436class Describe(Expression):
1437    arg_types = {"this": True, "style": False, "kind": False, "expressions": False}
1438
1439
1440class Kill(Expression):
1441    arg_types = {"this": True, "kind": False}
1442
1443
1444class Pragma(Expression):
1445    pass
1446
1447
1448class Set(Expression):
1449    arg_types = {"expressions": False, "unset": False, "tag": False}
1450
1451
1452class Heredoc(Expression):
1453    arg_types = {"this": True, "tag": False}
1454
1455
1456class SetItem(Expression):
1457    arg_types = {
1458        "this": False,
1459        "expressions": False,
1460        "kind": False,
1461        "collate": False,  # MySQL SET NAMES statement
1462        "global": False,
1463    }
1464
1465
1466class Show(Expression):
1467    arg_types = {
1468        "this": True,
1469        "history": False,
1470        "terse": False,
1471        "target": False,
1472        "offset": False,
1473        "starts_with": False,
1474        "limit": False,
1475        "from": False,
1476        "like": False,
1477        "where": False,
1478        "db": False,
1479        "scope": False,
1480        "scope_kind": False,
1481        "full": False,
1482        "mutex": False,
1483        "query": False,
1484        "channel": False,
1485        "global": False,
1486        "log": False,
1487        "position": False,
1488        "types": False,
1489    }
1490
1491
1492class UserDefinedFunction(Expression):
1493    arg_types = {"this": True, "expressions": False, "wrapped": False}
1494
1495
1496class CharacterSet(Expression):
1497    arg_types = {"this": True, "default": False}
1498
1499
1500class With(Expression):
1501    arg_types = {"expressions": True, "recursive": False}
1502
1503    @property
1504    def recursive(self) -> bool:
1505        return bool(self.args.get("recursive"))
1506
1507
1508class WithinGroup(Expression):
1509    arg_types = {"this": True, "expression": False}
1510
1511
1512# clickhouse supports scalar ctes
1513# https://clickhouse.com/docs/en/sql-reference/statements/select/with
1514class CTE(DerivedTable):
1515    arg_types = {
1516        "this": True,
1517        "alias": True,
1518        "scalar": False,
1519        "materialized": False,
1520    }
1521
1522
1523class TableAlias(Expression):
1524    arg_types = {"this": False, "columns": False}
1525
1526    @property
1527    def columns(self):
1528        return self.args.get("columns") or []
1529
1530
1531class BitString(Condition):
1532    pass
1533
1534
1535class HexString(Condition):
1536    pass
1537
1538
1539class ByteString(Condition):
1540    pass
1541
1542
1543class RawString(Condition):
1544    pass
1545
1546
1547class UnicodeString(Condition):
1548    arg_types = {"this": True, "escape": False}
1549
1550
1551class Column(Condition):
1552    arg_types = {"this": True, "table": False, "db": False, "catalog": False, "join_mark": False}
1553
1554    @property
1555    def table(self) -> str:
1556        return self.text("table")
1557
1558    @property
1559    def db(self) -> str:
1560        return self.text("db")
1561
1562    @property
1563    def catalog(self) -> str:
1564        return self.text("catalog")
1565
1566    @property
1567    def output_name(self) -> str:
1568        return self.name
1569
1570    @property
1571    def parts(self) -> t.List[Identifier]:
1572        """Return the parts of a column in order catalog, db, table, name."""
1573        return [
1574            t.cast(Identifier, self.args[part])
1575            for part in ("catalog", "db", "table", "this")
1576            if self.args.get(part)
1577        ]
1578
1579    def to_dot(self) -> Dot | Identifier:
1580        """Converts the column into a dot expression."""
1581        parts = self.parts
1582        parent = self.parent
1583
1584        while parent:
1585            if isinstance(parent, Dot):
1586                parts.append(parent.expression)
1587            parent = parent.parent
1588
1589        return Dot.build(deepcopy(parts)) if len(parts) > 1 else parts[0]
1590
1591
1592class ColumnPosition(Expression):
1593    arg_types = {"this": False, "position": True}
1594
1595
1596class ColumnDef(Expression):
1597    arg_types = {
1598        "this": True,
1599        "kind": False,
1600        "constraints": False,
1601        "exists": False,
1602        "position": False,
1603    }
1604
1605    @property
1606    def constraints(self) -> t.List[ColumnConstraint]:
1607        return self.args.get("constraints") or []
1608
1609    @property
1610    def kind(self) -> t.Optional[DataType]:
1611        return self.args.get("kind")
1612
1613
1614class AlterColumn(Expression):
1615    arg_types = {
1616        "this": True,
1617        "dtype": False,
1618        "collate": False,
1619        "using": False,
1620        "default": False,
1621        "drop": False,
1622        "comment": False,
1623    }
1624
1625
1626# https://docs.aws.amazon.com/redshift/latest/dg/r_ALTER_TABLE.html
1627class AlterDistStyle(Expression):
1628    pass
1629
1630
1631class AlterSortKey(Expression):
1632    arg_types = {"this": False, "expressions": False, "compound": False}
1633
1634
1635class RenameColumn(Expression):
1636    arg_types = {"this": True, "to": True, "exists": False}
1637
1638
1639class RenameTable(Expression):
1640    pass
1641
1642
1643class SwapTable(Expression):
1644    pass
1645
1646
1647class Comment(Expression):
1648    arg_types = {
1649        "this": True,
1650        "kind": True,
1651        "expression": True,
1652        "exists": False,
1653        "materialized": False,
1654    }
1655
1656
1657class Comprehension(Expression):
1658    arg_types = {"this": True, "expression": True, "iterator": True, "condition": False}
1659
1660
1661# https://clickhouse.com/docs/en/engines/table-engines/mergetree-family/mergetree#mergetree-table-ttl
1662class MergeTreeTTLAction(Expression):
1663    arg_types = {
1664        "this": True,
1665        "delete": False,
1666        "recompress": False,
1667        "to_disk": False,
1668        "to_volume": False,
1669    }
1670
1671
1672# https://clickhouse.com/docs/en/engines/table-engines/mergetree-family/mergetree#mergetree-table-ttl
1673class MergeTreeTTL(Expression):
1674    arg_types = {
1675        "expressions": True,
1676        "where": False,
1677        "group": False,
1678        "aggregates": False,
1679    }
1680
1681
1682# https://dev.mysql.com/doc/refman/8.0/en/create-table.html
1683class IndexConstraintOption(Expression):
1684    arg_types = {
1685        "key_block_size": False,
1686        "using": False,
1687        "parser": False,
1688        "comment": False,
1689        "visible": False,
1690        "engine_attr": False,
1691        "secondary_engine_attr": False,
1692    }
1693
1694
1695class ColumnConstraint(Expression):
1696    arg_types = {"this": False, "kind": True}
1697
1698    @property
1699    def kind(self) -> ColumnConstraintKind:
1700        return self.args["kind"]
1701
1702
1703class ColumnConstraintKind(Expression):
1704    pass
1705
1706
1707class AutoIncrementColumnConstraint(ColumnConstraintKind):
1708    pass
1709
1710
1711class PeriodForSystemTimeConstraint(ColumnConstraintKind):
1712    arg_types = {"this": True, "expression": True}
1713
1714
1715class CaseSpecificColumnConstraint(ColumnConstraintKind):
1716    arg_types = {"not_": True}
1717
1718
1719class CharacterSetColumnConstraint(ColumnConstraintKind):
1720    arg_types = {"this": True}
1721
1722
1723class CheckColumnConstraint(ColumnConstraintKind):
1724    arg_types = {"this": True, "enforced": False}
1725
1726
1727class ClusteredColumnConstraint(ColumnConstraintKind):
1728    pass
1729
1730
1731class CollateColumnConstraint(ColumnConstraintKind):
1732    pass
1733
1734
1735class CommentColumnConstraint(ColumnConstraintKind):
1736    pass
1737
1738
1739class CompressColumnConstraint(ColumnConstraintKind):
1740    pass
1741
1742
1743class DateFormatColumnConstraint(ColumnConstraintKind):
1744    arg_types = {"this": True}
1745
1746
1747class DefaultColumnConstraint(ColumnConstraintKind):
1748    pass
1749
1750
1751class EncodeColumnConstraint(ColumnConstraintKind):
1752    pass
1753
1754
1755# https://www.postgresql.org/docs/current/sql-createtable.html#SQL-CREATETABLE-EXCLUDE
1756class ExcludeColumnConstraint(ColumnConstraintKind):
1757    pass
1758
1759
1760class EphemeralColumnConstraint(ColumnConstraintKind):
1761    arg_types = {"this": False}
1762
1763
1764class WithOperator(Expression):
1765    arg_types = {"this": True, "op": True}
1766
1767
1768class GeneratedAsIdentityColumnConstraint(ColumnConstraintKind):
1769    # this: True -> ALWAYS, this: False -> BY DEFAULT
1770    arg_types = {
1771        "this": False,
1772        "expression": False,
1773        "on_null": False,
1774        "start": False,
1775        "increment": False,
1776        "minvalue": False,
1777        "maxvalue": False,
1778        "cycle": False,
1779    }
1780
1781
1782class GeneratedAsRowColumnConstraint(ColumnConstraintKind):
1783    arg_types = {"start": False, "hidden": False}
1784
1785
1786# https://dev.mysql.com/doc/refman/8.0/en/create-table.html
1787# https://github.com/ClickHouse/ClickHouse/blob/master/src/Parsers/ParserCreateQuery.h#L646
1788class IndexColumnConstraint(ColumnConstraintKind):
1789    arg_types = {
1790        "this": False,
1791        "expressions": False,
1792        "kind": False,
1793        "index_type": False,
1794        "options": False,
1795        "expression": False,  # Clickhouse
1796        "granularity": False,
1797    }
1798
1799
1800class InlineLengthColumnConstraint(ColumnConstraintKind):
1801    pass
1802
1803
1804class NonClusteredColumnConstraint(ColumnConstraintKind):
1805    pass
1806
1807
1808class NotForReplicationColumnConstraint(ColumnConstraintKind):
1809    arg_types = {}
1810
1811
1812class NotNullColumnConstraint(ColumnConstraintKind):
1813    arg_types = {"allow_null": False}
1814
1815
1816# https://dev.mysql.com/doc/refman/5.7/en/timestamp-initialization.html
1817class OnUpdateColumnConstraint(ColumnConstraintKind):
1818    pass
1819
1820
1821# https://docs.snowflake.com/en/sql-reference/sql/create-external-table#optional-parameters
1822class TransformColumnConstraint(ColumnConstraintKind):
1823    pass
1824
1825
1826class PrimaryKeyColumnConstraint(ColumnConstraintKind):
1827    arg_types = {"desc": False}
1828
1829
1830class TitleColumnConstraint(ColumnConstraintKind):
1831    pass
1832
1833
1834class UniqueColumnConstraint(ColumnConstraintKind):
1835    arg_types = {"this": False, "index_type": False, "on_conflict": False}
1836
1837
1838class UppercaseColumnConstraint(ColumnConstraintKind):
1839    arg_types: t.Dict[str, t.Any] = {}
1840
1841
1842class PathColumnConstraint(ColumnConstraintKind):
1843    pass
1844
1845
1846# computed column expression
1847# https://learn.microsoft.com/en-us/sql/t-sql/statements/create-table-transact-sql?view=sql-server-ver16
1848class ComputedColumnConstraint(ColumnConstraintKind):
1849    arg_types = {"this": True, "persisted": False, "not_null": False}
1850
1851
1852class Constraint(Expression):
1853    arg_types = {"this": True, "expressions": True}
1854
1855
1856class Delete(DML):
1857    arg_types = {
1858        "with": False,
1859        "this": False,
1860        "using": False,
1861        "where": False,
1862        "returning": False,
1863        "limit": False,
1864        "tables": False,  # Multiple-Table Syntax (MySQL)
1865    }
1866
1867    def delete(
1868        self,
1869        table: ExpOrStr,
1870        dialect: DialectType = None,
1871        copy: bool = True,
1872        **opts,
1873    ) -> Delete:
1874        """
1875        Create a DELETE expression or replace the table on an existing DELETE expression.
1876
1877        Example:
1878            >>> delete("tbl").sql()
1879            'DELETE FROM tbl'
1880
1881        Args:
1882            table: the table from which to delete.
1883            dialect: the dialect used to parse the input expression.
1884            copy: if `False`, modify this expression instance in-place.
1885            opts: other options to use to parse the input expressions.
1886
1887        Returns:
1888            Delete: the modified expression.
1889        """
1890        return _apply_builder(
1891            expression=table,
1892            instance=self,
1893            arg="this",
1894            dialect=dialect,
1895            into=Table,
1896            copy=copy,
1897            **opts,
1898        )
1899
1900    def where(
1901        self,
1902        *expressions: t.Optional[ExpOrStr],
1903        append: bool = True,
1904        dialect: DialectType = None,
1905        copy: bool = True,
1906        **opts,
1907    ) -> Delete:
1908        """
1909        Append to or set the WHERE expressions.
1910
1911        Example:
1912            >>> delete("tbl").where("x = 'a' OR x < 'b'").sql()
1913            "DELETE FROM tbl WHERE x = 'a' OR x < 'b'"
1914
1915        Args:
1916            *expressions: the SQL code strings to parse.
1917                If an `Expression` instance is passed, it will be used as-is.
1918                Multiple expressions are combined with an AND operator.
1919            append: if `True`, AND the new expressions to any existing expression.
1920                Otherwise, this resets the expression.
1921            dialect: the dialect used to parse the input expressions.
1922            copy: if `False`, modify this expression instance in-place.
1923            opts: other options to use to parse the input expressions.
1924
1925        Returns:
1926            Delete: the modified expression.
1927        """
1928        return _apply_conjunction_builder(
1929            *expressions,
1930            instance=self,
1931            arg="where",
1932            append=append,
1933            into=Where,
1934            dialect=dialect,
1935            copy=copy,
1936            **opts,
1937        )
1938
1939
1940class Drop(Expression):
1941    arg_types = {
1942        "this": False,
1943        "kind": False,
1944        "expressions": False,
1945        "exists": False,
1946        "temporary": False,
1947        "materialized": False,
1948        "cascade": False,
1949        "constraints": False,
1950        "purge": False,
1951        "cluster": False,
1952    }
1953
1954
1955class Filter(Expression):
1956    arg_types = {"this": True, "expression": True}
1957
1958
1959class Check(Expression):
1960    pass
1961
1962
1963# https://docs.snowflake.com/en/sql-reference/constructs/connect-by
1964class Connect(Expression):
1965    arg_types = {"start": False, "connect": True, "nocycle": False}
1966
1967
1968class CopyParameter(Expression):
1969    arg_types = {"this": True, "expression": False}
1970
1971
1972class Copy(Expression):
1973    arg_types = {
1974        "this": True,
1975        "kind": True,
1976        "files": True,
1977        "credentials": False,
1978        "format": False,
1979        "params": False,
1980    }
1981
1982
1983class Credentials(Expression):
1984    arg_types = {
1985        "credentials": False,
1986        "encryption": False,
1987        "storage": False,
1988        "iam_role": False,
1989        "region": False,
1990    }
1991
1992
1993class Prior(Expression):
1994    pass
1995
1996
1997class Directory(Expression):
1998    # https://spark.apache.org/docs/3.0.0-preview/sql-ref-syntax-dml-insert-overwrite-directory-hive.html
1999    arg_types = {"this": True, "local": False, "row_format": False}
2000
2001
2002class ForeignKey(Expression):
2003    arg_types = {
2004        "expressions": True,
2005        "reference": False,
2006        "delete": False,
2007        "update": False,
2008    }
2009
2010
2011class ColumnPrefix(Expression):
2012    arg_types = {"this": True, "expression": True}
2013
2014
2015class PrimaryKey(Expression):
2016    arg_types = {"expressions": True, "options": False}
2017
2018
2019# https://www.postgresql.org/docs/9.1/sql-selectinto.html
2020# https://docs.aws.amazon.com/redshift/latest/dg/r_SELECT_INTO.html#r_SELECT_INTO-examples
2021class Into(Expression):
2022    arg_types = {"this": True, "temporary": False, "unlogged": False}
2023
2024
2025class From(Expression):
2026    @property
2027    def name(self) -> str:
2028        return self.this.name
2029
2030    @property
2031    def alias_or_name(self) -> str:
2032        return self.this.alias_or_name
2033
2034
2035class Having(Expression):
2036    pass
2037
2038
2039class Hint(Expression):
2040    arg_types = {"expressions": True}
2041
2042
2043class JoinHint(Expression):
2044    arg_types = {"this": True, "expressions": True}
2045
2046
2047class Identifier(Expression):
2048    arg_types = {"this": True, "quoted": False, "global": False, "temporary": False}
2049
2050    @property
2051    def quoted(self) -> bool:
2052        return bool(self.args.get("quoted"))
2053
2054    @property
2055    def hashable_args(self) -> t.Any:
2056        return (self.this, self.quoted)
2057
2058    @property
2059    def output_name(self) -> str:
2060        return self.name
2061
2062
2063# https://www.postgresql.org/docs/current/indexes-opclass.html
2064class Opclass(Expression):
2065    arg_types = {"this": True, "expression": True}
2066
2067
2068class Index(Expression):
2069    arg_types = {
2070        "this": False,
2071        "table": False,
2072        "unique": False,
2073        "primary": False,
2074        "amp": False,  # teradata
2075        "params": False,
2076    }
2077
2078
2079class IndexParameters(Expression):
2080    arg_types = {
2081        "using": False,
2082        "include": False,
2083        "columns": False,
2084        "with_storage": False,
2085        "partition_by": False,
2086        "tablespace": False,
2087        "where": False,
2088    }
2089
2090
2091class Insert(DDL, DML):
2092    arg_types = {
2093        "hint": False,
2094        "with": False,
2095        "is_function": False,
2096        "this": False,
2097        "expression": False,
2098        "conflict": False,
2099        "returning": False,
2100        "overwrite": False,
2101        "exists": False,
2102        "alternative": False,
2103        "where": False,
2104        "ignore": False,
2105        "by_name": False,
2106        "stored": False,
2107    }
2108
2109    def with_(
2110        self,
2111        alias: ExpOrStr,
2112        as_: ExpOrStr,
2113        recursive: t.Optional[bool] = None,
2114        append: bool = True,
2115        dialect: DialectType = None,
2116        copy: bool = True,
2117        **opts,
2118    ) -> Insert:
2119        """
2120        Append to or set the common table expressions.
2121
2122        Example:
2123            >>> insert("SELECT x FROM cte", "t").with_("cte", as_="SELECT * FROM tbl").sql()
2124            'WITH cte AS (SELECT * FROM tbl) INSERT INTO t SELECT x FROM cte'
2125
2126        Args:
2127            alias: the SQL code string to parse as the table name.
2128                If an `Expression` instance is passed, this is used as-is.
2129            as_: the SQL code string to parse as the table expression.
2130                If an `Expression` instance is passed, it will be used as-is.
2131            recursive: set the RECURSIVE part of the expression. Defaults to `False`.
2132            append: if `True`, add to any existing expressions.
2133                Otherwise, this resets the expressions.
2134            dialect: the dialect used to parse the input expression.
2135            copy: if `False`, modify this expression instance in-place.
2136            opts: other options to use to parse the input expressions.
2137
2138        Returns:
2139            The modified expression.
2140        """
2141        return _apply_cte_builder(
2142            self, alias, as_, recursive=recursive, append=append, dialect=dialect, copy=copy, **opts
2143        )
2144
2145
2146class OnConflict(Expression):
2147    arg_types = {
2148        "duplicate": False,
2149        "expressions": False,
2150        "action": False,
2151        "conflict_keys": False,
2152        "constraint": False,
2153    }
2154
2155
2156class Returning(Expression):
2157    arg_types = {"expressions": True, "into": False}
2158
2159
2160# https://dev.mysql.com/doc/refman/8.0/en/charset-introducer.html
2161class Introducer(Expression):
2162    arg_types = {"this": True, "expression": True}
2163
2164
2165# national char, like n'utf8'
2166class National(Expression):
2167    pass
2168
2169
2170class LoadData(Expression):
2171    arg_types = {
2172        "this": True,
2173        "local": False,
2174        "overwrite": False,
2175        "inpath": True,
2176        "partition": False,
2177        "input_format": False,
2178        "serde": False,
2179    }
2180
2181
2182class Partition(Expression):
2183    arg_types = {"expressions": True}
2184
2185
2186class PartitionRange(Expression):
2187    arg_types = {"this": True, "expression": True}
2188
2189
2190# https://clickhouse.com/docs/en/sql-reference/statements/alter/partition#how-to-set-partition-expression
2191class PartitionId(Expression):
2192    pass
2193
2194
2195class Fetch(Expression):
2196    arg_types = {
2197        "direction": False,
2198        "count": False,
2199        "percent": False,
2200        "with_ties": False,
2201    }
2202
2203
2204class Group(Expression):
2205    arg_types = {
2206        "expressions": False,
2207        "grouping_sets": False,
2208        "cube": False,
2209        "rollup": False,
2210        "totals": False,
2211        "all": False,
2212    }
2213
2214
2215class Lambda(Expression):
2216    arg_types = {"this": True, "expressions": True}
2217
2218
2219class Limit(Expression):
2220    arg_types = {"this": False, "expression": True, "offset": False, "expressions": False}
2221
2222
2223class Literal(Condition):
2224    arg_types = {"this": True, "is_string": True}
2225
2226    @property
2227    def hashable_args(self) -> t.Any:
2228        return (self.this, self.args.get("is_string"))
2229
2230    @classmethod
2231    def number(cls, number) -> Literal:
2232        return cls(this=str(number), is_string=False)
2233
2234    @classmethod
2235    def string(cls, string) -> Literal:
2236        return cls(this=str(string), is_string=True)
2237
2238    @property
2239    def output_name(self) -> str:
2240        return self.name
2241
2242
2243class Join(Expression):
2244    arg_types = {
2245        "this": True,
2246        "on": False,
2247        "side": False,
2248        "kind": False,
2249        "using": False,
2250        "method": False,
2251        "global": False,
2252        "hint": False,
2253        "match_condition": False,  # Snowflake
2254    }
2255
2256    @property
2257    def method(self) -> str:
2258        return self.text("method").upper()
2259
2260    @property
2261    def kind(self) -> str:
2262        return self.text("kind").upper()
2263
2264    @property
2265    def side(self) -> str:
2266        return self.text("side").upper()
2267
2268    @property
2269    def hint(self) -> str:
2270        return self.text("hint").upper()
2271
2272    @property
2273    def alias_or_name(self) -> str:
2274        return self.this.alias_or_name
2275
2276    def on(
2277        self,
2278        *expressions: t.Optional[ExpOrStr],
2279        append: bool = True,
2280        dialect: DialectType = None,
2281        copy: bool = True,
2282        **opts,
2283    ) -> Join:
2284        """
2285        Append to or set the ON expressions.
2286
2287        Example:
2288            >>> import sqlglot
2289            >>> sqlglot.parse_one("JOIN x", into=Join).on("y = 1").sql()
2290            'JOIN x ON y = 1'
2291
2292        Args:
2293            *expressions: the SQL code strings to parse.
2294                If an `Expression` instance is passed, it will be used as-is.
2295                Multiple expressions are combined with an AND operator.
2296            append: if `True`, AND the new expressions to any existing expression.
2297                Otherwise, this resets the expression.
2298            dialect: the dialect used to parse the input expressions.
2299            copy: if `False`, modify this expression instance in-place.
2300            opts: other options to use to parse the input expressions.
2301
2302        Returns:
2303            The modified Join expression.
2304        """
2305        join = _apply_conjunction_builder(
2306            *expressions,
2307            instance=self,
2308            arg="on",
2309            append=append,
2310            dialect=dialect,
2311            copy=copy,
2312            **opts,
2313        )
2314
2315        if join.kind == "CROSS":
2316            join.set("kind", None)
2317
2318        return join
2319
2320    def using(
2321        self,
2322        *expressions: t.Optional[ExpOrStr],
2323        append: bool = True,
2324        dialect: DialectType = None,
2325        copy: bool = True,
2326        **opts,
2327    ) -> Join:
2328        """
2329        Append to or set the USING expressions.
2330
2331        Example:
2332            >>> import sqlglot
2333            >>> sqlglot.parse_one("JOIN x", into=Join).using("foo", "bla").sql()
2334            'JOIN x USING (foo, bla)'
2335
2336        Args:
2337            *expressions: the SQL code strings to parse.
2338                If an `Expression` instance is passed, it will be used as-is.
2339            append: if `True`, concatenate the new expressions to the existing "using" list.
2340                Otherwise, this resets the expression.
2341            dialect: the dialect used to parse the input expressions.
2342            copy: if `False`, modify this expression instance in-place.
2343            opts: other options to use to parse the input expressions.
2344
2345        Returns:
2346            The modified Join expression.
2347        """
2348        join = _apply_list_builder(
2349            *expressions,
2350            instance=self,
2351            arg="using",
2352            append=append,
2353            dialect=dialect,
2354            copy=copy,
2355            **opts,
2356        )
2357
2358        if join.kind == "CROSS":
2359            join.set("kind", None)
2360
2361        return join
2362
2363
2364class Lateral(UDTF):
2365    arg_types = {
2366        "this": True,
2367        "view": False,
2368        "outer": False,
2369        "alias": False,
2370        "cross_apply": False,  # True -> CROSS APPLY, False -> OUTER APPLY
2371    }
2372
2373
2374class MatchRecognizeMeasure(Expression):
2375    arg_types = {
2376        "this": True,
2377        "window_frame": False,
2378    }
2379
2380
2381class MatchRecognize(Expression):
2382    arg_types = {
2383        "partition_by": False,
2384        "order": False,
2385        "measures": False,
2386        "rows": False,
2387        "after": False,
2388        "pattern": False,
2389        "define": False,
2390        "alias": False,
2391    }
2392
2393
2394# Clickhouse FROM FINAL modifier
2395# https://clickhouse.com/docs/en/sql-reference/statements/select/from/#final-modifier
2396class Final(Expression):
2397    pass
2398
2399
2400class Offset(Expression):
2401    arg_types = {"this": False, "expression": True, "expressions": False}
2402
2403
2404class Order(Expression):
2405    arg_types = {
2406        "this": False,
2407        "expressions": True,
2408        "interpolate": False,
2409        "siblings": False,
2410    }
2411
2412
2413# https://clickhouse.com/docs/en/sql-reference/statements/select/order-by#order-by-expr-with-fill-modifier
2414class WithFill(Expression):
2415    arg_types = {"from": False, "to": False, "step": False}
2416
2417
2418# hive specific sorts
2419# https://cwiki.apache.org/confluence/display/Hive/LanguageManual+SortBy
2420class Cluster(Order):
2421    pass
2422
2423
2424class Distribute(Order):
2425    pass
2426
2427
2428class Sort(Order):
2429    pass
2430
2431
2432class Ordered(Expression):
2433    arg_types = {"this": True, "desc": False, "nulls_first": True, "with_fill": False}
2434
2435
2436class Property(Expression):
2437    arg_types = {"this": True, "value": True}
2438
2439
2440class AlgorithmProperty(Property):
2441    arg_types = {"this": True}
2442
2443
2444class AutoIncrementProperty(Property):
2445    arg_types = {"this": True}
2446
2447
2448# https://docs.aws.amazon.com/prescriptive-guidance/latest/materialized-views-redshift/refreshing-materialized-views.html
2449class AutoRefreshProperty(Property):
2450    arg_types = {"this": True}
2451
2452
2453class BackupProperty(Property):
2454    arg_types = {"this": True}
2455
2456
2457class BlockCompressionProperty(Property):
2458    arg_types = {
2459        "autotemp": False,
2460        "always": False,
2461        "default": False,
2462        "manual": False,
2463        "never": False,
2464    }
2465
2466
2467class CharacterSetProperty(Property):
2468    arg_types = {"this": True, "default": True}
2469
2470
2471class ChecksumProperty(Property):
2472    arg_types = {"on": False, "default": False}
2473
2474
2475class CollateProperty(Property):
2476    arg_types = {"this": True, "default": False}
2477
2478
2479class CopyGrantsProperty(Property):
2480    arg_types = {}
2481
2482
2483class DataBlocksizeProperty(Property):
2484    arg_types = {
2485        "size": False,
2486        "units": False,
2487        "minimum": False,
2488        "maximum": False,
2489        "default": False,
2490    }
2491
2492
2493class DefinerProperty(Property):
2494    arg_types = {"this": True}
2495
2496
2497class DistKeyProperty(Property):
2498    arg_types = {"this": True}
2499
2500
2501class DistStyleProperty(Property):
2502    arg_types = {"this": True}
2503
2504
2505class EngineProperty(Property):
2506    arg_types = {"this": True}
2507
2508
2509class HeapProperty(Property):
2510    arg_types = {}
2511
2512
2513class ToTableProperty(Property):
2514    arg_types = {"this": True}
2515
2516
2517class ExecuteAsProperty(Property):
2518    arg_types = {"this": True}
2519
2520
2521class ExternalProperty(Property):
2522    arg_types = {"this": False}
2523
2524
2525class FallbackProperty(Property):
2526    arg_types = {"no": True, "protection": False}
2527
2528
2529class FileFormatProperty(Property):
2530    arg_types = {"this": True}
2531
2532
2533class FreespaceProperty(Property):
2534    arg_types = {"this": True, "percent": False}
2535
2536
2537class GlobalProperty(Property):
2538    arg_types = {}
2539
2540
2541class IcebergProperty(Property):
2542    arg_types = {}
2543
2544
2545class InheritsProperty(Property):
2546    arg_types = {"expressions": True}
2547
2548
2549class InputModelProperty(Property):
2550    arg_types = {"this": True}
2551
2552
2553class OutputModelProperty(Property):
2554    arg_types = {"this": True}
2555
2556
2557class IsolatedLoadingProperty(Property):
2558    arg_types = {"no": False, "concurrent": False, "target": False}
2559
2560
2561class JournalProperty(Property):
2562    arg_types = {
2563        "no": False,
2564        "dual": False,
2565        "before": False,
2566        "local": False,
2567        "after": False,
2568    }
2569
2570
2571class LanguageProperty(Property):
2572    arg_types = {"this": True}
2573
2574
2575# spark ddl
2576class ClusteredByProperty(Property):
2577    arg_types = {"expressions": True, "sorted_by": False, "buckets": True}
2578
2579
2580class DictProperty(Property):
2581    arg_types = {"this": True, "kind": True, "settings": False}
2582
2583
2584class DictSubProperty(Property):
2585    pass
2586
2587
2588class DictRange(Property):
2589    arg_types = {"this": True, "min": True, "max": True}
2590
2591
2592# Clickhouse CREATE ... ON CLUSTER modifier
2593# https://clickhouse.com/docs/en/sql-reference/distributed-ddl
2594class OnCluster(Property):
2595    arg_types = {"this": True}
2596
2597
2598class LikeProperty(Property):
2599    arg_types = {"this": True, "expressions": False}
2600
2601
2602class LocationProperty(Property):
2603    arg_types = {"this": True}
2604
2605
2606class LockProperty(Property):
2607    arg_types = {"this": True}
2608
2609
2610class LockingProperty(Property):
2611    arg_types = {
2612        "this": False,
2613        "kind": True,
2614        "for_or_in": False,
2615        "lock_type": True,
2616        "override": False,
2617    }
2618
2619
2620class LogProperty(Property):
2621    arg_types = {"no": True}
2622
2623
2624class MaterializedProperty(Property):
2625    arg_types = {"this": False}
2626
2627
2628class MergeBlockRatioProperty(Property):
2629    arg_types = {"this": False, "no": False, "default": False, "percent": False}
2630
2631
2632class NoPrimaryIndexProperty(Property):
2633    arg_types = {}
2634
2635
2636class OnProperty(Property):
2637    arg_types = {"this": True}
2638
2639
2640class OnCommitProperty(Property):
2641    arg_types = {"delete": False}
2642
2643
2644class PartitionedByProperty(Property):
2645    arg_types = {"this": True}
2646
2647
2648# https://www.postgresql.org/docs/current/sql-createtable.html
2649class PartitionBoundSpec(Expression):
2650    # this -> IN / MODULUS, expression -> REMAINDER, from_expressions -> FROM (...), to_expressions -> TO (...)
2651    arg_types = {
2652        "this": False,
2653        "expression": False,
2654        "from_expressions": False,
2655        "to_expressions": False,
2656    }
2657
2658
2659class PartitionedOfProperty(Property):
2660    # this -> parent_table (schema), expression -> FOR VALUES ... / DEFAULT
2661    arg_types = {"this": True, "expression": True}
2662
2663
2664class RemoteWithConnectionModelProperty(Property):
2665    arg_types = {"this": True}
2666
2667
2668class ReturnsProperty(Property):
2669    arg_types = {"this": True, "is_table": False, "table": False}
2670
2671
2672class RowFormatProperty(Property):
2673    arg_types = {"this": True}
2674
2675
2676class RowFormatDelimitedProperty(Property):
2677    # https://cwiki.apache.org/confluence/display/hive/languagemanual+dml
2678    arg_types = {
2679        "fields": False,
2680        "escaped": False,
2681        "collection_items": False,
2682        "map_keys": False,
2683        "lines": False,
2684        "null": False,
2685        "serde": False,
2686    }
2687
2688
2689class RowFormatSerdeProperty(Property):
2690    arg_types = {"this": True, "serde_properties": False}
2691
2692
2693# https://spark.apache.org/docs/3.1.2/sql-ref-syntax-qry-select-transform.html
2694class QueryTransform(Expression):
2695    arg_types = {
2696        "expressions": True,
2697        "command_script": True,
2698        "schema": False,
2699        "row_format_before": False,
2700        "record_writer": False,
2701        "row_format_after": False,
2702        "record_reader": False,
2703    }
2704
2705
2706class SampleProperty(Property):
2707    arg_types = {"this": True}
2708
2709
2710class SchemaCommentProperty(Property):
2711    arg_types = {"this": True}
2712
2713
2714class SerdeProperties(Property):
2715    arg_types = {"expressions": True}
2716
2717
2718class SetProperty(Property):
2719    arg_types = {"multi": True}
2720
2721
2722class SharingProperty(Property):
2723    arg_types = {"this": False}
2724
2725
2726class SetConfigProperty(Property):
2727    arg_types = {"this": True}
2728
2729
2730class SettingsProperty(Property):
2731    arg_types = {"expressions": True}
2732
2733
2734class SortKeyProperty(Property):
2735    arg_types = {"this": True, "compound": False}
2736
2737
2738class SqlReadWriteProperty(Property):
2739    arg_types = {"this": True}
2740
2741
2742class SqlSecurityProperty(Property):
2743    arg_types = {"definer": True}
2744
2745
2746class StabilityProperty(Property):
2747    arg_types = {"this": True}
2748
2749
2750class TemporaryProperty(Property):
2751    arg_types = {"this": False}
2752
2753
2754class TransformModelProperty(Property):
2755    arg_types = {"expressions": True}
2756
2757
2758class TransientProperty(Property):
2759    arg_types = {"this": False}
2760
2761
2762class UnloggedProperty(Property):
2763    arg_types = {}
2764
2765
2766# https://learn.microsoft.com/en-us/sql/t-sql/statements/create-view-transact-sql?view=sql-server-ver16
2767class ViewAttributeProperty(Property):
2768    arg_types = {"this": True}
2769
2770
2771class VolatileProperty(Property):
2772    arg_types = {"this": False}
2773
2774
2775class WithDataProperty(Property):
2776    arg_types = {"no": True, "statistics": False}
2777
2778
2779class WithJournalTableProperty(Property):
2780    arg_types = {"this": True}
2781
2782
2783class WithSystemVersioningProperty(Property):
2784    # this -> history table name, expression -> data consistency check
2785    arg_types = {"this": False, "expression": False}
2786
2787
2788class Properties(Expression):
2789    arg_types = {"expressions": True}
2790
2791    NAME_TO_PROPERTY = {
2792        "ALGORITHM": AlgorithmProperty,
2793        "AUTO_INCREMENT": AutoIncrementProperty,
2794        "CHARACTER SET": CharacterSetProperty,
2795        "CLUSTERED_BY": ClusteredByProperty,
2796        "COLLATE": CollateProperty,
2797        "COMMENT": SchemaCommentProperty,
2798        "DEFINER": DefinerProperty,
2799        "DISTKEY": DistKeyProperty,
2800        "DISTSTYLE": DistStyleProperty,
2801        "ENGINE": EngineProperty,
2802        "EXECUTE AS": ExecuteAsProperty,
2803        "FORMAT": FileFormatProperty,
2804        "LANGUAGE": LanguageProperty,
2805        "LOCATION": LocationProperty,
2806        "LOCK": LockProperty,
2807        "PARTITIONED_BY": PartitionedByProperty,
2808        "RETURNS": ReturnsProperty,
2809        "ROW_FORMAT": RowFormatProperty,
2810        "SORTKEY": SortKeyProperty,
2811    }
2812
2813    PROPERTY_TO_NAME = {v: k for k, v in NAME_TO_PROPERTY.items()}
2814
2815    # CREATE property locations
2816    # Form: schema specified
2817    #   create [POST_CREATE]
2818    #     table a [POST_NAME]
2819    #     (b int) [POST_SCHEMA]
2820    #     with ([POST_WITH])
2821    #     index (b) [POST_INDEX]
2822    #
2823    # Form: alias selection
2824    #   create [POST_CREATE]
2825    #     table a [POST_NAME]
2826    #     as [POST_ALIAS] (select * from b) [POST_EXPRESSION]
2827    #     index (c) [POST_INDEX]
2828    class Location(AutoName):
2829        POST_CREATE = auto()
2830        POST_NAME = auto()
2831        POST_SCHEMA = auto()
2832        POST_WITH = auto()
2833        POST_ALIAS = auto()
2834        POST_EXPRESSION = auto()
2835        POST_INDEX = auto()
2836        UNSUPPORTED = auto()
2837
2838    @classmethod
2839    def from_dict(cls, properties_dict: t.Dict) -> Properties:
2840        expressions = []
2841        for key, value in properties_dict.items():
2842            property_cls = cls.NAME_TO_PROPERTY.get(key.upper())
2843            if property_cls:
2844                expressions.append(property_cls(this=convert(value)))
2845            else:
2846                expressions.append(Property(this=Literal.string(key), value=convert(value)))
2847
2848        return cls(expressions=expressions)
2849
2850
2851class Qualify(Expression):
2852    pass
2853
2854
2855class InputOutputFormat(Expression):
2856    arg_types = {"input_format": False, "output_format": False}
2857
2858
2859# https://www.ibm.com/docs/en/ias?topic=procedures-return-statement-in-sql
2860class Return(Expression):
2861    pass
2862
2863
2864class Reference(Expression):
2865    arg_types = {"this": True, "expressions": False, "options": False}
2866
2867
2868class Tuple(Expression):
2869    arg_types = {"expressions": False}
2870
2871    def isin(
2872        self,
2873        *expressions: t.Any,
2874        query: t.Optional[ExpOrStr] = None,
2875        unnest: t.Optional[ExpOrStr] | t.Collection[ExpOrStr] = None,
2876        copy: bool = True,
2877        **opts,
2878    ) -> In:
2879        return In(
2880            this=maybe_copy(self, copy),
2881            expressions=[convert(e, copy=copy) for e in expressions],
2882            query=maybe_parse(query, copy=copy, **opts) if query else None,
2883            unnest=(
2884                Unnest(
2885                    expressions=[
2886                        maybe_parse(t.cast(ExpOrStr, e), copy=copy, **opts)
2887                        for e in ensure_list(unnest)
2888                    ]
2889                )
2890                if unnest
2891                else None
2892            ),
2893        )
2894
2895
2896QUERY_MODIFIERS = {
2897    "match": False,
2898    "laterals": False,
2899    "joins": False,
2900    "connect": False,
2901    "pivots": False,
2902    "prewhere": False,
2903    "where": False,
2904    "group": False,
2905    "having": False,
2906    "qualify": False,
2907    "windows": False,
2908    "distribute": False,
2909    "sort": False,
2910    "cluster": False,
2911    "order": False,
2912    "limit": False,
2913    "offset": False,
2914    "locks": False,
2915    "sample": False,
2916    "settings": False,
2917    "format": False,
2918    "options": False,
2919}
2920
2921
2922# https://learn.microsoft.com/en-us/sql/t-sql/queries/option-clause-transact-sql?view=sql-server-ver16
2923# https://learn.microsoft.com/en-us/sql/t-sql/queries/hints-transact-sql-query?view=sql-server-ver16
2924class QueryOption(Expression):
2925    arg_types = {"this": True, "expression": False}
2926
2927
2928# https://learn.microsoft.com/en-us/sql/t-sql/queries/hints-transact-sql-table?view=sql-server-ver16
2929class WithTableHint(Expression):
2930    arg_types = {"expressions": True}
2931
2932
2933# https://dev.mysql.com/doc/refman/8.0/en/index-hints.html
2934class IndexTableHint(Expression):
2935    arg_types = {"this": True, "expressions": False, "target": False}
2936
2937
2938# https://docs.snowflake.com/en/sql-reference/constructs/at-before
2939class HistoricalData(Expression):
2940    arg_types = {"this": True, "kind": True, "expression": True}
2941
2942
2943class Table(Expression):
2944    arg_types = {
2945        "this": False,
2946        "alias": False,
2947        "db": False,
2948        "catalog": False,
2949        "laterals": False,
2950        "joins": False,
2951        "pivots": False,
2952        "hints": False,
2953        "system_time": False,
2954        "version": False,
2955        "format": False,
2956        "pattern": False,
2957        "ordinality": False,
2958        "when": False,
2959        "only": False,
2960        "partition": False,
2961    }
2962
2963    @property
2964    def name(self) -> str:
2965        if isinstance(self.this, Func):
2966            return ""
2967        return self.this.name
2968
2969    @property
2970    def db(self) -> str:
2971        return self.text("db")
2972
2973    @property
2974    def catalog(self) -> str:
2975        return self.text("catalog")
2976
2977    @property
2978    def selects(self) -> t.List[Expression]:
2979        return []
2980
2981    @property
2982    def named_selects(self) -> t.List[str]:
2983        return []
2984
2985    @property
2986    def parts(self) -> t.List[Expression]:
2987        """Return the parts of a table in order catalog, db, table."""
2988        parts: t.List[Expression] = []
2989
2990        for arg in ("catalog", "db", "this"):
2991            part = self.args.get(arg)
2992
2993            if isinstance(part, Dot):
2994                parts.extend(part.flatten())
2995            elif isinstance(part, Expression):
2996                parts.append(part)
2997
2998        return parts
2999
3000    def to_column(self, copy: bool = True) -> Alias | Column | Dot:
3001        parts = self.parts
3002        col = column(*reversed(parts[0:4]), fields=parts[4:], copy=copy)  # type: ignore
3003        alias = self.args.get("alias")
3004        if alias:
3005            col = alias_(col, alias.this, copy=copy)
3006        return col
3007
3008
3009class Union(Query):
3010    arg_types = {
3011        "with": False,
3012        "this": True,
3013        "expression": True,
3014        "distinct": False,
3015        "by_name": False,
3016        **QUERY_MODIFIERS,
3017    }
3018
3019    def select(
3020        self,
3021        *expressions: t.Optional[ExpOrStr],
3022        append: bool = True,
3023        dialect: DialectType = None,
3024        copy: bool = True,
3025        **opts,
3026    ) -> Union:
3027        this = maybe_copy(self, copy)
3028        this.this.unnest().select(*expressions, append=append, dialect=dialect, copy=False, **opts)
3029        this.expression.unnest().select(
3030            *expressions, append=append, dialect=dialect, copy=False, **opts
3031        )
3032        return this
3033
3034    @property
3035    def named_selects(self) -> t.List[str]:
3036        return self.this.unnest().named_selects
3037
3038    @property
3039    def is_star(self) -> bool:
3040        return self.this.is_star or self.expression.is_star
3041
3042    @property
3043    def selects(self) -> t.List[Expression]:
3044        return self.this.unnest().selects
3045
3046    @property
3047    def left(self) -> Expression:
3048        return self.this
3049
3050    @property
3051    def right(self) -> Expression:
3052        return self.expression
3053
3054
3055class Except(Union):
3056    pass
3057
3058
3059class Intersect(Union):
3060    pass
3061
3062
3063class Unnest(UDTF):
3064    arg_types = {
3065        "expressions": True,
3066        "alias": False,
3067        "offset": False,
3068    }
3069
3070    @property
3071    def selects(self) -> t.List[Expression]:
3072        columns = super().selects
3073        offset = self.args.get("offset")
3074        if offset:
3075            columns = columns + [to_identifier("offset") if offset is True else offset]
3076        return columns
3077
3078
3079class Update(Expression):
3080    arg_types = {
3081        "with": False,
3082        "this": False,
3083        "expressions": True,
3084        "from": False,
3085        "where": False,
3086        "returning": False,
3087        "order": False,
3088        "limit": False,
3089    }
3090
3091
3092class Values(UDTF):
3093    arg_types = {"expressions": True, "alias": False}
3094
3095
3096class Var(Expression):
3097    pass
3098
3099
3100class Version(Expression):
3101    """
3102    Time travel, iceberg, bigquery etc
3103    https://trino.io/docs/current/connector/iceberg.html?highlight=snapshot#using-snapshots
3104    https://www.databricks.com/blog/2019/02/04/introducing-delta-time-travel-for-large-scale-data-lakes.html
3105    https://cloud.google.com/bigquery/docs/reference/standard-sql/query-syntax#for_system_time_as_of
3106    https://learn.microsoft.com/en-us/sql/relational-databases/tables/querying-data-in-a-system-versioned-temporal-table?view=sql-server-ver16
3107    this is either TIMESTAMP or VERSION
3108    kind is ("AS OF", "BETWEEN")
3109    """
3110
3111    arg_types = {"this": True, "kind": True, "expression": False}
3112
3113
3114class Schema(Expression):
3115    arg_types = {"this": False, "expressions": False}
3116
3117
3118# https://dev.mysql.com/doc/refman/8.0/en/select.html
3119# https://docs.oracle.com/en/database/oracle/oracle-database/19/sqlrf/SELECT.html
3120class Lock(Expression):
3121    arg_types = {"update": True, "expressions": False, "wait": False}
3122
3123
3124class Select(Query):
3125    arg_types = {
3126        "with": False,
3127        "kind": False,
3128        "expressions": False,
3129        "hint": False,
3130        "distinct": False,
3131        "into": False,
3132        "from": False,
3133        **QUERY_MODIFIERS,
3134    }
3135
3136    def from_(
3137        self, expression: ExpOrStr, dialect: DialectType = None, copy: bool = True, **opts
3138    ) -> Select:
3139        """
3140        Set the FROM expression.
3141
3142        Example:
3143            >>> Select().from_("tbl").select("x").sql()
3144            'SELECT x FROM tbl'
3145
3146        Args:
3147            expression : the SQL code strings to parse.
3148                If a `From` instance is passed, this is used as-is.
3149                If another `Expression` instance is passed, it will be wrapped in a `From`.
3150            dialect: the dialect used to parse the input expression.
3151            copy: if `False`, modify this expression instance in-place.
3152            opts: other options to use to parse the input expressions.
3153
3154        Returns:
3155            The modified Select expression.
3156        """
3157        return _apply_builder(
3158            expression=expression,
3159            instance=self,
3160            arg="from",
3161            into=From,
3162            prefix="FROM",
3163            dialect=dialect,
3164            copy=copy,
3165            **opts,
3166        )
3167
3168    def group_by(
3169        self,
3170        *expressions: t.Optional[ExpOrStr],
3171        append: bool = True,
3172        dialect: DialectType = None,
3173        copy: bool = True,
3174        **opts,
3175    ) -> Select:
3176        """
3177        Set the GROUP BY expression.
3178
3179        Example:
3180            >>> Select().from_("tbl").select("x", "COUNT(1)").group_by("x").sql()
3181            'SELECT x, COUNT(1) FROM tbl GROUP BY x'
3182
3183        Args:
3184            *expressions: the SQL code strings to parse.
3185                If a `Group` instance is passed, this is used as-is.
3186                If another `Expression` instance is passed, it will be wrapped in a `Group`.
3187                If nothing is passed in then a group by is not applied to the expression
3188            append: if `True`, add to any existing expressions.
3189                Otherwise, this flattens all the `Group` expression into a single expression.
3190            dialect: the dialect used to parse the input expression.
3191            copy: if `False`, modify this expression instance in-place.
3192            opts: other options to use to parse the input expressions.
3193
3194        Returns:
3195            The modified Select expression.
3196        """
3197        if not expressions:
3198            return self if not copy else self.copy()
3199
3200        return _apply_child_list_builder(
3201            *expressions,
3202            instance=self,
3203            arg="group",
3204            append=append,
3205            copy=copy,
3206            prefix="GROUP BY",
3207            into=Group,
3208            dialect=dialect,
3209            **opts,
3210        )
3211
3212    def sort_by(
3213        self,
3214        *expressions: t.Optional[ExpOrStr],
3215        append: bool = True,
3216        dialect: DialectType = None,
3217        copy: bool = True,
3218        **opts,
3219    ) -> Select:
3220        """
3221        Set the SORT BY expression.
3222
3223        Example:
3224            >>> Select().from_("tbl").select("x").sort_by("x DESC").sql(dialect="hive")
3225            'SELECT x FROM tbl SORT BY x DESC'
3226
3227        Args:
3228            *expressions: the SQL code strings to parse.
3229                If a `Group` instance is passed, this is used as-is.
3230                If another `Expression` instance is passed, it will be wrapped in a `SORT`.
3231            append: if `True`, add to any existing expressions.
3232                Otherwise, this flattens all the `Order` expression into a single expression.
3233            dialect: the dialect used to parse the input expression.
3234            copy: if `False`, modify this expression instance in-place.
3235            opts: other options to use to parse the input expressions.
3236
3237        Returns:
3238            The modified Select expression.
3239        """
3240        return _apply_child_list_builder(
3241            *expressions,
3242            instance=self,
3243            arg="sort",
3244            append=append,
3245            copy=copy,
3246            prefix="SORT BY",
3247            into=Sort,
3248            dialect=dialect,
3249            **opts,
3250        )
3251
3252    def cluster_by(
3253        self,
3254        *expressions: t.Optional[ExpOrStr],
3255        append: bool = True,
3256        dialect: DialectType = None,
3257        copy: bool = True,
3258        **opts,
3259    ) -> Select:
3260        """
3261        Set the CLUSTER BY expression.
3262
3263        Example:
3264            >>> Select().from_("tbl").select("x").cluster_by("x DESC").sql(dialect="hive")
3265            'SELECT x FROM tbl CLUSTER BY x DESC'
3266
3267        Args:
3268            *expressions: the SQL code strings to parse.
3269                If a `Group` instance is passed, this is used as-is.
3270                If another `Expression` instance is passed, it will be wrapped in a `Cluster`.
3271            append: if `True`, add to any existing expressions.
3272                Otherwise, this flattens all the `Order` expression into a single expression.
3273            dialect: the dialect used to parse the input expression.
3274            copy: if `False`, modify this expression instance in-place.
3275            opts: other options to use to parse the input expressions.
3276
3277        Returns:
3278            The modified Select expression.
3279        """
3280        return _apply_child_list_builder(
3281            *expressions,
3282            instance=self,
3283            arg="cluster",
3284            append=append,
3285            copy=copy,
3286            prefix="CLUSTER BY",
3287            into=Cluster,
3288            dialect=dialect,
3289            **opts,
3290        )
3291
3292    def select(
3293        self,
3294        *expressions: t.Optional[ExpOrStr],
3295        append: bool = True,
3296        dialect: DialectType = None,
3297        copy: bool = True,
3298        **opts,
3299    ) -> Select:
3300        return _apply_list_builder(
3301            *expressions,
3302            instance=self,
3303            arg="expressions",
3304            append=append,
3305            dialect=dialect,
3306            into=Expression,
3307            copy=copy,
3308            **opts,
3309        )
3310
3311    def lateral(
3312        self,
3313        *expressions: t.Optional[ExpOrStr],
3314        append: bool = True,
3315        dialect: DialectType = None,
3316        copy: bool = True,
3317        **opts,
3318    ) -> Select:
3319        """
3320        Append to or set the LATERAL expressions.
3321
3322        Example:
3323            >>> Select().select("x").lateral("OUTER explode(y) tbl2 AS z").from_("tbl").sql()
3324            'SELECT x FROM tbl LATERAL VIEW OUTER EXPLODE(y) tbl2 AS z'
3325
3326        Args:
3327            *expressions: the SQL code strings to parse.
3328                If an `Expression` instance is passed, it will be used as-is.
3329            append: if `True`, add to any existing expressions.
3330                Otherwise, this resets the expressions.
3331            dialect: the dialect used to parse the input expressions.
3332            copy: if `False`, modify this expression instance in-place.
3333            opts: other options to use to parse the input expressions.
3334
3335        Returns:
3336            The modified Select expression.
3337        """
3338        return _apply_list_builder(
3339            *expressions,
3340            instance=self,
3341            arg="laterals",
3342            append=append,
3343            into=Lateral,
3344            prefix="LATERAL VIEW",
3345            dialect=dialect,
3346            copy=copy,
3347            **opts,
3348        )
3349
3350    def join(
3351        self,
3352        expression: ExpOrStr,
3353        on: t.Optional[ExpOrStr] = None,
3354        using: t.Optional[ExpOrStr | t.Collection[ExpOrStr]] = None,
3355        append: bool = True,
3356        join_type: t.Optional[str] = None,
3357        join_alias: t.Optional[Identifier | str] = None,
3358        dialect: DialectType = None,
3359        copy: bool = True,
3360        **opts,
3361    ) -> Select:
3362        """
3363        Append to or set the JOIN expressions.
3364
3365        Example:
3366            >>> Select().select("*").from_("tbl").join("tbl2", on="tbl1.y = tbl2.y").sql()
3367            'SELECT * FROM tbl JOIN tbl2 ON tbl1.y = tbl2.y'
3368
3369            >>> Select().select("1").from_("a").join("b", using=["x", "y", "z"]).sql()
3370            'SELECT 1 FROM a JOIN b USING (x, y, z)'
3371
3372            Use `join_type` to change the type of join:
3373
3374            >>> Select().select("*").from_("tbl").join("tbl2", on="tbl1.y = tbl2.y", join_type="left outer").sql()
3375            'SELECT * FROM tbl LEFT OUTER JOIN tbl2 ON tbl1.y = tbl2.y'
3376
3377        Args:
3378            expression: the SQL code string to parse.
3379                If an `Expression` instance is passed, it will be used as-is.
3380            on: optionally specify the join "on" criteria as a SQL string.
3381                If an `Expression` instance is passed, it will be used as-is.
3382            using: optionally specify the join "using" criteria as a SQL string.
3383                If an `Expression` instance is passed, it will be used as-is.
3384            append: if `True`, add to any existing expressions.
3385                Otherwise, this resets the expressions.
3386            join_type: if set, alter the parsed join type.
3387            join_alias: an optional alias for the joined source.
3388            dialect: the dialect used to parse the input expressions.
3389            copy: if `False`, modify this expression instance in-place.
3390            opts: other options to use to parse the input expressions.
3391
3392        Returns:
3393            Select: the modified expression.
3394        """
3395        parse_args: t.Dict[str, t.Any] = {"dialect": dialect, **opts}
3396
3397        try:
3398            expression = maybe_parse(expression, into=Join, prefix="JOIN", **parse_args)
3399        except ParseError:
3400            expression = maybe_parse(expression, into=(Join, Expression), **parse_args)
3401
3402        join = expression if isinstance(expression, Join) else Join(this=expression)
3403
3404        if isinstance(join.this, Select):
3405            join.this.replace(join.this.subquery())
3406
3407        if join_type:
3408            method: t.Optional[Token]
3409            side: t.Optional[Token]
3410            kind: t.Optional[Token]
3411
3412            method, side, kind = maybe_parse(join_type, into="JOIN_TYPE", **parse_args)  # type: ignore
3413
3414            if method:
3415                join.set("method", method.text)
3416            if side:
3417                join.set("side", side.text)
3418            if kind:
3419                join.set("kind", kind.text)
3420
3421        if on:
3422            on = and_(*ensure_list(on), dialect=dialect, copy=copy, **opts)
3423            join.set("on", on)
3424
3425        if using:
3426            join = _apply_list_builder(
3427                *ensure_list(using),
3428                instance=join,
3429                arg="using",
3430                append=append,
3431                copy=copy,
3432                into=Identifier,
3433                **opts,
3434            )
3435
3436        if join_alias:
3437            join.set("this", alias_(join.this, join_alias, table=True))
3438
3439        return _apply_list_builder(
3440            join,
3441            instance=self,
3442            arg="joins",
3443            append=append,
3444            copy=copy,
3445            **opts,
3446        )
3447
3448    def where(
3449        self,
3450        *expressions: t.Optional[ExpOrStr],
3451        append: bool = True,
3452        dialect: DialectType = None,
3453        copy: bool = True,
3454        **opts,
3455    ) -> Select:
3456        """
3457        Append to or set the WHERE expressions.
3458
3459        Example:
3460            >>> Select().select("x").from_("tbl").where("x = 'a' OR x < 'b'").sql()
3461            "SELECT x FROM tbl WHERE x = 'a' OR x < 'b'"
3462
3463        Args:
3464            *expressions: the SQL code strings to parse.
3465                If an `Expression` instance is passed, it will be used as-is.
3466                Multiple expressions are combined with an AND operator.
3467            append: if `True`, AND the new expressions to any existing expression.
3468                Otherwise, this resets the expression.
3469            dialect: the dialect used to parse the input expressions.
3470            copy: if `False`, modify this expression instance in-place.
3471            opts: other options to use to parse the input expressions.
3472
3473        Returns:
3474            Select: the modified expression.
3475        """
3476        return _apply_conjunction_builder(
3477            *expressions,
3478            instance=self,
3479            arg="where",
3480            append=append,
3481            into=Where,
3482            dialect=dialect,
3483            copy=copy,
3484            **opts,
3485        )
3486
3487    def having(
3488        self,
3489        *expressions: t.Optional[ExpOrStr],
3490        append: bool = True,
3491        dialect: DialectType = None,
3492        copy: bool = True,
3493        **opts,
3494    ) -> Select:
3495        """
3496        Append to or set the HAVING expressions.
3497
3498        Example:
3499            >>> Select().select("x", "COUNT(y)").from_("tbl").group_by("x").having("COUNT(y) > 3").sql()
3500            'SELECT x, COUNT(y) FROM tbl GROUP BY x HAVING COUNT(y) > 3'
3501
3502        Args:
3503            *expressions: the SQL code strings to parse.
3504                If an `Expression` instance is passed, it will be used as-is.
3505                Multiple expressions are combined with an AND operator.
3506            append: if `True`, AND the new expressions to any existing expression.
3507                Otherwise, this resets the expression.
3508            dialect: the dialect used to parse the input expressions.
3509            copy: if `False`, modify this expression instance in-place.
3510            opts: other options to use to parse the input expressions.
3511
3512        Returns:
3513            The modified Select expression.
3514        """
3515        return _apply_conjunction_builder(
3516            *expressions,
3517            instance=self,
3518            arg="having",
3519            append=append,
3520            into=Having,
3521            dialect=dialect,
3522            copy=copy,
3523            **opts,
3524        )
3525
3526    def window(
3527        self,
3528        *expressions: t.Optional[ExpOrStr],
3529        append: bool = True,
3530        dialect: DialectType = None,
3531        copy: bool = True,
3532        **opts,
3533    ) -> Select:
3534        return _apply_list_builder(
3535            *expressions,
3536            instance=self,
3537            arg="windows",
3538            append=append,
3539            into=Window,
3540            dialect=dialect,
3541            copy=copy,
3542            **opts,
3543        )
3544
3545    def qualify(
3546        self,
3547        *expressions: t.Optional[ExpOrStr],
3548        append: bool = True,
3549        dialect: DialectType = None,
3550        copy: bool = True,
3551        **opts,
3552    ) -> Select:
3553        return _apply_conjunction_builder(
3554            *expressions,
3555            instance=self,
3556            arg="qualify",
3557            append=append,
3558            into=Qualify,
3559            dialect=dialect,
3560            copy=copy,
3561            **opts,
3562        )
3563
3564    def distinct(
3565        self, *ons: t.Optional[ExpOrStr], distinct: bool = True, copy: bool = True
3566    ) -> Select:
3567        """
3568        Set the OFFSET expression.
3569
3570        Example:
3571            >>> Select().from_("tbl").select("x").distinct().sql()
3572            'SELECT DISTINCT x FROM tbl'
3573
3574        Args:
3575            ons: the expressions to distinct on
3576            distinct: whether the Select should be distinct
3577            copy: if `False`, modify this expression instance in-place.
3578
3579        Returns:
3580            Select: the modified expression.
3581        """
3582        instance = maybe_copy(self, copy)
3583        on = Tuple(expressions=[maybe_parse(on, copy=copy) for on in ons if on]) if ons else None
3584        instance.set("distinct", Distinct(on=on) if distinct else None)
3585        return instance
3586
3587    def ctas(
3588        self,
3589        table: ExpOrStr,
3590        properties: t.Optional[t.Dict] = None,
3591        dialect: DialectType = None,
3592        copy: bool = True,
3593        **opts,
3594    ) -> Create:
3595        """
3596        Convert this expression to a CREATE TABLE AS statement.
3597
3598        Example:
3599            >>> Select().select("*").from_("tbl").ctas("x").sql()
3600            'CREATE TABLE x AS SELECT * FROM tbl'
3601
3602        Args:
3603            table: the SQL code string to parse as the table name.
3604                If another `Expression` instance is passed, it will be used as-is.
3605            properties: an optional mapping of table properties
3606            dialect: the dialect used to parse the input table.
3607            copy: if `False`, modify this expression instance in-place.
3608            opts: other options to use to parse the input table.
3609
3610        Returns:
3611            The new Create expression.
3612        """
3613        instance = maybe_copy(self, copy)
3614        table_expression = maybe_parse(table, into=Table, dialect=dialect, **opts)
3615
3616        properties_expression = None
3617        if properties:
3618            properties_expression = Properties.from_dict(properties)
3619
3620        return Create(
3621            this=table_expression,
3622            kind="TABLE",
3623            expression=instance,
3624            properties=properties_expression,
3625        )
3626
3627    def lock(self, update: bool = True, copy: bool = True) -> Select:
3628        """
3629        Set the locking read mode for this expression.
3630
3631        Examples:
3632            >>> Select().select("x").from_("tbl").where("x = 'a'").lock().sql("mysql")
3633            "SELECT x FROM tbl WHERE x = 'a' FOR UPDATE"
3634
3635            >>> Select().select("x").from_("tbl").where("x = 'a'").lock(update=False).sql("mysql")
3636            "SELECT x FROM tbl WHERE x = 'a' FOR SHARE"
3637
3638        Args:
3639            update: if `True`, the locking type will be `FOR UPDATE`, else it will be `FOR SHARE`.
3640            copy: if `False`, modify this expression instance in-place.
3641
3642        Returns:
3643            The modified expression.
3644        """
3645        inst = maybe_copy(self, copy)
3646        inst.set("locks", [Lock(update=update)])
3647
3648        return inst
3649
3650    def hint(self, *hints: ExpOrStr, dialect: DialectType = None, copy: bool = True) -> Select:
3651        """
3652        Set hints for this expression.
3653
3654        Examples:
3655            >>> Select().select("x").from_("tbl").hint("BROADCAST(y)").sql(dialect="spark")
3656            'SELECT /*+ BROADCAST(y) */ x FROM tbl'
3657
3658        Args:
3659            hints: The SQL code strings to parse as the hints.
3660                If an `Expression` instance is passed, it will be used as-is.
3661            dialect: The dialect used to parse the hints.
3662            copy: If `False`, modify this expression instance in-place.
3663
3664        Returns:
3665            The modified expression.
3666        """
3667        inst = maybe_copy(self, copy)
3668        inst.set(
3669            "hint", Hint(expressions=[maybe_parse(h, copy=copy, dialect=dialect) for h in hints])
3670        )
3671
3672        return inst
3673
3674    @property
3675    def named_selects(self) -> t.List[str]:
3676        return [e.output_name for e in self.expressions if e.alias_or_name]
3677
3678    @property
3679    def is_star(self) -> bool:
3680        return any(expression.is_star for expression in self.expressions)
3681
3682    @property
3683    def selects(self) -> t.List[Expression]:
3684        return self.expressions
3685
3686
3687UNWRAPPED_QUERIES = (Select, Union)
3688
3689
3690class Subquery(DerivedTable, Query):
3691    arg_types = {
3692        "this": True,
3693        "alias": False,
3694        "with": False,
3695        **QUERY_MODIFIERS,
3696    }
3697
3698    def unnest(self):
3699        """Returns the first non subquery."""
3700        expression = self
3701        while isinstance(expression, Subquery):
3702            expression = expression.this
3703        return expression
3704
3705    def unwrap(self) -> Subquery:
3706        expression = self
3707        while expression.same_parent and expression.is_wrapper:
3708            expression = t.cast(Subquery, expression.parent)
3709        return expression
3710
3711    def select(
3712        self,
3713        *expressions: t.Optional[ExpOrStr],
3714        append: bool = True,
3715        dialect: DialectType = None,
3716        copy: bool = True,
3717        **opts,
3718    ) -> Subquery:
3719        this = maybe_copy(self, copy)
3720        this.unnest().select(*expressions, append=append, dialect=dialect, copy=False, **opts)
3721        return this
3722
3723    @property
3724    def is_wrapper(self) -> bool:
3725        """
3726        Whether this Subquery acts as a simple wrapper around another expression.
3727
3728        SELECT * FROM (((SELECT * FROM t)))
3729                      ^
3730                      This corresponds to a "wrapper" Subquery node
3731        """
3732        return all(v is None for k, v in self.args.items() if k != "this")
3733
3734    @property
3735    def is_star(self) -> bool:
3736        return self.this.is_star
3737
3738    @property
3739    def output_name(self) -> str:
3740        return self.alias
3741
3742
3743class TableSample(Expression):
3744    arg_types = {
3745        "this": False,
3746        "expressions": False,
3747        "method": False,
3748        "bucket_numerator": False,
3749        "bucket_denominator": False,
3750        "bucket_field": False,
3751        "percent": False,
3752        "rows": False,
3753        "size": False,
3754        "seed": False,
3755    }
3756
3757
3758class Tag(Expression):
3759    """Tags are used for generating arbitrary sql like SELECT <span>x</span>."""
3760
3761    arg_types = {
3762        "this": False,
3763        "prefix": False,
3764        "postfix": False,
3765    }
3766
3767
3768# Represents both the standard SQL PIVOT operator and DuckDB's "simplified" PIVOT syntax
3769# https://duckdb.org/docs/sql/statements/pivot
3770class Pivot(Expression):
3771    arg_types = {
3772        "this": False,
3773        "alias": False,
3774        "expressions": False,
3775        "field": False,
3776        "unpivot": False,
3777        "using": False,
3778        "group": False,
3779        "columns": False,
3780        "include_nulls": False,
3781    }
3782
3783    @property
3784    def unpivot(self) -> bool:
3785        return bool(self.args.get("unpivot"))
3786
3787
3788class Window(Condition):
3789    arg_types = {
3790        "this": True,
3791        "partition_by": False,
3792        "order": False,
3793        "spec": False,
3794        "alias": False,
3795        "over": False,
3796        "first": False,
3797    }
3798
3799
3800class WindowSpec(Expression):
3801    arg_types = {
3802        "kind": False,
3803        "start": False,
3804        "start_side": False,
3805        "end": False,
3806        "end_side": False,
3807    }
3808
3809
3810class PreWhere(Expression):
3811    pass
3812
3813
3814class Where(Expression):
3815    pass
3816
3817
3818class Star(Expression):
3819    arg_types = {"except": False, "replace": False}
3820
3821    @property
3822    def name(self) -> str:
3823        return "*"
3824
3825    @property
3826    def output_name(self) -> str:
3827        return self.name
3828
3829
3830class Parameter(Condition):
3831    arg_types = {"this": True, "expression": False}
3832
3833
3834class SessionParameter(Condition):
3835    arg_types = {"this": True, "kind": False}
3836
3837
3838class Placeholder(Condition):
3839    arg_types = {"this": False, "kind": False}
3840
3841    @property
3842    def name(self) -> str:
3843        return self.this or "?"
3844
3845
3846class Null(Condition):
3847    arg_types: t.Dict[str, t.Any] = {}
3848
3849    @property
3850    def name(self) -> str:
3851        return "NULL"
3852
3853
3854class Boolean(Condition):
3855    pass
3856
3857
3858class DataTypeParam(Expression):
3859    arg_types = {"this": True, "expression": False}
3860
3861    @property
3862    def name(self) -> str:
3863        return self.this.name
3864
3865
3866class DataType(Expression):
3867    arg_types = {
3868        "this": True,
3869        "expressions": False,
3870        "nested": False,
3871        "values": False,
3872        "prefix": False,
3873        "kind": False,
3874    }
3875
3876    class Type(AutoName):
3877        ARRAY = auto()
3878        AGGREGATEFUNCTION = auto()
3879        SIMPLEAGGREGATEFUNCTION = auto()
3880        BIGDECIMAL = auto()
3881        BIGINT = auto()
3882        BIGSERIAL = auto()
3883        BINARY = auto()
3884        BIT = auto()
3885        BOOLEAN = auto()
3886        BPCHAR = auto()
3887        CHAR = auto()
3888        DATE = auto()
3889        DATE32 = auto()
3890        DATEMULTIRANGE = auto()
3891        DATERANGE = auto()
3892        DATETIME = auto()
3893        DATETIME64 = auto()
3894        DECIMAL = auto()
3895        DOUBLE = auto()
3896        ENUM = auto()
3897        ENUM8 = auto()
3898        ENUM16 = auto()
3899        FIXEDSTRING = auto()
3900        FLOAT = auto()
3901        GEOGRAPHY = auto()
3902        GEOMETRY = auto()
3903        HLLSKETCH = auto()
3904        HSTORE = auto()
3905        IMAGE = auto()
3906        INET = auto()
3907        INT = auto()
3908        INT128 = auto()
3909        INT256 = auto()
3910        INT4MULTIRANGE = auto()
3911        INT4RANGE = auto()
3912        INT8MULTIRANGE = auto()
3913        INT8RANGE = auto()
3914        INTERVAL = auto()
3915        IPADDRESS = auto()
3916        IPPREFIX = auto()
3917        IPV4 = auto()
3918        IPV6 = auto()
3919        JSON = auto()
3920        JSONB = auto()
3921        LONGBLOB = auto()
3922        LONGTEXT = auto()
3923        LOWCARDINALITY = auto()
3924        MAP = auto()
3925        MEDIUMBLOB = auto()
3926        MEDIUMINT = auto()
3927        MEDIUMTEXT = auto()
3928        MONEY = auto()
3929        NAME = auto()
3930        NCHAR = auto()
3931        NESTED = auto()
3932        NULL = auto()
3933        NULLABLE = auto()
3934        NUMMULTIRANGE = auto()
3935        NUMRANGE = auto()
3936        NVARCHAR = auto()
3937        OBJECT = auto()
3938        ROWVERSION = auto()
3939        SERIAL = auto()
3940        SET = auto()
3941        SMALLINT = auto()
3942        SMALLMONEY = auto()
3943        SMALLSERIAL = auto()
3944        STRUCT = auto()
3945        SUPER = auto()
3946        TEXT = auto()
3947        TINYBLOB = auto()
3948        TINYTEXT = auto()
3949        TIME = auto()
3950        TIMETZ = auto()
3951        TIMESTAMP = auto()
3952        TIMESTAMPNTZ = auto()
3953        TIMESTAMPLTZ = auto()
3954        TIMESTAMPTZ = auto()
3955        TIMESTAMP_S = auto()
3956        TIMESTAMP_MS = auto()
3957        TIMESTAMP_NS = auto()
3958        TINYINT = auto()
3959        TSMULTIRANGE = auto()
3960        TSRANGE = auto()
3961        TSTZMULTIRANGE = auto()
3962        TSTZRANGE = auto()
3963        UBIGINT = auto()
3964        UINT = auto()
3965        UINT128 = auto()
3966        UINT256 = auto()
3967        UMEDIUMINT = auto()
3968        UDECIMAL = auto()
3969        UNIQUEIDENTIFIER = auto()
3970        UNKNOWN = auto()  # Sentinel value, useful for type annotation
3971        USERDEFINED = "USER-DEFINED"
3972        USMALLINT = auto()
3973        UTINYINT = auto()
3974        UUID = auto()
3975        VARBINARY = auto()
3976        VARCHAR = auto()
3977        VARIANT = auto()
3978        XML = auto()
3979        YEAR = auto()
3980        TDIGEST = auto()
3981
3982    STRUCT_TYPES = {
3983        Type.NESTED,
3984        Type.OBJECT,
3985        Type.STRUCT,
3986    }
3987
3988    NESTED_TYPES = {
3989        *STRUCT_TYPES,
3990        Type.ARRAY,
3991        Type.MAP,
3992    }
3993
3994    TEXT_TYPES = {
3995        Type.CHAR,
3996        Type.NCHAR,
3997        Type.NVARCHAR,
3998        Type.TEXT,
3999        Type.VARCHAR,
4000        Type.NAME,
4001    }
4002
4003    SIGNED_INTEGER_TYPES = {
4004        Type.BIGINT,
4005        Type.INT,
4006        Type.INT128,
4007        Type.INT256,
4008        Type.MEDIUMINT,
4009        Type.SMALLINT,
4010        Type.TINYINT,
4011    }
4012
4013    UNSIGNED_INTEGER_TYPES = {
4014        Type.UBIGINT,
4015        Type.UINT,
4016        Type.UINT128,
4017        Type.UINT256,
4018        Type.UMEDIUMINT,
4019        Type.USMALLINT,
4020        Type.UTINYINT,
4021    }
4022
4023    INTEGER_TYPES = {
4024        *SIGNED_INTEGER_TYPES,
4025        *UNSIGNED_INTEGER_TYPES,
4026        Type.BIT,
4027    }
4028
4029    FLOAT_TYPES = {
4030        Type.DOUBLE,
4031        Type.FLOAT,
4032    }
4033
4034    REAL_TYPES = {
4035        *FLOAT_TYPES,
4036        Type.BIGDECIMAL,
4037        Type.DECIMAL,
4038        Type.MONEY,
4039        Type.SMALLMONEY,
4040        Type.UDECIMAL,
4041    }
4042
4043    NUMERIC_TYPES = {
4044        *INTEGER_TYPES,
4045        *REAL_TYPES,
4046    }
4047
4048    TEMPORAL_TYPES = {
4049        Type.DATE,
4050        Type.DATE32,
4051        Type.DATETIME,
4052        Type.DATETIME64,
4053        Type.TIME,
4054        Type.TIMESTAMP,
4055        Type.TIMESTAMPNTZ,
4056        Type.TIMESTAMPLTZ,
4057        Type.TIMESTAMPTZ,
4058        Type.TIMESTAMP_MS,
4059        Type.TIMESTAMP_NS,
4060        Type.TIMESTAMP_S,
4061        Type.TIMETZ,
4062    }
4063
4064    @classmethod
4065    def build(
4066        cls,
4067        dtype: DATA_TYPE,
4068        dialect: DialectType = None,
4069        udt: bool = False,
4070        copy: bool = True,
4071        **kwargs,
4072    ) -> DataType:
4073        """
4074        Constructs a DataType object.
4075
4076        Args:
4077            dtype: the data type of interest.
4078            dialect: the dialect to use for parsing `dtype`, in case it's a string.
4079            udt: when set to True, `dtype` will be used as-is if it can't be parsed into a
4080                DataType, thus creating a user-defined type.
4081            copy: whether to copy the data type.
4082            kwargs: additional arguments to pass in the constructor of DataType.
4083
4084        Returns:
4085            The constructed DataType object.
4086        """
4087        from sqlglot import parse_one
4088
4089        if isinstance(dtype, str):
4090            if dtype.upper() == "UNKNOWN":
4091                return DataType(this=DataType.Type.UNKNOWN, **kwargs)
4092
4093            try:
4094                data_type_exp = parse_one(
4095                    dtype, read=dialect, into=DataType, error_level=ErrorLevel.IGNORE
4096                )
4097            except ParseError:
4098                if udt:
4099                    return DataType(this=DataType.Type.USERDEFINED, kind=dtype, **kwargs)
4100                raise
4101        elif isinstance(dtype, DataType.Type):
4102            data_type_exp = DataType(this=dtype)
4103        elif isinstance(dtype, DataType):
4104            return maybe_copy(dtype, copy)
4105        else:
4106            raise ValueError(f"Invalid data type: {type(dtype)}. Expected str or DataType.Type")
4107
4108        return DataType(**{**data_type_exp.args, **kwargs})
4109
4110    def is_type(self, *dtypes: DATA_TYPE) -> bool:
4111        """
4112        Checks whether this DataType matches one of the provided data types. Nested types or precision
4113        will be compared using "structural equivalence" semantics, so e.g. array<int> != array<float>.
4114
4115        Args:
4116            dtypes: the data types to compare this DataType to.
4117
4118        Returns:
4119            True, if and only if there is a type in `dtypes` which is equal to this DataType.
4120        """
4121        for dtype in dtypes:
4122            other = DataType.build(dtype, copy=False, udt=True)
4123
4124            if (
4125                other.expressions
4126                or self.this == DataType.Type.USERDEFINED
4127                or other.this == DataType.Type.USERDEFINED
4128            ):
4129                matches = self == other
4130            else:
4131                matches = self.this == other.this
4132
4133            if matches:
4134                return True
4135        return False
4136
4137
4138DATA_TYPE = t.Union[str, DataType, DataType.Type]
4139
4140
4141# https://www.postgresql.org/docs/15/datatype-pseudo.html
4142class PseudoType(DataType):
4143    arg_types = {"this": True}
4144
4145
4146# https://www.postgresql.org/docs/15/datatype-oid.html
4147class ObjectIdentifier(DataType):
4148    arg_types = {"this": True}
4149
4150
4151# WHERE x <OP> EXISTS|ALL|ANY|SOME(SELECT ...)
4152class SubqueryPredicate(Predicate):
4153    pass
4154
4155
4156class All(SubqueryPredicate):
4157    pass
4158
4159
4160class Any(SubqueryPredicate):
4161    pass
4162
4163
4164class Exists(SubqueryPredicate):
4165    pass
4166
4167
4168# Commands to interact with the databases or engines. For most of the command
4169# expressions we parse whatever comes after the command's name as a string.
4170class Command(Expression):
4171    arg_types = {"this": True, "expression": False}
4172
4173
4174class Transaction(Expression):
4175    arg_types = {"this": False, "modes": False, "mark": False}
4176
4177
4178class Commit(Expression):
4179    arg_types = {"chain": False, "this": False, "durability": False}
4180
4181
4182class Rollback(Expression):
4183    arg_types = {"savepoint": False, "this": False}
4184
4185
4186class AlterTable(Expression):
4187    arg_types = {
4188        "this": True,
4189        "actions": True,
4190        "exists": False,
4191        "only": False,
4192        "options": False,
4193        "cluster": False,
4194    }
4195
4196
4197class AddConstraint(Expression):
4198    arg_types = {"expressions": True}
4199
4200
4201class DropPartition(Expression):
4202    arg_types = {"expressions": True, "exists": False}
4203
4204
4205# https://clickhouse.com/docs/en/sql-reference/statements/alter/partition#replace-partition
4206class ReplacePartition(Expression):
4207    arg_types = {"expression": True, "source": True}
4208
4209
4210# Binary expressions like (ADD a b)
4211class Binary(Condition):
4212    arg_types = {"this": True, "expression": True}
4213
4214    @property
4215    def left(self) -> Expression:
4216        return self.this
4217
4218    @property
4219    def right(self) -> Expression:
4220        return self.expression
4221
4222
4223class Add(Binary):
4224    pass
4225
4226
4227class Connector(Binary):
4228    pass
4229
4230
4231class And(Connector):
4232    pass
4233
4234
4235class Or(Connector):
4236    pass
4237
4238
4239class BitwiseAnd(Binary):
4240    pass
4241
4242
4243class BitwiseLeftShift(Binary):
4244    pass
4245
4246
4247class BitwiseOr(Binary):
4248    pass
4249
4250
4251class BitwiseRightShift(Binary):
4252    pass
4253
4254
4255class BitwiseXor(Binary):
4256    pass
4257
4258
4259class Div(Binary):
4260    arg_types = {"this": True, "expression": True, "typed": False, "safe": False}
4261
4262
4263class Overlaps(Binary):
4264    pass
4265
4266
4267class Dot(Binary):
4268    @property
4269    def is_star(self) -> bool:
4270        return self.expression.is_star
4271
4272    @property
4273    def name(self) -> str:
4274        return self.expression.name
4275
4276    @property
4277    def output_name(self) -> str:
4278        return self.name
4279
4280    @classmethod
4281    def build(self, expressions: t.Sequence[Expression]) -> Dot:
4282        """Build a Dot object with a sequence of expressions."""
4283        if len(expressions) < 2:
4284            raise ValueError("Dot requires >= 2 expressions.")
4285
4286        return t.cast(Dot, reduce(lambda x, y: Dot(this=x, expression=y), expressions))
4287
4288    @property
4289    def parts(self) -> t.List[Expression]:
4290        """Return the parts of a table / column in order catalog, db, table."""
4291        this, *parts = self.flatten()
4292
4293        parts.reverse()
4294
4295        for arg in COLUMN_PARTS:
4296            part = this.args.get(arg)
4297
4298            if isinstance(part, Expression):
4299                parts.append(part)
4300
4301        parts.reverse()
4302        return parts
4303
4304
4305class DPipe(Binary):
4306    arg_types = {"this": True, "expression": True, "safe": False}
4307
4308
4309class EQ(Binary, Predicate):
4310    pass
4311
4312
4313class NullSafeEQ(Binary, Predicate):
4314    pass
4315
4316
4317class NullSafeNEQ(Binary, Predicate):
4318    pass
4319
4320
4321# Represents e.g. := in DuckDB which is mostly used for setting parameters
4322class PropertyEQ(Binary):
4323    pass
4324
4325
4326class Distance(Binary):
4327    pass
4328
4329
4330class Escape(Binary):
4331    pass
4332
4333
4334class Glob(Binary, Predicate):
4335    pass
4336
4337
4338class GT(Binary, Predicate):
4339    pass
4340
4341
4342class GTE(Binary, Predicate):
4343    pass
4344
4345
4346class ILike(Binary, Predicate):
4347    pass
4348
4349
4350class ILikeAny(Binary, Predicate):
4351    pass
4352
4353
4354class IntDiv(Binary):
4355    pass
4356
4357
4358class Is(Binary, Predicate):
4359    pass
4360
4361
4362class Kwarg(Binary):
4363    """Kwarg in special functions like func(kwarg => y)."""
4364
4365
4366class Like(Binary, Predicate):
4367    pass
4368
4369
4370class LikeAny(Binary, Predicate):
4371    pass
4372
4373
4374class LT(Binary, Predicate):
4375    pass
4376
4377
4378class LTE(Binary, Predicate):
4379    pass
4380
4381
4382class Mod(Binary):
4383    pass
4384
4385
4386class Mul(Binary):
4387    pass
4388
4389
4390class NEQ(Binary, Predicate):
4391    pass
4392
4393
4394# https://www.postgresql.org/docs/current/ddl-schemas.html#DDL-SCHEMAS-PATH
4395class Operator(Binary):
4396    arg_types = {"this": True, "operator": True, "expression": True}
4397
4398
4399class SimilarTo(Binary, Predicate):
4400    pass
4401
4402
4403class Slice(Binary):
4404    arg_types = {"this": False, "expression": False}
4405
4406
4407class Sub(Binary):
4408    pass
4409
4410
4411# Unary Expressions
4412# (NOT a)
4413class Unary(Condition):
4414    pass
4415
4416
4417class BitwiseNot(Unary):
4418    pass
4419
4420
4421class Not(Unary):
4422    pass
4423
4424
4425class Paren(Unary):
4426    @property
4427    def output_name(self) -> str:
4428        return self.this.name
4429
4430
4431class Neg(Unary):
4432    pass
4433
4434
4435class Alias(Expression):
4436    arg_types = {"this": True, "alias": False}
4437
4438    @property
4439    def output_name(self) -> str:
4440        return self.alias
4441
4442
4443# BigQuery requires the UNPIVOT column list aliases to be either strings or ints, but
4444# other dialects require identifiers. This enables us to transpile between them easily.
4445class PivotAlias(Alias):
4446    pass
4447
4448
4449class Aliases(Expression):
4450    arg_types = {"this": True, "expressions": True}
4451
4452    @property
4453    def aliases(self):
4454        return self.expressions
4455
4456
4457# https://docs.aws.amazon.com/redshift/latest/dg/query-super.html
4458class AtIndex(Expression):
4459    arg_types = {"this": True, "expression": True}
4460
4461
4462class AtTimeZone(Expression):
4463    arg_types = {"this": True, "zone": True}
4464
4465
4466class FromTimeZone(Expression):
4467    arg_types = {"this": True, "zone": True}
4468
4469
4470class Between(Predicate):
4471    arg_types = {"this": True, "low": True, "high": True}
4472
4473
4474class Bracket(Condition):
4475    # https://cloud.google.com/bigquery/docs/reference/standard-sql/operators#array_subscript_operator
4476    arg_types = {
4477        "this": True,
4478        "expressions": True,
4479        "offset": False,
4480        "safe": False,
4481        "returns_list_for_maps": False,
4482    }
4483
4484    @property
4485    def output_name(self) -> str:
4486        if len(self.expressions) == 1:
4487            return self.expressions[0].output_name
4488
4489        return super().output_name
4490
4491
4492class Distinct(Expression):
4493    arg_types = {"expressions": False, "on": False}
4494
4495
4496class In(Predicate):
4497    arg_types = {
4498        "this": True,
4499        "expressions": False,
4500        "query": False,
4501        "unnest": False,
4502        "field": False,
4503        "is_global": False,
4504    }
4505
4506
4507# https://cloud.google.com/bigquery/docs/reference/standard-sql/procedural-language#for-in
4508class ForIn(Expression):
4509    arg_types = {"this": True, "expression": True}
4510
4511
4512class TimeUnit(Expression):
4513    """Automatically converts unit arg into a var."""
4514
4515    arg_types = {"unit": False}
4516
4517    UNABBREVIATED_UNIT_NAME = {
4518        "D": "DAY",
4519        "H": "HOUR",
4520        "M": "MINUTE",
4521        "MS": "MILLISECOND",
4522        "NS": "NANOSECOND",
4523        "Q": "QUARTER",
4524        "S": "SECOND",
4525        "US": "MICROSECOND",
4526        "W": "WEEK",
4527        "Y": "YEAR",
4528    }
4529
4530    VAR_LIKE = (Column, Literal, Var)
4531
4532    def __init__(self, **args):
4533        unit = args.get("unit")
4534        if isinstance(unit, self.VAR_LIKE):
4535            args["unit"] = Var(
4536                this=(self.UNABBREVIATED_UNIT_NAME.get(unit.name) or unit.name).upper()
4537            )
4538        elif isinstance(unit, Week):
4539            unit.set("this", Var(this=unit.this.name.upper()))
4540
4541        super().__init__(**args)
4542
4543    @property
4544    def unit(self) -> t.Optional[Var | IntervalSpan]:
4545        return self.args.get("unit")
4546
4547
4548class IntervalOp(TimeUnit):
4549    arg_types = {"unit": True, "expression": True}
4550
4551    def interval(self):
4552        return Interval(
4553            this=self.expression.copy(),
4554            unit=self.unit.copy(),
4555        )
4556
4557
4558# https://www.oracletutorial.com/oracle-basics/oracle-interval/
4559# https://trino.io/docs/current/language/types.html#interval-day-to-second
4560# https://docs.databricks.com/en/sql/language-manual/data-types/interval-type.html
4561class IntervalSpan(DataType):
4562    arg_types = {"this": True, "expression": True}
4563
4564
4565class Interval(TimeUnit):
4566    arg_types = {"this": False, "unit": False}
4567
4568
4569class IgnoreNulls(Expression):
4570    pass
4571
4572
4573class RespectNulls(Expression):
4574    pass
4575
4576
4577# https://cloud.google.com/bigquery/docs/reference/standard-sql/aggregate-function-calls#max_min_clause
4578class HavingMax(Expression):
4579    arg_types = {"this": True, "expression": True, "max": True}
4580
4581
4582# Functions
4583class Func(Condition):
4584    """
4585    The base class for all function expressions.
4586
4587    Attributes:
4588        is_var_len_args (bool): if set to True the last argument defined in arg_types will be
4589            treated as a variable length argument and the argument's value will be stored as a list.
4590        _sql_names (list): the SQL name (1st item in the list) and aliases (subsequent items) for this
4591            function expression. These values are used to map this node to a name during parsing as
4592            well as to provide the function's name during SQL string generation. By default the SQL
4593            name is set to the expression's class name transformed to snake case.
4594    """
4595
4596    is_var_len_args = False
4597
4598    @classmethod
4599    def from_arg_list(cls, args):
4600        if cls.is_var_len_args:
4601            all_arg_keys = list(cls.arg_types)
4602            # If this function supports variable length argument treat the last argument as such.
4603            non_var_len_arg_keys = all_arg_keys[:-1] if cls.is_var_len_args else all_arg_keys
4604            num_non_var = len(non_var_len_arg_keys)
4605
4606            args_dict = {arg_key: arg for arg, arg_key in zip(args, non_var_len_arg_keys)}
4607            args_dict[all_arg_keys[-1]] = args[num_non_var:]
4608        else:
4609            args_dict = {arg_key: arg for arg, arg_key in zip(args, cls.arg_types)}
4610
4611        return cls(**args_dict)
4612
4613    @classmethod
4614    def sql_names(cls):
4615        if cls is Func:
4616            raise NotImplementedError(
4617                "SQL name is only supported by concrete function implementations"
4618            )
4619        if "_sql_names" not in cls.__dict__:
4620            cls._sql_names = [camel_to_snake_case(cls.__name__)]
4621        return cls._sql_names
4622
4623    @classmethod
4624    def sql_name(cls):
4625        return cls.sql_names()[0]
4626
4627    @classmethod
4628    def default_parser_mappings(cls):
4629        return {name: cls.from_arg_list for name in cls.sql_names()}
4630
4631
4632class AggFunc(Func):
4633    pass
4634
4635
4636class ParameterizedAgg(AggFunc):
4637    arg_types = {"this": True, "expressions": True, "params": True}
4638
4639
4640class Abs(Func):
4641    pass
4642
4643
4644class ArgMax(AggFunc):
4645    arg_types = {"this": True, "expression": True, "count": False}
4646    _sql_names = ["ARG_MAX", "ARGMAX", "MAX_BY"]
4647
4648
4649class ArgMin(AggFunc):
4650    arg_types = {"this": True, "expression": True, "count": False}
4651    _sql_names = ["ARG_MIN", "ARGMIN", "MIN_BY"]
4652
4653
4654class ApproxTopK(AggFunc):
4655    arg_types = {"this": True, "expression": False, "counters": False}
4656
4657
4658class Flatten(Func):
4659    pass
4660
4661
4662# https://spark.apache.org/docs/latest/api/sql/index.html#transform
4663class Transform(Func):
4664    arg_types = {"this": True, "expression": True}
4665
4666
4667class Anonymous(Func):
4668    arg_types = {"this": True, "expressions": False}
4669    is_var_len_args = True
4670
4671    @property
4672    def name(self) -> str:
4673        return self.this if isinstance(self.this, str) else self.this.name
4674
4675
4676class AnonymousAggFunc(AggFunc):
4677    arg_types = {"this": True, "expressions": False}
4678    is_var_len_args = True
4679
4680
4681# https://clickhouse.com/docs/en/sql-reference/aggregate-functions/combinators
4682class CombinedAggFunc(AnonymousAggFunc):
4683    arg_types = {"this": True, "expressions": False, "parts": True}
4684
4685
4686class CombinedParameterizedAgg(ParameterizedAgg):
4687    arg_types = {"this": True, "expressions": True, "params": True, "parts": True}
4688
4689
4690# https://docs.snowflake.com/en/sql-reference/functions/hll
4691# https://docs.aws.amazon.com/redshift/latest/dg/r_HLL_function.html
4692class Hll(AggFunc):
4693    arg_types = {"this": True, "expressions": False}
4694    is_var_len_args = True
4695
4696
4697class ApproxDistinct(AggFunc):
4698    arg_types = {"this": True, "accuracy": False}
4699    _sql_names = ["APPROX_DISTINCT", "APPROX_COUNT_DISTINCT"]
4700
4701
4702class Array(Func):
4703    arg_types = {"expressions": False}
4704    is_var_len_args = True
4705
4706
4707# https://docs.snowflake.com/en/sql-reference/functions/to_array
4708class ToArray(Func):
4709    pass
4710
4711
4712# https://docs.snowflake.com/en/sql-reference/functions/to_char
4713# https://docs.oracle.com/en/database/oracle/oracle-database/23/sqlrf/TO_CHAR-number.html
4714class ToChar(Func):
4715    arg_types = {"this": True, "format": False, "nlsparam": False}
4716
4717
4718# https://docs.snowflake.com/en/sql-reference/functions/to_decimal
4719# https://docs.oracle.com/en/database/oracle/oracle-database/23/sqlrf/TO_NUMBER.html
4720class ToNumber(Func):
4721    arg_types = {
4722        "this": True,
4723        "format": False,
4724        "nlsparam": False,
4725        "precision": False,
4726        "scale": False,
4727    }
4728
4729
4730# https://learn.microsoft.com/en-us/sql/t-sql/functions/cast-and-convert-transact-sql?view=sql-server-ver16#syntax
4731class Convert(Func):
4732    arg_types = {"this": True, "expression": True, "style": False}
4733
4734
4735class GenerateSeries(Func):
4736    arg_types = {"start": True, "end": True, "step": False, "is_end_exclusive": False}
4737
4738
4739class ArrayAgg(AggFunc):
4740    pass
4741
4742
4743class ArrayUniqueAgg(AggFunc):
4744    pass
4745
4746
4747class ArrayAll(Func):
4748    arg_types = {"this": True, "expression": True}
4749
4750
4751# Represents Python's `any(f(x) for x in array)`, where `array` is `this` and `f` is `expression`
4752class ArrayAny(Func):
4753    arg_types = {"this": True, "expression": True}
4754
4755
4756class ArrayConcat(Func):
4757    _sql_names = ["ARRAY_CONCAT", "ARRAY_CAT"]
4758    arg_types = {"this": True, "expressions": False}
4759    is_var_len_args = True
4760
4761
4762class ArrayContains(Binary, Func):
4763    pass
4764
4765
4766class ArrayContained(Binary):
4767    pass
4768
4769
4770class ArrayFilter(Func):
4771    arg_types = {"this": True, "expression": True}
4772    _sql_names = ["FILTER", "ARRAY_FILTER"]
4773
4774
4775class ArrayToString(Func):
4776    arg_types = {"this": True, "expression": True, "null": False}
4777    _sql_names = ["ARRAY_TO_STRING", "ARRAY_JOIN"]
4778
4779
4780class ArrayOverlaps(Binary, Func):
4781    pass
4782
4783
4784class ArraySize(Func):
4785    arg_types = {"this": True, "expression": False}
4786    _sql_names = ["ARRAY_SIZE", "ARRAY_LENGTH"]
4787
4788
4789class ArraySort(Func):
4790    arg_types = {"this": True, "expression": False}
4791
4792
4793class ArraySum(Func):
4794    arg_types = {"this": True, "expression": False}
4795
4796
4797class ArrayUnionAgg(AggFunc):
4798    pass
4799
4800
4801class Avg(AggFunc):
4802    pass
4803
4804
4805class AnyValue(AggFunc):
4806    pass
4807
4808
4809class Lag(AggFunc):
4810    arg_types = {"this": True, "offset": False, "default": False}
4811
4812
4813class Lead(AggFunc):
4814    arg_types = {"this": True, "offset": False, "default": False}
4815
4816
4817# some dialects have a distinction between first and first_value, usually first is an aggregate func
4818# and first_value is a window func
4819class First(AggFunc):
4820    pass
4821
4822
4823class Last(AggFunc):
4824    pass
4825
4826
4827class FirstValue(AggFunc):
4828    pass
4829
4830
4831class LastValue(AggFunc):
4832    pass
4833
4834
4835class NthValue(AggFunc):
4836    arg_types = {"this": True, "offset": True}
4837
4838
4839class Case(Func):
4840    arg_types = {"this": False, "ifs": True, "default": False}
4841
4842    def when(self, condition: ExpOrStr, then: ExpOrStr, copy: bool = True, **opts) -> Case:
4843        instance = maybe_copy(self, copy)
4844        instance.append(
4845            "ifs",
4846            If(
4847                this=maybe_parse(condition, copy=copy, **opts),
4848                true=maybe_parse(then, copy=copy, **opts),
4849            ),
4850        )
4851        return instance
4852
4853    def else_(self, condition: ExpOrStr, copy: bool = True, **opts) -> Case:
4854        instance = maybe_copy(self, copy)
4855        instance.set("default", maybe_parse(condition, copy=copy, **opts))
4856        return instance
4857
4858
4859class Cast(Func):
4860    arg_types = {
4861        "this": True,
4862        "to": True,
4863        "format": False,
4864        "safe": False,
4865        "action": False,
4866    }
4867
4868    @property
4869    def name(self) -> str:
4870        return self.this.name
4871
4872    @property
4873    def to(self) -> DataType:
4874        return self.args["to"]
4875
4876    @property
4877    def output_name(self) -> str:
4878        return self.name
4879
4880    def is_type(self, *dtypes: DATA_TYPE) -> bool:
4881        """
4882        Checks whether this Cast's DataType matches one of the provided data types. Nested types
4883        like arrays or structs will be compared using "structural equivalence" semantics, so e.g.
4884        array<int> != array<float>.
4885
4886        Args:
4887            dtypes: the data types to compare this Cast's DataType to.
4888
4889        Returns:
4890            True, if and only if there is a type in `dtypes` which is equal to this Cast's DataType.
4891        """
4892        return self.to.is_type(*dtypes)
4893
4894
4895class TryCast(Cast):
4896    pass
4897
4898
4899class Try(Func):
4900    pass
4901
4902
4903class CastToStrType(Func):
4904    arg_types = {"this": True, "to": True}
4905
4906
4907class Collate(Binary, Func):
4908    pass
4909
4910
4911class Ceil(Func):
4912    arg_types = {"this": True, "decimals": False}
4913    _sql_names = ["CEIL", "CEILING"]
4914
4915
4916class Coalesce(Func):
4917    arg_types = {"this": True, "expressions": False}
4918    is_var_len_args = True
4919    _sql_names = ["COALESCE", "IFNULL", "NVL"]
4920
4921
4922class Chr(Func):
4923    arg_types = {"this": True, "charset": False, "expressions": False}
4924    is_var_len_args = True
4925    _sql_names = ["CHR", "CHAR"]
4926
4927
4928class Concat(Func):
4929    arg_types = {"expressions": True, "safe": False, "coalesce": False}
4930    is_var_len_args = True
4931
4932
4933class ConcatWs(Concat):
4934    _sql_names = ["CONCAT_WS"]
4935
4936
4937# https://docs.oracle.com/cd/B13789_01/server.101/b10759/operators004.htm#i1035022
4938class ConnectByRoot(Func):
4939    pass
4940
4941
4942class Count(AggFunc):
4943    arg_types = {"this": False, "expressions": False}
4944    is_var_len_args = True
4945
4946
4947class CountIf(AggFunc):
4948    _sql_names = ["COUNT_IF", "COUNTIF"]
4949
4950
4951# cube root
4952class Cbrt(Func):
4953    pass
4954
4955
4956class CurrentDate(Func):
4957    arg_types = {"this": False}
4958
4959
4960class CurrentDatetime(Func):
4961    arg_types = {"this": False}
4962
4963
4964class CurrentTime(Func):
4965    arg_types = {"this": False}
4966
4967
4968class CurrentTimestamp(Func):
4969    arg_types = {"this": False, "transaction": False}
4970
4971
4972class CurrentUser(Func):
4973    arg_types = {"this": False}
4974
4975
4976class DateAdd(Func, IntervalOp):
4977    arg_types = {"this": True, "expression": True, "unit": False}
4978
4979
4980class DateSub(Func, IntervalOp):
4981    arg_types = {"this": True, "expression": True, "unit": False}
4982
4983
4984class DateDiff(Func, TimeUnit):
4985    _sql_names = ["DATEDIFF", "DATE_DIFF"]
4986    arg_types = {"this": True, "expression": True, "unit": False}
4987
4988
4989class DateTrunc(Func):
4990    arg_types = {"unit": True, "this": True, "zone": False}
4991
4992    def __init__(self, **args):
4993        unit = args.get("unit")
4994        if isinstance(unit, TimeUnit.VAR_LIKE):
4995            args["unit"] = Literal.string(
4996                (TimeUnit.UNABBREVIATED_UNIT_NAME.get(unit.name) or unit.name).upper()
4997            )
4998        elif isinstance(unit, Week):
4999            unit.set("this", Literal.string(unit.this.name.upper()))
5000
5001        super().__init__(**args)
5002
5003    @property
5004    def unit(self) -> Expression:
5005        return self.args["unit"]
5006
5007
5008class DatetimeAdd(Func, IntervalOp):
5009    arg_types = {"this": True, "expression": True, "unit": False}
5010
5011
5012class DatetimeSub(Func, IntervalOp):
5013    arg_types = {"this": True, "expression": True, "unit": False}
5014
5015
5016class DatetimeDiff(Func, TimeUnit):
5017    arg_types = {"this": True, "expression": True, "unit": False}
5018
5019
5020class DatetimeTrunc(Func, TimeUnit):
5021    arg_types = {"this": True, "unit": True, "zone": False}
5022
5023
5024class DayOfWeek(Func):
5025    _sql_names = ["DAY_OF_WEEK", "DAYOFWEEK"]
5026
5027
5028class DayOfMonth(Func):
5029    _sql_names = ["DAY_OF_MONTH", "DAYOFMONTH"]
5030
5031
5032class DayOfYear(Func):
5033    _sql_names = ["DAY_OF_YEAR", "DAYOFYEAR"]
5034
5035
5036class ToDays(Func):
5037    pass
5038
5039
5040class WeekOfYear(Func):
5041    _sql_names = ["WEEK_OF_YEAR", "WEEKOFYEAR"]
5042
5043
5044class MonthsBetween(Func):
5045    arg_types = {"this": True, "expression": True, "roundoff": False}
5046
5047
5048class LastDay(Func, TimeUnit):
5049    _sql_names = ["LAST_DAY", "LAST_DAY_OF_MONTH"]
5050    arg_types = {"this": True, "unit": False}
5051
5052
5053class Extract(Func):
5054    arg_types = {"this": True, "expression": True}
5055
5056
5057class Timestamp(Func):
5058    arg_types = {"this": False, "expression": False, "with_tz": False}
5059
5060
5061class TimestampAdd(Func, TimeUnit):
5062    arg_types = {"this": True, "expression": True, "unit": False}
5063
5064
5065class TimestampSub(Func, TimeUnit):
5066    arg_types = {"this": True, "expression": True, "unit": False}
5067
5068
5069class TimestampDiff(Func, TimeUnit):
5070    _sql_names = ["TIMESTAMPDIFF", "TIMESTAMP_DIFF"]
5071    arg_types = {"this": True, "expression": True, "unit": False}
5072
5073
5074class TimestampTrunc(Func, TimeUnit):
5075    arg_types = {"this": True, "unit": True, "zone": False}
5076
5077
5078class TimeAdd(Func, TimeUnit):
5079    arg_types = {"this": True, "expression": True, "unit": False}
5080
5081
5082class TimeSub(Func, TimeUnit):
5083    arg_types = {"this": True, "expression": True, "unit": False}
5084
5085
5086class TimeDiff(Func, TimeUnit):
5087    arg_types = {"this": True, "expression": True, "unit": False}
5088
5089
5090class TimeTrunc(Func, TimeUnit):
5091    arg_types = {"this": True, "unit": True, "zone": False}
5092
5093
5094class DateFromParts(Func):
5095    _sql_names = ["DATE_FROM_PARTS", "DATEFROMPARTS"]
5096    arg_types = {"year": True, "month": True, "day": True}
5097
5098
5099class TimeFromParts(Func):
5100    _sql_names = ["TIME_FROM_PARTS", "TIMEFROMPARTS"]
5101    arg_types = {
5102        "hour": True,
5103        "min": True,
5104        "sec": True,
5105        "nano": False,
5106        "fractions": False,
5107        "precision": False,
5108    }
5109
5110
5111class DateStrToDate(Func):
5112    pass
5113
5114
5115class DateToDateStr(Func):
5116    pass
5117
5118
5119class DateToDi(Func):
5120    pass
5121
5122
5123# https://cloud.google.com/bigquery/docs/reference/standard-sql/date_functions#date
5124class Date(Func):
5125    arg_types = {"this": False, "zone": False, "expressions": False}
5126    is_var_len_args = True
5127
5128
5129class Day(Func):
5130    pass
5131
5132
5133class Decode(Func):
5134    arg_types = {"this": True, "charset": True, "replace": False}
5135
5136
5137class DiToDate(Func):
5138    pass
5139
5140
5141class Encode(Func):
5142    arg_types = {"this": True, "charset": True}
5143
5144
5145class Exp(Func):
5146    pass
5147
5148
5149# https://docs.snowflake.com/en/sql-reference/functions/flatten
5150class Explode(Func):
5151    arg_types = {"this": True, "expressions": False}
5152    is_var_len_args = True
5153
5154
5155class ExplodeOuter(Explode):
5156    pass
5157
5158
5159class Posexplode(Explode):
5160    pass
5161
5162
5163class PosexplodeOuter(Posexplode, ExplodeOuter):
5164    pass
5165
5166
5167class Floor(Func):
5168    arg_types = {"this": True, "decimals": False}
5169
5170
5171class FromBase64(Func):
5172    pass
5173
5174
5175class ToBase64(Func):
5176    pass
5177
5178
5179class GenerateDateArray(Func):
5180    arg_types = {"start": True, "end": True, "interval": False}
5181
5182
5183class Greatest(Func):
5184    arg_types = {"this": True, "expressions": False}
5185    is_var_len_args = True
5186
5187
5188class GroupConcat(AggFunc):
5189    arg_types = {"this": True, "separator": False}
5190
5191
5192class Hex(Func):
5193    pass
5194
5195
5196class Xor(Connector, Func):
5197    arg_types = {"this": False, "expression": False, "expressions": False}
5198
5199
5200class If(Func):
5201    arg_types = {"this": True, "true": True, "false": False}
5202    _sql_names = ["IF", "IIF"]
5203
5204
5205class Nullif(Func):
5206    arg_types = {"this": True, "expression": True}
5207
5208
5209class Initcap(Func):
5210    arg_types = {"this": True, "expression": False}
5211
5212
5213class IsNan(Func):
5214    _sql_names = ["IS_NAN", "ISNAN"]
5215
5216
5217class IsInf(Func):
5218    _sql_names = ["IS_INF", "ISINF"]
5219
5220
5221class JSONPath(Expression):
5222    arg_types = {"expressions": True}
5223
5224    @property
5225    def output_name(self) -> str:
5226        last_segment = self.expressions[-1].this
5227        return last_segment if isinstance(last_segment, str) else ""
5228
5229
5230class JSONPathPart(Expression):
5231    arg_types = {}
5232
5233
5234class JSONPathFilter(JSONPathPart):
5235    arg_types = {"this": True}
5236
5237
5238class JSONPathKey(JSONPathPart):
5239    arg_types = {"this": True}
5240
5241
5242class JSONPathRecursive(JSONPathPart):
5243    arg_types = {"this": False}
5244
5245
5246class JSONPathRoot(JSONPathPart):
5247    pass
5248
5249
5250class JSONPathScript(JSONPathPart):
5251    arg_types = {"this": True}
5252
5253
5254class JSONPathSlice(JSONPathPart):
5255    arg_types = {"start": False, "end": False, "step": False}
5256
5257
5258class JSONPathSelector(JSONPathPart):
5259    arg_types = {"this": True}
5260
5261
5262class JSONPathSubscript(JSONPathPart):
5263    arg_types = {"this": True}
5264
5265
5266class JSONPathUnion(JSONPathPart):
5267    arg_types = {"expressions": True}
5268
5269
5270class JSONPathWildcard(JSONPathPart):
5271    pass
5272
5273
5274class FormatJson(Expression):
5275    pass
5276
5277
5278class JSONKeyValue(Expression):
5279    arg_types = {"this": True, "expression": True}
5280
5281
5282class JSONObject(Func):
5283    arg_types = {
5284        "expressions": False,
5285        "null_handling": False,
5286        "unique_keys": False,
5287        "return_type": False,
5288        "encoding": False,
5289    }
5290
5291
5292class JSONObjectAgg(AggFunc):
5293    arg_types = {
5294        "expressions": False,
5295        "null_handling": False,
5296        "unique_keys": False,
5297        "return_type": False,
5298        "encoding": False,
5299    }
5300
5301
5302# https://docs.oracle.com/en/database/oracle/oracle-database/19/sqlrf/JSON_ARRAY.html
5303class JSONArray(Func):
5304    arg_types = {
5305        "expressions": True,
5306        "null_handling": False,
5307        "return_type": False,
5308        "strict": False,
5309    }
5310
5311
5312# https://docs.oracle.com/en/database/oracle/oracle-database/19/sqlrf/JSON_ARRAYAGG.html
5313class JSONArrayAgg(Func):
5314    arg_types = {
5315        "this": True,
5316        "order": False,
5317        "null_handling": False,
5318        "return_type": False,
5319        "strict": False,
5320    }
5321
5322
5323# https://docs.oracle.com/en/database/oracle/oracle-database/19/sqlrf/JSON_TABLE.html
5324# Note: parsing of JSON column definitions is currently incomplete.
5325class JSONColumnDef(Expression):
5326    arg_types = {"this": False, "kind": False, "path": False, "nested_schema": False}
5327
5328
5329class JSONSchema(Expression):
5330    arg_types = {"expressions": True}
5331
5332
5333# # https://docs.oracle.com/en/database/oracle/oracle-database/19/sqlrf/JSON_TABLE.html
5334class JSONTable(Func):
5335    arg_types = {
5336        "this": True,
5337        "schema": True,
5338        "path": False,
5339        "error_handling": False,
5340        "empty_handling": False,
5341    }
5342
5343
5344class OpenJSONColumnDef(Expression):
5345    arg_types = {"this": True, "kind": True, "path": False, "as_json": False}
5346
5347
5348class OpenJSON(Func):
5349    arg_types = {"this": True, "path": False, "expressions": False}
5350
5351
5352class JSONBContains(Binary):
5353    _sql_names = ["JSONB_CONTAINS"]
5354
5355
5356class JSONExtract(Binary, Func):
5357    arg_types = {"this": True, "expression": True, "only_json_types": False, "expressions": False}
5358    _sql_names = ["JSON_EXTRACT"]
5359    is_var_len_args = True
5360
5361    @property
5362    def output_name(self) -> str:
5363        return self.expression.output_name if not self.expressions else ""
5364
5365
5366class JSONExtractScalar(Binary, Func):
5367    arg_types = {"this": True, "expression": True, "only_json_types": False, "expressions": False}
5368    _sql_names = ["JSON_EXTRACT_SCALAR"]
5369    is_var_len_args = True
5370
5371    @property
5372    def output_name(self) -> str:
5373        return self.expression.output_name
5374
5375
5376class JSONBExtract(Binary, Func):
5377    _sql_names = ["JSONB_EXTRACT"]
5378
5379
5380class JSONBExtractScalar(Binary, Func):
5381    _sql_names = ["JSONB_EXTRACT_SCALAR"]
5382
5383
5384class JSONFormat(Func):
5385    arg_types = {"this": False, "options": False}
5386    _sql_names = ["JSON_FORMAT"]
5387
5388
5389# https://dev.mysql.com/doc/refman/8.0/en/json-search-functions.html#operator_member-of
5390class JSONArrayContains(Binary, Predicate, Func):
5391    _sql_names = ["JSON_ARRAY_CONTAINS"]
5392
5393
5394class ParseJSON(Func):
5395    # BigQuery, Snowflake have PARSE_JSON, Presto has JSON_PARSE
5396    _sql_names = ["PARSE_JSON", "JSON_PARSE"]
5397    arg_types = {"this": True, "expressions": False}
5398    is_var_len_args = True
5399
5400
5401class Least(Func):
5402    arg_types = {"this": True, "expressions": False}
5403    is_var_len_args = True
5404
5405
5406class Left(Func):
5407    arg_types = {"this": True, "expression": True}
5408
5409
5410class Right(Func):
5411    arg_types = {"this": True, "expression": True}
5412
5413
5414class Length(Func):
5415    _sql_names = ["LENGTH", "LEN"]
5416
5417
5418class Levenshtein(Func):
5419    arg_types = {
5420        "this": True,
5421        "expression": False,
5422        "ins_cost": False,
5423        "del_cost": False,
5424        "sub_cost": False,
5425    }
5426
5427
5428class Ln(Func):
5429    pass
5430
5431
5432class Log(Func):
5433    arg_types = {"this": True, "expression": False}
5434
5435
5436class LogicalOr(AggFunc):
5437    _sql_names = ["LOGICAL_OR", "BOOL_OR", "BOOLOR_AGG"]
5438
5439
5440class LogicalAnd(AggFunc):
5441    _sql_names = ["LOGICAL_AND", "BOOL_AND", "BOOLAND_AGG"]
5442
5443
5444class Lower(Func):
5445    _sql_names = ["LOWER", "LCASE"]
5446
5447
5448class Map(Func):
5449    arg_types = {"keys": False, "values": False}
5450
5451    @property
5452    def keys(self) -> t.List[Expression]:
5453        keys = self.args.get("keys")
5454        return keys.expressions if keys else []
5455
5456    @property
5457    def values(self) -> t.List[Expression]:
5458        values = self.args.get("values")
5459        return values.expressions if values else []
5460
5461
5462# Represents the MAP {...} syntax in DuckDB - basically convert a struct to a MAP
5463class ToMap(Func):
5464    pass
5465
5466
5467class MapFromEntries(Func):
5468    pass
5469
5470
5471class StarMap(Func):
5472    pass
5473
5474
5475class VarMap(Func):
5476    arg_types = {"keys": True, "values": True}
5477    is_var_len_args = True
5478
5479    @property
5480    def keys(self) -> t.List[Expression]:
5481        return self.args["keys"].expressions
5482
5483    @property
5484    def values(self) -> t.List[Expression]:
5485        return self.args["values"].expressions
5486
5487
5488# https://dev.mysql.com/doc/refman/8.0/en/fulltext-search.html
5489class MatchAgainst(Func):
5490    arg_types = {"this": True, "expressions": True, "modifier": False}
5491
5492
5493class Max(AggFunc):
5494    arg_types = {"this": True, "expressions": False}
5495    is_var_len_args = True
5496
5497
5498class MD5(Func):
5499    _sql_names = ["MD5"]
5500
5501
5502# Represents the variant of the MD5 function that returns a binary value
5503class MD5Digest(Func):
5504    _sql_names = ["MD5_DIGEST"]
5505
5506
5507class Min(AggFunc):
5508    arg_types = {"this": True, "expressions": False}
5509    is_var_len_args = True
5510
5511
5512class Month(Func):
5513    pass
5514
5515
5516class AddMonths(Func):
5517    arg_types = {"this": True, "expression": True}
5518
5519
5520class Nvl2(Func):
5521    arg_types = {"this": True, "true": True, "false": False}
5522
5523
5524# https://cloud.google.com/bigquery/docs/reference/standard-sql/bigqueryml-syntax-predict#mlpredict_function
5525class Predict(Func):
5526    arg_types = {"this": True, "expression": True, "params_struct": False}
5527
5528
5529class Pow(Binary, Func):
5530    _sql_names = ["POWER", "POW"]
5531
5532
5533class PercentileCont(AggFunc):
5534    arg_types = {"this": True, "expression": False}
5535
5536
5537class PercentileDisc(AggFunc):
5538    arg_types = {"this": True, "expression": False}
5539
5540
5541class Quantile(AggFunc):
5542    arg_types = {"this": True, "quantile": True}
5543
5544
5545class ApproxQuantile(Quantile):
5546    arg_types = {"this": True, "quantile": True, "accuracy": False, "weight": False}
5547
5548
5549class Quarter(Func):
5550    pass
5551
5552
5553class Rand(Func):
5554    _sql_names = ["RAND", "RANDOM"]
5555    arg_types = {"this": False}
5556
5557
5558class Randn(Func):
5559    arg_types = {"this": False}
5560
5561
5562class RangeN(Func):
5563    arg_types = {"this": True, "expressions": True, "each": False}
5564
5565
5566class ReadCSV(Func):
5567    _sql_names = ["READ_CSV"]
5568    is_var_len_args = True
5569    arg_types = {"this": True, "expressions": False}
5570
5571
5572class Reduce(Func):
5573    arg_types = {"this": True, "initial": True, "merge": True, "finish": False}
5574
5575
5576class RegexpExtract(Func):
5577    arg_types = {
5578        "this": True,
5579        "expression": True,
5580        "position": False,
5581        "occurrence": False,
5582        "parameters": False,
5583        "group": False,
5584    }
5585
5586
5587class RegexpReplace(Func):
5588    arg_types = {
5589        "this": True,
5590        "expression": True,
5591        "replacement": False,
5592        "position": False,
5593        "occurrence": False,
5594        "modifiers": False,
5595    }
5596
5597
5598class RegexpLike(Binary, Func):
5599    arg_types = {"this": True, "expression": True, "flag": False}
5600
5601
5602class RegexpILike(Binary, Func):
5603    arg_types = {"this": True, "expression": True, "flag": False}
5604
5605
5606# https://spark.apache.org/docs/latest/api/python/reference/pyspark.sql/api/pyspark.sql.functions.split.html
5607# limit is the number of times a pattern is applied
5608class RegexpSplit(Func):
5609    arg_types = {"this": True, "expression": True, "limit": False}
5610
5611
5612class Repeat(Func):
5613    arg_types = {"this": True, "times": True}
5614
5615
5616# https://learn.microsoft.com/en-us/sql/t-sql/functions/round-transact-sql?view=sql-server-ver16
5617# tsql third argument function == trunctaion if not 0
5618class Round(Func):
5619    arg_types = {"this": True, "decimals": False, "truncate": False}
5620
5621
5622class RowNumber(Func):
5623    arg_types: t.Dict[str, t.Any] = {}
5624
5625
5626class SafeDivide(Func):
5627    arg_types = {"this": True, "expression": True}
5628
5629
5630class SHA(Func):
5631    _sql_names = ["SHA", "SHA1"]
5632
5633
5634class SHA2(Func):
5635    _sql_names = ["SHA2"]
5636    arg_types = {"this": True, "length": False}
5637
5638
5639class Sign(Func):
5640    _sql_names = ["SIGN", "SIGNUM"]
5641
5642
5643class SortArray(Func):
5644    arg_types = {"this": True, "asc": False}
5645
5646
5647class Split(Func):
5648    arg_types = {"this": True, "expression": True, "limit": False}
5649
5650
5651# Start may be omitted in the case of postgres
5652# https://www.postgresql.org/docs/9.1/functions-string.html @ Table 9-6
5653class Substring(Func):
5654    arg_types = {"this": True, "start": False, "length": False}
5655
5656
5657class StandardHash(Func):
5658    arg_types = {"this": True, "expression": False}
5659
5660
5661class StartsWith(Func):
5662    _sql_names = ["STARTS_WITH", "STARTSWITH"]
5663    arg_types = {"this": True, "expression": True}
5664
5665
5666class StrPosition(Func):
5667    arg_types = {
5668        "this": True,
5669        "substr": True,
5670        "position": False,
5671        "instance": False,
5672    }
5673
5674
5675class StrToDate(Func):
5676    arg_types = {"this": True, "format": True}
5677
5678
5679class StrToTime(Func):
5680    arg_types = {"this": True, "format": True, "zone": False}
5681
5682
5683# Spark allows unix_timestamp()
5684# https://spark.apache.org/docs/3.1.3/api/python/reference/api/pyspark.sql.functions.unix_timestamp.html
5685class StrToUnix(Func):
5686    arg_types = {"this": False, "format": False}
5687
5688
5689# https://prestodb.io/docs/current/functions/string.html
5690# https://spark.apache.org/docs/latest/api/sql/index.html#str_to_map
5691class StrToMap(Func):
5692    arg_types = {
5693        "this": True,
5694        "pair_delim": False,
5695        "key_value_delim": False,
5696        "duplicate_resolution_callback": False,
5697    }
5698
5699
5700class NumberToStr(Func):
5701    arg_types = {"this": True, "format": True, "culture": False}
5702
5703
5704class FromBase(Func):
5705    arg_types = {"this": True, "expression": True}
5706
5707
5708class Struct(Func):
5709    arg_types = {"expressions": False}
5710    is_var_len_args = True
5711
5712
5713class StructExtract(Func):
5714    arg_types = {"this": True, "expression": True}
5715
5716
5717# https://learn.microsoft.com/en-us/sql/t-sql/functions/stuff-transact-sql?view=sql-server-ver16
5718# https://docs.snowflake.com/en/sql-reference/functions/insert
5719class Stuff(Func):
5720    _sql_names = ["STUFF", "INSERT"]
5721    arg_types = {"this": True, "start": True, "length": True, "expression": True}
5722
5723
5724class Sum(AggFunc):
5725    pass
5726
5727
5728class Sqrt(Func):
5729    pass
5730
5731
5732class Stddev(AggFunc):
5733    pass
5734
5735
5736class StddevPop(AggFunc):
5737    pass
5738
5739
5740class StddevSamp(AggFunc):
5741    pass
5742
5743
5744class TimeToStr(Func):
5745    arg_types = {"this": True, "format": True, "culture": False, "timezone": False}
5746
5747
5748class TimeToTimeStr(Func):
5749    pass
5750
5751
5752class TimeToUnix(Func):
5753    pass
5754
5755
5756class TimeStrToDate(Func):
5757    pass
5758
5759
5760class TimeStrToTime(Func):
5761    pass
5762
5763
5764class TimeStrToUnix(Func):
5765    pass
5766
5767
5768class Trim(Func):
5769    arg_types = {
5770        "this": True,
5771        "expression": False,
5772        "position": False,
5773        "collation": False,
5774    }
5775
5776
5777class TsOrDsAdd(Func, TimeUnit):
5778    # return_type is used to correctly cast the arguments of this expression when transpiling it
5779    arg_types = {"this": True, "expression": True, "unit": False, "return_type": False}
5780
5781    @property
5782    def return_type(self) -> DataType:
5783        return DataType.build(self.args.get("return_type") or DataType.Type.DATE)
5784
5785
5786class TsOrDsDiff(Func, TimeUnit):
5787    arg_types = {"this": True, "expression": True, "unit": False}
5788
5789
5790class TsOrDsToDateStr(Func):
5791    pass
5792
5793
5794class TsOrDsToDate(Func):
5795    arg_types = {"this": True, "format": False, "safe": False}
5796
5797
5798class TsOrDsToTime(Func):
5799    pass
5800
5801
5802class TsOrDsToTimestamp(Func):
5803    pass
5804
5805
5806class TsOrDiToDi(Func):
5807    pass
5808
5809
5810class Unhex(Func):
5811    pass
5812
5813
5814# https://cloud.google.com/bigquery/docs/reference/standard-sql/date_functions#unix_date
5815class UnixDate(Func):
5816    pass
5817
5818
5819class UnixToStr(Func):
5820    arg_types = {"this": True, "format": False}
5821
5822
5823# https://prestodb.io/docs/current/functions/datetime.html
5824# presto has weird zone/hours/minutes
5825class UnixToTime(Func):
5826    arg_types = {
5827        "this": True,
5828        "scale": False,
5829        "zone": False,
5830        "hours": False,
5831        "minutes": False,
5832        "format": False,
5833    }
5834
5835    SECONDS = Literal.number(0)
5836    DECIS = Literal.number(1)
5837    CENTIS = Literal.number(2)
5838    MILLIS = Literal.number(3)
5839    DECIMILLIS = Literal.number(4)
5840    CENTIMILLIS = Literal.number(5)
5841    MICROS = Literal.number(6)
5842    DECIMICROS = Literal.number(7)
5843    CENTIMICROS = Literal.number(8)
5844    NANOS = Literal.number(9)
5845
5846
5847class UnixToTimeStr(Func):
5848    pass
5849
5850
5851class TimestampFromParts(Func):
5852    _sql_names = ["TIMESTAMP_FROM_PARTS", "TIMESTAMPFROMPARTS"]
5853    arg_types = {
5854        "year": True,
5855        "month": True,
5856        "day": True,
5857        "hour": True,
5858        "min": True,
5859        "sec": True,
5860        "nano": False,
5861        "zone": False,
5862        "milli": False,
5863    }
5864
5865
5866class Upper(Func):
5867    _sql_names = ["UPPER", "UCASE"]
5868
5869
5870class Corr(Binary, AggFunc):
5871    pass
5872
5873
5874class Variance(AggFunc):
5875    _sql_names = ["VARIANCE", "VARIANCE_SAMP", "VAR_SAMP"]
5876
5877
5878class VariancePop(AggFunc):
5879    _sql_names = ["VARIANCE_POP", "VAR_POP"]
5880
5881
5882class CovarSamp(Binary, AggFunc):
5883    pass
5884
5885
5886class CovarPop(Binary, AggFunc):
5887    pass
5888
5889
5890class Week(Func):
5891    arg_types = {"this": True, "mode": False}
5892
5893
5894class XMLTable(Func):
5895    arg_types = {"this": True, "passing": False, "columns": False, "by_ref": False}
5896
5897
5898class Year(Func):
5899    pass
5900
5901
5902class Use(Expression):
5903    arg_types = {"this": True, "kind": False}
5904
5905
5906class Merge(Expression):
5907    arg_types = {
5908        "this": True,
5909        "using": True,
5910        "on": True,
5911        "expressions": True,
5912        "with": False,
5913    }
5914
5915
5916class When(Func):
5917    arg_types = {"matched": True, "source": False, "condition": False, "then": True}
5918
5919
5920# https://docs.oracle.com/javadb/10.8.3.0/ref/rrefsqljnextvaluefor.html
5921# https://learn.microsoft.com/en-us/sql/t-sql/functions/next-value-for-transact-sql?view=sql-server-ver16
5922class NextValueFor(Func):
5923    arg_types = {"this": True, "order": False}
5924
5925
5926# Refers to a trailing semi-colon. This is only used to preserve trailing comments
5927# select 1; -- my comment
5928class Semicolon(Expression):
5929    arg_types = {}
5930
5931
5932def _norm_arg(arg):
5933    return arg.lower() if type(arg) is str else arg
5934
5935
5936ALL_FUNCTIONS = subclasses(__name__, Func, (AggFunc, Anonymous, Func))
5937FUNCTION_BY_NAME = {name: func for func in ALL_FUNCTIONS for name in func.sql_names()}
5938
5939JSON_PATH_PARTS = subclasses(__name__, JSONPathPart, (JSONPathPart,))
5940
5941PERCENTILES = (PercentileCont, PercentileDisc)
5942
5943
5944# Helpers
5945@t.overload
5946def maybe_parse(
5947    sql_or_expression: ExpOrStr,
5948    *,
5949    into: t.Type[E],
5950    dialect: DialectType = None,
5951    prefix: t.Optional[str] = None,
5952    copy: bool = False,
5953    **opts,
5954) -> E: ...
5955
5956
5957@t.overload
5958def maybe_parse(
5959    sql_or_expression: str | E,
5960    *,
5961    into: t.Optional[IntoType] = None,
5962    dialect: DialectType = None,
5963    prefix: t.Optional[str] = None,
5964    copy: bool = False,
5965    **opts,
5966) -> E: ...
5967
5968
5969def maybe_parse(
5970    sql_or_expression: ExpOrStr,
5971    *,
5972    into: t.Optional[IntoType] = None,
5973    dialect: DialectType = None,
5974    prefix: t.Optional[str] = None,
5975    copy: bool = False,
5976    **opts,
5977) -> Expression:
5978    """Gracefully handle a possible string or expression.
5979
5980    Example:
5981        >>> maybe_parse("1")
5982        Literal(this=1, is_string=False)
5983        >>> maybe_parse(to_identifier("x"))
5984        Identifier(this=x, quoted=False)
5985
5986    Args:
5987        sql_or_expression: the SQL code string or an expression
5988        into: the SQLGlot Expression to parse into
5989        dialect: the dialect used to parse the input expressions (in the case that an
5990            input expression is a SQL string).
5991        prefix: a string to prefix the sql with before it gets parsed
5992            (automatically includes a space)
5993        copy: whether to copy the expression.
5994        **opts: other options to use to parse the input expressions (again, in the case
5995            that an input expression is a SQL string).
5996
5997    Returns:
5998        Expression: the parsed or given expression.
5999    """
6000    if isinstance(sql_or_expression, Expression):
6001        if copy:
6002            return sql_or_expression.copy()
6003        return sql_or_expression
6004
6005    if sql_or_expression is None:
6006        raise ParseError("SQL cannot be None")
6007
6008    import sqlglot
6009
6010    sql = str(sql_or_expression)
6011    if prefix:
6012        sql = f"{prefix} {sql}"
6013
6014    return sqlglot.parse_one(sql, read=dialect, into=into, **opts)
6015
6016
6017@t.overload
6018def maybe_copy(instance: None, copy: bool = True) -> None: ...
6019
6020
6021@t.overload
6022def maybe_copy(instance: E, copy: bool = True) -> E: ...
6023
6024
6025def maybe_copy(instance, copy=True):
6026    return instance.copy() if copy and instance else instance
6027
6028
6029def _to_s(node: t.Any, verbose: bool = False, level: int = 0) -> str:
6030    """Generate a textual representation of an Expression tree"""
6031    indent = "\n" + ("  " * (level + 1))
6032    delim = f",{indent}"
6033
6034    if isinstance(node, Expression):
6035        args = {k: v for k, v in node.args.items() if (v is not None and v != []) or verbose}
6036
6037        if (node.type or verbose) and not isinstance(node, DataType):
6038            args["_type"] = node.type
6039        if node.comments or verbose:
6040            args["_comments"] = node.comments
6041
6042        if verbose:
6043            args["_id"] = id(node)
6044
6045        # Inline leaves for a more compact representation
6046        if node.is_leaf():
6047            indent = ""
6048            delim = ", "
6049
6050        items = delim.join([f"{k}={_to_s(v, verbose, level + 1)}" for k, v in args.items()])
6051        return f"{node.__class__.__name__}({indent}{items})"
6052
6053    if isinstance(node, list):
6054        items = delim.join(_to_s(i, verbose, level + 1) for i in node)
6055        items = f"{indent}{items}" if items else ""
6056        return f"[{items}]"
6057
6058    # Indent multiline strings to match the current level
6059    return indent.join(textwrap.dedent(str(node).strip("\n")).splitlines())
6060
6061
6062def _is_wrong_expression(expression, into):
6063    return isinstance(expression, Expression) and not isinstance(expression, into)
6064
6065
6066def _apply_builder(
6067    expression,
6068    instance,
6069    arg,
6070    copy=True,
6071    prefix=None,
6072    into=None,
6073    dialect=None,
6074    into_arg="this",
6075    **opts,
6076):
6077    if _is_wrong_expression(expression, into):
6078        expression = into(**{into_arg: expression})
6079    instance = maybe_copy(instance, copy)
6080    expression = maybe_parse(
6081        sql_or_expression=expression,
6082        prefix=prefix,
6083        into=into,
6084        dialect=dialect,
6085        **opts,
6086    )
6087    instance.set(arg, expression)
6088    return instance
6089
6090
6091def _apply_child_list_builder(
6092    *expressions,
6093    instance,
6094    arg,
6095    append=True,
6096    copy=True,
6097    prefix=None,
6098    into=None,
6099    dialect=None,
6100    properties=None,
6101    **opts,
6102):
6103    instance = maybe_copy(instance, copy)
6104    parsed = []
6105    for expression in expressions:
6106        if expression is not None:
6107            if _is_wrong_expression(expression, into):
6108                expression = into(expressions=[expression])
6109
6110            expression = maybe_parse(
6111                expression,
6112                into=into,
6113                dialect=dialect,
6114                prefix=prefix,
6115                **opts,
6116            )
6117            parsed.extend(expression.expressions)
6118
6119    existing = instance.args.get(arg)
6120    if append and existing:
6121        parsed = existing.expressions + parsed
6122
6123    child = into(expressions=parsed)
6124    for k, v in (properties or {}).items():
6125        child.set(k, v)
6126    instance.set(arg, child)
6127
6128    return instance
6129
6130
6131def _apply_list_builder(
6132    *expressions,
6133    instance,
6134    arg,
6135    append=True,
6136    copy=True,
6137    prefix=None,
6138    into=None,
6139    dialect=None,
6140    **opts,
6141):
6142    inst = maybe_copy(instance, copy)
6143
6144    expressions = [
6145        maybe_parse(
6146            sql_or_expression=expression,
6147            into=into,
6148            prefix=prefix,
6149            dialect=dialect,
6150            **opts,
6151        )
6152        for expression in expressions
6153        if expression is not None
6154    ]
6155
6156    existing_expressions = inst.args.get(arg)
6157    if append and existing_expressions:
6158        expressions = existing_expressions + expressions
6159
6160    inst.set(arg, expressions)
6161    return inst
6162
6163
6164def _apply_conjunction_builder(
6165    *expressions,
6166    instance,
6167    arg,
6168    into=None,
6169    append=True,
6170    copy=True,
6171    dialect=None,
6172    **opts,
6173):
6174    expressions = [exp for exp in expressions if exp is not None and exp != ""]
6175    if not expressions:
6176        return instance
6177
6178    inst = maybe_copy(instance, copy)
6179
6180    existing = inst.args.get(arg)
6181    if append and existing is not None:
6182        expressions = [existing.this if into else existing] + list(expressions)
6183
6184    node = and_(*expressions, dialect=dialect, copy=copy, **opts)
6185
6186    inst.set(arg, into(this=node) if into else node)
6187    return inst
6188
6189
6190def _apply_cte_builder(
6191    instance: E,
6192    alias: ExpOrStr,
6193    as_: ExpOrStr,
6194    recursive: t.Optional[bool] = None,
6195    append: bool = True,
6196    dialect: DialectType = None,
6197    copy: bool = True,
6198    **opts,
6199) -> E:
6200    alias_expression = maybe_parse(alias, dialect=dialect, into=TableAlias, **opts)
6201    as_expression = maybe_parse(as_, dialect=dialect, **opts)
6202    cte = CTE(this=as_expression, alias=alias_expression)
6203    return _apply_child_list_builder(
6204        cte,
6205        instance=instance,
6206        arg="with",
6207        append=append,
6208        copy=copy,
6209        into=With,
6210        properties={"recursive": recursive or False},
6211    )
6212
6213
6214def _combine(
6215    expressions: t.Sequence[t.Optional[ExpOrStr]],
6216    operator: t.Type[Connector],
6217    dialect: DialectType = None,
6218    copy: bool = True,
6219    **opts,
6220) -> Expression:
6221    conditions = [
6222        condition(expression, dialect=dialect, copy=copy, **opts)
6223        for expression in expressions
6224        if expression is not None
6225    ]
6226
6227    this, *rest = conditions
6228    if rest:
6229        this = _wrap(this, Connector)
6230    for expression in rest:
6231        this = operator(this=this, expression=_wrap(expression, Connector))
6232
6233    return this
6234
6235
6236def _wrap(expression: E, kind: t.Type[Expression]) -> E | Paren:
6237    return Paren(this=expression) if isinstance(expression, kind) else expression
6238
6239
6240def union(
6241    left: ExpOrStr,
6242    right: ExpOrStr,
6243    distinct: bool = True,
6244    dialect: DialectType = None,
6245    copy: bool = True,
6246    **opts,
6247) -> Union:
6248    """
6249    Initializes a syntax tree from one UNION expression.
6250
6251    Example:
6252        >>> union("SELECT * FROM foo", "SELECT * FROM bla").sql()
6253        'SELECT * FROM foo UNION SELECT * FROM bla'
6254
6255    Args:
6256        left: the SQL code string corresponding to the left-hand side.
6257            If an `Expression` instance is passed, it will be used as-is.
6258        right: the SQL code string corresponding to the right-hand side.
6259            If an `Expression` instance is passed, it will be used as-is.
6260        distinct: set the DISTINCT flag if and only if this is true.
6261        dialect: the dialect used to parse the input expression.
6262        copy: whether to copy the expression.
6263        opts: other options to use to parse the input expressions.
6264
6265    Returns:
6266        The new Union instance.
6267    """
6268    left = maybe_parse(sql_or_expression=left, dialect=dialect, copy=copy, **opts)
6269    right = maybe_parse(sql_or_expression=right, dialect=dialect, copy=copy, **opts)
6270
6271    return Union(this=left, expression=right, distinct=distinct)
6272
6273
6274def intersect(
6275    left: ExpOrStr,
6276    right: ExpOrStr,
6277    distinct: bool = True,
6278    dialect: DialectType = None,
6279    copy: bool = True,
6280    **opts,
6281) -> Intersect:
6282    """
6283    Initializes a syntax tree from one INTERSECT expression.
6284
6285    Example:
6286        >>> intersect("SELECT * FROM foo", "SELECT * FROM bla").sql()
6287        'SELECT * FROM foo INTERSECT SELECT * FROM bla'
6288
6289    Args:
6290        left: the SQL code string corresponding to the left-hand side.
6291            If an `Expression` instance is passed, it will be used as-is.
6292        right: the SQL code string corresponding to the right-hand side.
6293            If an `Expression` instance is passed, it will be used as-is.
6294        distinct: set the DISTINCT flag if and only if this is true.
6295        dialect: the dialect used to parse the input expression.
6296        copy: whether to copy the expression.
6297        opts: other options to use to parse the input expressions.
6298
6299    Returns:
6300        The new Intersect instance.
6301    """
6302    left = maybe_parse(sql_or_expression=left, dialect=dialect, copy=copy, **opts)
6303    right = maybe_parse(sql_or_expression=right, dialect=dialect, copy=copy, **opts)
6304
6305    return Intersect(this=left, expression=right, distinct=distinct)
6306
6307
6308def except_(
6309    left: ExpOrStr,
6310    right: ExpOrStr,
6311    distinct: bool = True,
6312    dialect: DialectType = None,
6313    copy: bool = True,
6314    **opts,
6315) -> Except:
6316    """
6317    Initializes a syntax tree from one EXCEPT expression.
6318
6319    Example:
6320        >>> except_("SELECT * FROM foo", "SELECT * FROM bla").sql()
6321        'SELECT * FROM foo EXCEPT SELECT * FROM bla'
6322
6323    Args:
6324        left: the SQL code string corresponding to the left-hand side.
6325            If an `Expression` instance is passed, it will be used as-is.
6326        right: the SQL code string corresponding to the right-hand side.
6327            If an `Expression` instance is passed, it will be used as-is.
6328        distinct: set the DISTINCT flag if and only if this is true.
6329        dialect: the dialect used to parse the input expression.
6330        copy: whether to copy the expression.
6331        opts: other options to use to parse the input expressions.
6332
6333    Returns:
6334        The new Except instance.
6335    """
6336    left = maybe_parse(sql_or_expression=left, dialect=dialect, copy=copy, **opts)
6337    right = maybe_parse(sql_or_expression=right, dialect=dialect, copy=copy, **opts)
6338
6339    return Except(this=left, expression=right, distinct=distinct)
6340
6341
6342def select(*expressions: ExpOrStr, dialect: DialectType = None, **opts) -> Select:
6343    """
6344    Initializes a syntax tree from one or multiple SELECT expressions.
6345
6346    Example:
6347        >>> select("col1", "col2").from_("tbl").sql()
6348        'SELECT col1, col2 FROM tbl'
6349
6350    Args:
6351        *expressions: the SQL code string to parse as the expressions of a
6352            SELECT statement. If an Expression instance is passed, this is used as-is.
6353        dialect: the dialect used to parse the input expressions (in the case that an
6354            input expression is a SQL string).
6355        **opts: other options to use to parse the input expressions (again, in the case
6356            that an input expression is a SQL string).
6357
6358    Returns:
6359        Select: the syntax tree for the SELECT statement.
6360    """
6361    return Select().select(*expressions, dialect=dialect, **opts)
6362
6363
6364def from_(expression: ExpOrStr, dialect: DialectType = None, **opts) -> Select:
6365    """
6366    Initializes a syntax tree from a FROM expression.
6367
6368    Example:
6369        >>> from_("tbl").select("col1", "col2").sql()
6370        'SELECT col1, col2 FROM tbl'
6371
6372    Args:
6373        *expression: the SQL code string to parse as the FROM expressions of a
6374            SELECT statement. If an Expression instance is passed, this is used as-is.
6375        dialect: the dialect used to parse the input expression (in the case that the
6376            input expression is a SQL string).
6377        **opts: other options to use to parse the input expressions (again, in the case
6378            that the input expression is a SQL string).
6379
6380    Returns:
6381        Select: the syntax tree for the SELECT statement.
6382    """
6383    return Select().from_(expression, dialect=dialect, **opts)
6384
6385
6386def update(
6387    table: str | Table,
6388    properties: dict,
6389    where: t.Optional[ExpOrStr] = None,
6390    from_: t.Optional[ExpOrStr] = None,
6391    dialect: DialectType = None,
6392    **opts,
6393) -> Update:
6394    """
6395    Creates an update statement.
6396
6397    Example:
6398        >>> update("my_table", {"x": 1, "y": "2", "z": None}, from_="baz", where="id > 1").sql()
6399        "UPDATE my_table SET x = 1, y = '2', z = NULL FROM baz WHERE id > 1"
6400
6401    Args:
6402        *properties: dictionary of properties to set which are
6403            auto converted to sql objects eg None -> NULL
6404        where: sql conditional parsed into a WHERE statement
6405        from_: sql statement parsed into a FROM statement
6406        dialect: the dialect used to parse the input expressions.
6407        **opts: other options to use to parse the input expressions.
6408
6409    Returns:
6410        Update: the syntax tree for the UPDATE statement.
6411    """
6412    update_expr = Update(this=maybe_parse(table, into=Table, dialect=dialect))
6413    update_expr.set(
6414        "expressions",
6415        [
6416            EQ(this=maybe_parse(k, dialect=dialect, **opts), expression=convert(v))
6417            for k, v in properties.items()
6418        ],
6419    )
6420    if from_:
6421        update_expr.set(
6422            "from",
6423            maybe_parse(from_, into=From, dialect=dialect, prefix="FROM", **opts),
6424        )
6425    if isinstance(where, Condition):
6426        where = Where(this=where)
6427    if where:
6428        update_expr.set(
6429            "where",
6430            maybe_parse(where, into=Where, dialect=dialect, prefix="WHERE", **opts),
6431        )
6432    return update_expr
6433
6434
6435def delete(
6436    table: ExpOrStr,
6437    where: t.Optional[ExpOrStr] = None,
6438    returning: t.Optional[ExpOrStr] = None,
6439    dialect: DialectType = None,
6440    **opts,
6441) -> Delete:
6442    """
6443    Builds a delete statement.
6444
6445    Example:
6446        >>> delete("my_table", where="id > 1").sql()
6447        'DELETE FROM my_table WHERE id > 1'
6448
6449    Args:
6450        where: sql conditional parsed into a WHERE statement
6451        returning: sql conditional parsed into a RETURNING statement
6452        dialect: the dialect used to parse the input expressions.
6453        **opts: other options to use to parse the input expressions.
6454
6455    Returns:
6456        Delete: the syntax tree for the DELETE statement.
6457    """
6458    delete_expr = Delete().delete(table, dialect=dialect, copy=False, **opts)
6459    if where:
6460        delete_expr = delete_expr.where(where, dialect=dialect, copy=False, **opts)
6461    if returning:
6462        delete_expr = t.cast(
6463            Delete, delete_expr.returning(returning, dialect=dialect, copy=False, **opts)
6464        )
6465    return delete_expr
6466
6467
6468def insert(
6469    expression: ExpOrStr,
6470    into: ExpOrStr,
6471    columns: t.Optional[t.Sequence[str | Identifier]] = None,
6472    overwrite: t.Optional[bool] = None,
6473    returning: t.Optional[ExpOrStr] = None,
6474    dialect: DialectType = None,
6475    copy: bool = True,
6476    **opts,
6477) -> Insert:
6478    """
6479    Builds an INSERT statement.
6480
6481    Example:
6482        >>> insert("VALUES (1, 2, 3)", "tbl").sql()
6483        'INSERT INTO tbl VALUES (1, 2, 3)'
6484
6485    Args:
6486        expression: the sql string or expression of the INSERT statement
6487        into: the tbl to insert data to.
6488        columns: optionally the table's column names.
6489        overwrite: whether to INSERT OVERWRITE or not.
6490        returning: sql conditional parsed into a RETURNING statement
6491        dialect: the dialect used to parse the input expressions.
6492        copy: whether to copy the expression.
6493        **opts: other options to use to parse the input expressions.
6494
6495    Returns:
6496        Insert: the syntax tree for the INSERT statement.
6497    """
6498    expr = maybe_parse(expression, dialect=dialect, copy=copy, **opts)
6499    this: Table | Schema = maybe_parse(into, into=Table, dialect=dialect, copy=copy, **opts)
6500
6501    if columns:
6502        this = Schema(this=this, expressions=[to_identifier(c, copy=copy) for c in columns])
6503
6504    insert = Insert(this=this, expression=expr, overwrite=overwrite)
6505
6506    if returning:
6507        insert = t.cast(Insert, insert.returning(returning, dialect=dialect, copy=False, **opts))
6508
6509    return insert
6510
6511
6512def condition(
6513    expression: ExpOrStr, dialect: DialectType = None, copy: bool = True, **opts
6514) -> Condition:
6515    """
6516    Initialize a logical condition expression.
6517
6518    Example:
6519        >>> condition("x=1").sql()
6520        'x = 1'
6521
6522        This is helpful for composing larger logical syntax trees:
6523        >>> where = condition("x=1")
6524        >>> where = where.and_("y=1")
6525        >>> Select().from_("tbl").select("*").where(where).sql()
6526        'SELECT * FROM tbl WHERE x = 1 AND y = 1'
6527
6528    Args:
6529        *expression: the SQL code string to parse.
6530            If an Expression instance is passed, this is used as-is.
6531        dialect: the dialect used to parse the input expression (in the case that the
6532            input expression is a SQL string).
6533        copy: Whether to copy `expression` (only applies to expressions).
6534        **opts: other options to use to parse the input expressions (again, in the case
6535            that the input expression is a SQL string).
6536
6537    Returns:
6538        The new Condition instance
6539    """
6540    return maybe_parse(
6541        expression,
6542        into=Condition,
6543        dialect=dialect,
6544        copy=copy,
6545        **opts,
6546    )
6547
6548
6549def and_(
6550    *expressions: t.Optional[ExpOrStr], dialect: DialectType = None, copy: bool = True, **opts
6551) -> Condition:
6552    """
6553    Combine multiple conditions with an AND logical operator.
6554
6555    Example:
6556        >>> and_("x=1", and_("y=1", "z=1")).sql()
6557        'x = 1 AND (y = 1 AND z = 1)'
6558
6559    Args:
6560        *expressions: the SQL code strings to parse.
6561            If an Expression instance is passed, this is used as-is.
6562        dialect: the dialect used to parse the input expression.
6563        copy: whether to copy `expressions` (only applies to Expressions).
6564        **opts: other options to use to parse the input expressions.
6565
6566    Returns:
6567        The new condition
6568    """
6569    return t.cast(Condition, _combine(expressions, And, dialect, copy=copy, **opts))
6570
6571
6572def or_(
6573    *expressions: t.Optional[ExpOrStr], dialect: DialectType = None, copy: bool = True, **opts
6574) -> Condition:
6575    """
6576    Combine multiple conditions with an OR logical operator.
6577
6578    Example:
6579        >>> or_("x=1", or_("y=1", "z=1")).sql()
6580        'x = 1 OR (y = 1 OR z = 1)'
6581
6582    Args:
6583        *expressions: the SQL code strings to parse.
6584            If an Expression instance is passed, this is used as-is.
6585        dialect: the dialect used to parse the input expression.
6586        copy: whether to copy `expressions` (only applies to Expressions).
6587        **opts: other options to use to parse the input expressions.
6588
6589    Returns:
6590        The new condition
6591    """
6592    return t.cast(Condition, _combine(expressions, Or, dialect, copy=copy, **opts))
6593
6594
6595def xor(
6596    *expressions: t.Optional[ExpOrStr], dialect: DialectType = None, copy: bool = True, **opts
6597) -> Condition:
6598    """
6599    Combine multiple conditions with an XOR logical operator.
6600
6601    Example:
6602        >>> xor("x=1", xor("y=1", "z=1")).sql()
6603        'x = 1 XOR (y = 1 XOR z = 1)'
6604
6605    Args:
6606        *expressions: the SQL code strings to parse.
6607            If an Expression instance is passed, this is used as-is.
6608        dialect: the dialect used to parse the input expression.
6609        copy: whether to copy `expressions` (only applies to Expressions).
6610        **opts: other options to use to parse the input expressions.
6611
6612    Returns:
6613        The new condition
6614    """
6615    return t.cast(Condition, _combine(expressions, Xor, dialect, copy=copy, **opts))
6616
6617
6618def not_(expression: ExpOrStr, dialect: DialectType = None, copy: bool = True, **opts) -> Not:
6619    """
6620    Wrap a condition with a NOT operator.
6621
6622    Example:
6623        >>> not_("this_suit='black'").sql()
6624        "NOT this_suit = 'black'"
6625
6626    Args:
6627        expression: the SQL code string to parse.
6628            If an Expression instance is passed, this is used as-is.
6629        dialect: the dialect used to parse the input expression.
6630        copy: whether to copy the expression or not.
6631        **opts: other options to use to parse the input expressions.
6632
6633    Returns:
6634        The new condition.
6635    """
6636    this = condition(
6637        expression,
6638        dialect=dialect,
6639        copy=copy,
6640        **opts,
6641    )
6642    return Not(this=_wrap(this, Connector))
6643
6644
6645def paren(expression: ExpOrStr, copy: bool = True) -> Paren:
6646    """
6647    Wrap an expression in parentheses.
6648
6649    Example:
6650        >>> paren("5 + 3").sql()
6651        '(5 + 3)'
6652
6653    Args:
6654        expression: the SQL code string to parse.
6655            If an Expression instance is passed, this is used as-is.
6656        copy: whether to copy the expression or not.
6657
6658    Returns:
6659        The wrapped expression.
6660    """
6661    return Paren(this=maybe_parse(expression, copy=copy))
6662
6663
6664SAFE_IDENTIFIER_RE: t.Pattern[str] = re.compile(r"^[_a-zA-Z][\w]*$")
6665
6666
6667@t.overload
6668def to_identifier(name: None, quoted: t.Optional[bool] = None, copy: bool = True) -> None: ...
6669
6670
6671@t.overload
6672def to_identifier(
6673    name: str | Identifier, quoted: t.Optional[bool] = None, copy: bool = True
6674) -> Identifier: ...
6675
6676
6677def to_identifier(name, quoted=None, copy=True):
6678    """Builds an identifier.
6679
6680    Args:
6681        name: The name to turn into an identifier.
6682        quoted: Whether to force quote the identifier.
6683        copy: Whether to copy name if it's an Identifier.
6684
6685    Returns:
6686        The identifier ast node.
6687    """
6688
6689    if name is None:
6690        return None
6691
6692    if isinstance(name, Identifier):
6693        identifier = maybe_copy(name, copy)
6694    elif isinstance(name, str):
6695        identifier = Identifier(
6696            this=name,
6697            quoted=not SAFE_IDENTIFIER_RE.match(name) if quoted is None else quoted,
6698        )
6699    else:
6700        raise ValueError(f"Name needs to be a string or an Identifier, got: {name.__class__}")
6701    return identifier
6702
6703
6704def parse_identifier(name: str | Identifier, dialect: DialectType = None) -> Identifier:
6705    """
6706    Parses a given string into an identifier.
6707
6708    Args:
6709        name: The name to parse into an identifier.
6710        dialect: The dialect to parse against.
6711
6712    Returns:
6713        The identifier ast node.
6714    """
6715    try:
6716        expression = maybe_parse(name, dialect=dialect, into=Identifier)
6717    except ParseError:
6718        expression = to_identifier(name)
6719
6720    return expression
6721
6722
6723INTERVAL_STRING_RE = re.compile(r"\s*([0-9]+)\s*([a-zA-Z]+)\s*")
6724
6725
6726def to_interval(interval: str | Literal) -> Interval:
6727    """Builds an interval expression from a string like '1 day' or '5 months'."""
6728    if isinstance(interval, Literal):
6729        if not interval.is_string:
6730            raise ValueError("Invalid interval string.")
6731
6732        interval = interval.this
6733
6734    interval_parts = INTERVAL_STRING_RE.match(interval)  # type: ignore
6735
6736    if not interval_parts:
6737        raise ValueError("Invalid interval string.")
6738
6739    return Interval(
6740        this=Literal.string(interval_parts.group(1)),
6741        unit=Var(this=interval_parts.group(2).upper()),
6742    )
6743
6744
6745def to_table(
6746    sql_path: str | Table, dialect: DialectType = None, copy: bool = True, **kwargs
6747) -> Table:
6748    """
6749    Create a table expression from a `[catalog].[schema].[table]` sql path. Catalog and schema are optional.
6750    If a table is passed in then that table is returned.
6751
6752    Args:
6753        sql_path: a `[catalog].[schema].[table]` string.
6754        dialect: the source dialect according to which the table name will be parsed.
6755        copy: Whether to copy a table if it is passed in.
6756        kwargs: the kwargs to instantiate the resulting `Table` expression with.
6757
6758    Returns:
6759        A table expression.
6760    """
6761    if isinstance(sql_path, Table):
6762        return maybe_copy(sql_path, copy=copy)
6763
6764    table = maybe_parse(sql_path, into=Table, dialect=dialect)
6765
6766    for k, v in kwargs.items():
6767        table.set(k, v)
6768
6769    return table
6770
6771
6772def to_column(
6773    sql_path: str | Column,
6774    quoted: t.Optional[bool] = None,
6775    dialect: DialectType = None,
6776    copy: bool = True,
6777    **kwargs,
6778) -> Column:
6779    """
6780    Create a column from a `[table].[column]` sql path. Table is optional.
6781    If a column is passed in then that column is returned.
6782
6783    Args:
6784        sql_path: a `[table].[column]` string.
6785        quoted: Whether or not to force quote identifiers.
6786        dialect: the source dialect according to which the column name will be parsed.
6787        copy: Whether to copy a column if it is passed in.
6788        kwargs: the kwargs to instantiate the resulting `Column` expression with.
6789
6790    Returns:
6791        A column expression.
6792    """
6793    if isinstance(sql_path, Column):
6794        return maybe_copy(sql_path, copy=copy)
6795
6796    try:
6797        col = maybe_parse(sql_path, into=Column, dialect=dialect)
6798    except ParseError:
6799        return column(*reversed(sql_path.split(".")), quoted=quoted, **kwargs)
6800
6801    for k, v in kwargs.items():
6802        col.set(k, v)
6803
6804    if quoted:
6805        for i in col.find_all(Identifier):
6806            i.set("quoted", True)
6807
6808    return col
6809
6810
6811def alias_(
6812    expression: ExpOrStr,
6813    alias: t.Optional[str | Identifier],
6814    table: bool | t.Sequence[str | Identifier] = False,
6815    quoted: t.Optional[bool] = None,
6816    dialect: DialectType = None,
6817    copy: bool = True,
6818    **opts,
6819):
6820    """Create an Alias expression.
6821
6822    Example:
6823        >>> alias_('foo', 'bar').sql()
6824        'foo AS bar'
6825
6826        >>> alias_('(select 1, 2)', 'bar', table=['a', 'b']).sql()
6827        '(SELECT 1, 2) AS bar(a, b)'
6828
6829    Args:
6830        expression: the SQL code strings to parse.
6831            If an Expression instance is passed, this is used as-is.
6832        alias: the alias name to use. If the name has
6833            special characters it is quoted.
6834        table: Whether to create a table alias, can also be a list of columns.
6835        quoted: whether to quote the alias
6836        dialect: the dialect used to parse the input expression.
6837        copy: Whether to copy the expression.
6838        **opts: other options to use to parse the input expressions.
6839
6840    Returns:
6841        Alias: the aliased expression
6842    """
6843    exp = maybe_parse(expression, dialect=dialect, copy=copy, **opts)
6844    alias = to_identifier(alias, quoted=quoted)
6845
6846    if table:
6847        table_alias = TableAlias(this=alias)
6848        exp.set("alias", table_alias)
6849
6850        if not isinstance(table, bool):
6851            for column in table:
6852                table_alias.append("columns", to_identifier(column, quoted=quoted))
6853
6854        return exp
6855
6856    # We don't set the "alias" arg for Window expressions, because that would add an IDENTIFIER node in
6857    # the AST, representing a "named_window" [1] construct (eg. bigquery). What we want is an ALIAS node
6858    # for the complete Window expression.
6859    #
6860    # [1]: https://cloud.google.com/bigquery/docs/reference/standard-sql/window-function-calls
6861
6862    if "alias" in exp.arg_types and not isinstance(exp, Window):
6863        exp.set("alias", alias)
6864        return exp
6865    return Alias(this=exp, alias=alias)
6866
6867
6868def subquery(
6869    expression: ExpOrStr,
6870    alias: t.Optional[Identifier | str] = None,
6871    dialect: DialectType = None,
6872    **opts,
6873) -> Select:
6874    """
6875    Build a subquery expression that's selected from.
6876
6877    Example:
6878        >>> subquery('select x from tbl', 'bar').select('x').sql()
6879        'SELECT x FROM (SELECT x FROM tbl) AS bar'
6880
6881    Args:
6882        expression: the SQL code strings to parse.
6883            If an Expression instance is passed, this is used as-is.
6884        alias: the alias name to use.
6885        dialect: the dialect used to parse the input expression.
6886        **opts: other options to use to parse the input expressions.
6887
6888    Returns:
6889        A new Select instance with the subquery expression included.
6890    """
6891
6892    expression = maybe_parse(expression, dialect=dialect, **opts).subquery(alias, **opts)
6893    return Select().from_(expression, dialect=dialect, **opts)
6894
6895
6896@t.overload
6897def column(
6898    col: str | Identifier,
6899    table: t.Optional[str | Identifier] = None,
6900    db: t.Optional[str | Identifier] = None,
6901    catalog: t.Optional[str | Identifier] = None,
6902    *,
6903    fields: t.Collection[t.Union[str, Identifier]],
6904    quoted: t.Optional[bool] = None,
6905    copy: bool = True,
6906) -> Dot:
6907    pass
6908
6909
6910@t.overload
6911def column(
6912    col: str | Identifier,
6913    table: t.Optional[str | Identifier] = None,
6914    db: t.Optional[str | Identifier] = None,
6915    catalog: t.Optional[str | Identifier] = None,
6916    *,
6917    fields: Lit[None] = None,
6918    quoted: t.Optional[bool] = None,
6919    copy: bool = True,
6920) -> Column:
6921    pass
6922
6923
6924def column(
6925    col,
6926    table=None,
6927    db=None,
6928    catalog=None,
6929    *,
6930    fields=None,
6931    quoted=None,
6932    copy=True,
6933):
6934    """
6935    Build a Column.
6936
6937    Args:
6938        col: Column name.
6939        table: Table name.
6940        db: Database name.
6941        catalog: Catalog name.
6942        fields: Additional fields using dots.
6943        quoted: Whether to force quotes on the column's identifiers.
6944        copy: Whether to copy identifiers if passed in.
6945
6946    Returns:
6947        The new Column instance.
6948    """
6949    this = Column(
6950        this=to_identifier(col, quoted=quoted, copy=copy),
6951        table=to_identifier(table, quoted=quoted, copy=copy),
6952        db=to_identifier(db, quoted=quoted, copy=copy),
6953        catalog=to_identifier(catalog, quoted=quoted, copy=copy),
6954    )
6955
6956    if fields:
6957        this = Dot.build(
6958            (this, *(to_identifier(field, quoted=quoted, copy=copy) for field in fields))
6959        )
6960    return this
6961
6962
6963def cast(expression: ExpOrStr, to: DATA_TYPE, copy: bool = True, **opts) -> Cast:
6964    """Cast an expression to a data type.
6965
6966    Example:
6967        >>> cast('x + 1', 'int').sql()
6968        'CAST(x + 1 AS INT)'
6969
6970    Args:
6971        expression: The expression to cast.
6972        to: The datatype to cast to.
6973        copy: Whether to copy the supplied expressions.
6974
6975    Returns:
6976        The new Cast instance.
6977    """
6978    expr = maybe_parse(expression, copy=copy, **opts)
6979    data_type = DataType.build(to, copy=copy, **opts)
6980
6981    if expr.is_type(data_type):
6982        return expr
6983
6984    expr = Cast(this=expr, to=data_type)
6985    expr.type = data_type
6986
6987    return expr
6988
6989
6990def table_(
6991    table: Identifier | str,
6992    db: t.Optional[Identifier | str] = None,
6993    catalog: t.Optional[Identifier | str] = None,
6994    quoted: t.Optional[bool] = None,
6995    alias: t.Optional[Identifier | str] = None,
6996) -> Table:
6997    """Build a Table.
6998
6999    Args:
7000        table: Table name.
7001        db: Database name.
7002        catalog: Catalog name.
7003        quote: Whether to force quotes on the table's identifiers.
7004        alias: Table's alias.
7005
7006    Returns:
7007        The new Table instance.
7008    """
7009    return Table(
7010        this=to_identifier(table, quoted=quoted) if table else None,
7011        db=to_identifier(db, quoted=quoted) if db else None,
7012        catalog=to_identifier(catalog, quoted=quoted) if catalog else None,
7013        alias=TableAlias(this=to_identifier(alias)) if alias else None,
7014    )
7015
7016
7017def values(
7018    values: t.Iterable[t.Tuple[t.Any, ...]],
7019    alias: t.Optional[str] = None,
7020    columns: t.Optional[t.Iterable[str] | t.Dict[str, DataType]] = None,
7021) -> Values:
7022    """Build VALUES statement.
7023
7024    Example:
7025        >>> values([(1, '2')]).sql()
7026        "VALUES (1, '2')"
7027
7028    Args:
7029        values: values statements that will be converted to SQL
7030        alias: optional alias
7031        columns: Optional list of ordered column names or ordered dictionary of column names to types.
7032         If either are provided then an alias is also required.
7033
7034    Returns:
7035        Values: the Values expression object
7036    """
7037    if columns and not alias:
7038        raise ValueError("Alias is required when providing columns")
7039
7040    return Values(
7041        expressions=[convert(tup) for tup in values],
7042        alias=(
7043            TableAlias(this=to_identifier(alias), columns=[to_identifier(x) for x in columns])
7044            if columns
7045            else (TableAlias(this=to_identifier(alias)) if alias else None)
7046        ),
7047    )
7048
7049
7050def var(name: t.Optional[ExpOrStr]) -> Var:
7051    """Build a SQL variable.
7052
7053    Example:
7054        >>> repr(var('x'))
7055        'Var(this=x)'
7056
7057        >>> repr(var(column('x', table='y')))
7058        'Var(this=x)'
7059
7060    Args:
7061        name: The name of the var or an expression who's name will become the var.
7062
7063    Returns:
7064        The new variable node.
7065    """
7066    if not name:
7067        raise ValueError("Cannot convert empty name into var.")
7068
7069    if isinstance(name, Expression):
7070        name = name.name
7071    return Var(this=name)
7072
7073
7074def rename_table(
7075    old_name: str | Table,
7076    new_name: str | Table,
7077    dialect: DialectType = None,
7078) -> AlterTable:
7079    """Build ALTER TABLE... RENAME... expression
7080
7081    Args:
7082        old_name: The old name of the table
7083        new_name: The new name of the table
7084        dialect: The dialect to parse the table.
7085
7086    Returns:
7087        Alter table expression
7088    """
7089    old_table = to_table(old_name, dialect=dialect)
7090    new_table = to_table(new_name, dialect=dialect)
7091    return AlterTable(
7092        this=old_table,
7093        actions=[
7094            RenameTable(this=new_table),
7095        ],
7096    )
7097
7098
7099def rename_column(
7100    table_name: str | Table,
7101    old_column_name: str | Column,
7102    new_column_name: str | Column,
7103    exists: t.Optional[bool] = None,
7104    dialect: DialectType = None,
7105) -> AlterTable:
7106    """Build ALTER TABLE... RENAME COLUMN... expression
7107
7108    Args:
7109        table_name: Name of the table
7110        old_column: The old name of the column
7111        new_column: The new name of the column
7112        exists: Whether to add the `IF EXISTS` clause
7113        dialect: The dialect to parse the table/column.
7114
7115    Returns:
7116        Alter table expression
7117    """
7118    table = to_table(table_name, dialect=dialect)
7119    old_column = to_column(old_column_name, dialect=dialect)
7120    new_column = to_column(new_column_name, dialect=dialect)
7121    return AlterTable(
7122        this=table,
7123        actions=[
7124            RenameColumn(this=old_column, to=new_column, exists=exists),
7125        ],
7126    )
7127
7128
7129def convert(value: t.Any, copy: bool = False) -> Expression:
7130    """Convert a python value into an expression object.
7131
7132    Raises an error if a conversion is not possible.
7133
7134    Args:
7135        value: A python object.
7136        copy: Whether to copy `value` (only applies to Expressions and collections).
7137
7138    Returns:
7139        The equivalent expression object.
7140    """
7141    if isinstance(value, Expression):
7142        return maybe_copy(value, copy)
7143    if isinstance(value, str):
7144        return Literal.string(value)
7145    if isinstance(value, bool):
7146        return Boolean(this=value)
7147    if value is None or (isinstance(value, float) and math.isnan(value)):
7148        return null()
7149    if isinstance(value, numbers.Number):
7150        return Literal.number(value)
7151    if isinstance(value, bytes):
7152        return HexString(this=value.hex())
7153    if isinstance(value, datetime.datetime):
7154        datetime_literal = Literal.string(
7155            (value if value.tzinfo else value.replace(tzinfo=datetime.timezone.utc)).isoformat(
7156                sep=" "
7157            )
7158        )
7159        return TimeStrToTime(this=datetime_literal)
7160    if isinstance(value, datetime.date):
7161        date_literal = Literal.string(value.strftime("%Y-%m-%d"))
7162        return DateStrToDate(this=date_literal)
7163    if isinstance(value, tuple):
7164        if hasattr(value, "_fields"):
7165            return Struct(
7166                expressions=[
7167                    PropertyEQ(
7168                        this=to_identifier(k), expression=convert(getattr(value, k), copy=copy)
7169                    )
7170                    for k in value._fields
7171                ]
7172            )
7173        return Tuple(expressions=[convert(v, copy=copy) for v in value])
7174    if isinstance(value, list):
7175        return Array(expressions=[convert(v, copy=copy) for v in value])
7176    if isinstance(value, dict):
7177        return Map(
7178            keys=Array(expressions=[convert(k, copy=copy) for k in value]),
7179            values=Array(expressions=[convert(v, copy=copy) for v in value.values()]),
7180        )
7181    if hasattr(value, "__dict__"):
7182        return Struct(
7183            expressions=[
7184                PropertyEQ(this=to_identifier(k), expression=convert(v, copy=copy))
7185                for k, v in value.__dict__.items()
7186            ]
7187        )
7188    raise ValueError(f"Cannot convert {value}")
7189
7190
7191def replace_children(expression: Expression, fun: t.Callable, *args, **kwargs) -> None:
7192    """
7193    Replace children of an expression with the result of a lambda fun(child) -> exp.
7194    """
7195    for k, v in tuple(expression.args.items()):
7196        is_list_arg = type(v) is list
7197
7198        child_nodes = v if is_list_arg else [v]
7199        new_child_nodes = []
7200
7201        for cn in child_nodes:
7202            if isinstance(cn, Expression):
7203                for child_node in ensure_collection(fun(cn, *args, **kwargs)):
7204                    new_child_nodes.append(child_node)
7205            else:
7206                new_child_nodes.append(cn)
7207
7208        expression.set(k, new_child_nodes if is_list_arg else seq_get(new_child_nodes, 0))
7209
7210
7211def replace_tree(
7212    expression: Expression,
7213    fun: t.Callable,
7214    prune: t.Optional[t.Callable[[Expression], bool]] = None,
7215) -> Expression:
7216    """
7217    Replace an entire tree with the result of function calls on each node.
7218
7219    This will be traversed in reverse dfs, so leaves first.
7220    If new nodes are created as a result of function calls, they will also be traversed.
7221    """
7222    stack = list(expression.dfs(prune=prune))
7223
7224    while stack:
7225        node = stack.pop()
7226        new_node = fun(node)
7227
7228        if new_node is not node:
7229            node.replace(new_node)
7230
7231            if isinstance(new_node, Expression):
7232                stack.append(new_node)
7233
7234    return new_node
7235
7236
7237def column_table_names(expression: Expression, exclude: str = "") -> t.Set[str]:
7238    """
7239    Return all table names referenced through columns in an expression.
7240
7241    Example:
7242        >>> import sqlglot
7243        >>> sorted(column_table_names(sqlglot.parse_one("a.b AND c.d AND c.e")))
7244        ['a', 'c']
7245
7246    Args:
7247        expression: expression to find table names.
7248        exclude: a table name to exclude
7249
7250    Returns:
7251        A list of unique names.
7252    """
7253    return {
7254        table
7255        for table in (column.table for column in expression.find_all(Column))
7256        if table and table != exclude
7257    }
7258
7259
7260def table_name(table: Table | str, dialect: DialectType = None, identify: bool = False) -> str:
7261    """Get the full name of a table as a string.
7262
7263    Args:
7264        table: Table expression node or string.
7265        dialect: The dialect to generate the table name for.
7266        identify: Determines when an identifier should be quoted. Possible values are:
7267            False (default): Never quote, except in cases where it's mandatory by the dialect.
7268            True: Always quote.
7269
7270    Examples:
7271        >>> from sqlglot import exp, parse_one
7272        >>> table_name(parse_one("select * from a.b.c").find(exp.Table))
7273        'a.b.c'
7274
7275    Returns:
7276        The table name.
7277    """
7278
7279    table = maybe_parse(table, into=Table, dialect=dialect)
7280
7281    if not table:
7282        raise ValueError(f"Cannot parse {table}")
7283
7284    return ".".join(
7285        (
7286            part.sql(dialect=dialect, identify=True, copy=False)
7287            if identify or not SAFE_IDENTIFIER_RE.match(part.name)
7288            else part.name
7289        )
7290        for part in table.parts
7291    )
7292
7293
7294def normalize_table_name(table: str | Table, dialect: DialectType = None, copy: bool = True) -> str:
7295    """Returns a case normalized table name without quotes.
7296
7297    Args:
7298        table: the table to normalize
7299        dialect: the dialect to use for normalization rules
7300        copy: whether to copy the expression.
7301
7302    Examples:
7303        >>> normalize_table_name("`A-B`.c", dialect="bigquery")
7304        'A-B.c'
7305    """
7306    from sqlglot.optimizer.normalize_identifiers import normalize_identifiers
7307
7308    return ".".join(
7309        p.name
7310        for p in normalize_identifiers(
7311            to_table(table, dialect=dialect, copy=copy), dialect=dialect
7312        ).parts
7313    )
7314
7315
7316def replace_tables(
7317    expression: E, mapping: t.Dict[str, str], dialect: DialectType = None, copy: bool = True
7318) -> E:
7319    """Replace all tables in expression according to the mapping.
7320
7321    Args:
7322        expression: expression node to be transformed and replaced.
7323        mapping: mapping of table names.
7324        dialect: the dialect of the mapping table
7325        copy: whether to copy the expression.
7326
7327    Examples:
7328        >>> from sqlglot import exp, parse_one
7329        >>> replace_tables(parse_one("select * from a.b"), {"a.b": "c"}).sql()
7330        'SELECT * FROM c /* a.b */'
7331
7332    Returns:
7333        The mapped expression.
7334    """
7335
7336    mapping = {normalize_table_name(k, dialect=dialect): v for k, v in mapping.items()}
7337
7338    def _replace_tables(node: Expression) -> Expression:
7339        if isinstance(node, Table):
7340            original = normalize_table_name(node, dialect=dialect)
7341            new_name = mapping.get(original)
7342
7343            if new_name:
7344                table = to_table(
7345                    new_name,
7346                    **{k: v for k, v in node.args.items() if k not in TABLE_PARTS},
7347                    dialect=dialect,
7348                )
7349                table.add_comments([original])
7350                return table
7351        return node
7352
7353    return expression.transform(_replace_tables, copy=copy)  # type: ignore
7354
7355
7356def replace_placeholders(expression: Expression, *args, **kwargs) -> Expression:
7357    """Replace placeholders in an expression.
7358
7359    Args:
7360        expression: expression node to be transformed and replaced.
7361        args: positional names that will substitute unnamed placeholders in the given order.
7362        kwargs: keyword arguments that will substitute named placeholders.
7363
7364    Examples:
7365        >>> from sqlglot import exp, parse_one
7366        >>> replace_placeholders(
7367        ...     parse_one("select * from :tbl where ? = ?"),
7368        ...     exp.to_identifier("str_col"), "b", tbl=exp.to_identifier("foo")
7369        ... ).sql()
7370        "SELECT * FROM foo WHERE str_col = 'b'"
7371
7372    Returns:
7373        The mapped expression.
7374    """
7375
7376    def _replace_placeholders(node: Expression, args, **kwargs) -> Expression:
7377        if isinstance(node, Placeholder):
7378            if node.this:
7379                new_name = kwargs.get(node.this)
7380                if new_name is not None:
7381                    return convert(new_name)
7382            else:
7383                try:
7384                    return convert(next(args))
7385                except StopIteration:
7386                    pass
7387        return node
7388
7389    return expression.transform(_replace_placeholders, iter(args), **kwargs)
7390
7391
7392def expand(
7393    expression: Expression,
7394    sources: t.Dict[str, Query],
7395    dialect: DialectType = None,
7396    copy: bool = True,
7397) -> Expression:
7398    """Transforms an expression by expanding all referenced sources into subqueries.
7399
7400    Examples:
7401        >>> from sqlglot import parse_one
7402        >>> expand(parse_one("select * from x AS z"), {"x": parse_one("select * from y")}).sql()
7403        'SELECT * FROM (SELECT * FROM y) AS z /* source: x */'
7404
7405        >>> expand(parse_one("select * from x AS z"), {"x": parse_one("select * from y"), "y": parse_one("select * from z")}).sql()
7406        'SELECT * FROM (SELECT * FROM (SELECT * FROM z) AS y /* source: y */) AS z /* source: x */'
7407
7408    Args:
7409        expression: The expression to expand.
7410        sources: A dictionary of name to Queries.
7411        dialect: The dialect of the sources dict.
7412        copy: Whether to copy the expression during transformation. Defaults to True.
7413
7414    Returns:
7415        The transformed expression.
7416    """
7417    sources = {normalize_table_name(k, dialect=dialect): v for k, v in sources.items()}
7418
7419    def _expand(node: Expression):
7420        if isinstance(node, Table):
7421            name = normalize_table_name(node, dialect=dialect)
7422            source = sources.get(name)
7423            if source:
7424                subquery = source.subquery(node.alias or name)
7425                subquery.comments = [f"source: {name}"]
7426                return subquery.transform(_expand, copy=False)
7427        return node
7428
7429    return expression.transform(_expand, copy=copy)
7430
7431
7432def func(name: str, *args, copy: bool = True, dialect: DialectType = None, **kwargs) -> Func:
7433    """
7434    Returns a Func expression.
7435
7436    Examples:
7437        >>> func("abs", 5).sql()
7438        'ABS(5)'
7439
7440        >>> func("cast", this=5, to=DataType.build("DOUBLE")).sql()
7441        'CAST(5 AS DOUBLE)'
7442
7443    Args:
7444        name: the name of the function to build.
7445        args: the args used to instantiate the function of interest.
7446        copy: whether to copy the argument expressions.
7447        dialect: the source dialect.
7448        kwargs: the kwargs used to instantiate the function of interest.
7449
7450    Note:
7451        The arguments `args` and `kwargs` are mutually exclusive.
7452
7453    Returns:
7454        An instance of the function of interest, or an anonymous function, if `name` doesn't
7455        correspond to an existing `sqlglot.expressions.Func` class.
7456    """
7457    if args and kwargs:
7458        raise ValueError("Can't use both args and kwargs to instantiate a function.")
7459
7460    from sqlglot.dialects.dialect import Dialect
7461
7462    dialect = Dialect.get_or_raise(dialect)
7463
7464    converted: t.List[Expression] = [maybe_parse(arg, dialect=dialect, copy=copy) for arg in args]
7465    kwargs = {key: maybe_parse(value, dialect=dialect, copy=copy) for key, value in kwargs.items()}
7466
7467    constructor = dialect.parser_class.FUNCTIONS.get(name.upper())
7468    if constructor:
7469        if converted:
7470            if "dialect" in constructor.__code__.co_varnames:
7471                function = constructor(converted, dialect=dialect)
7472            else:
7473                function = constructor(converted)
7474        elif constructor.__name__ == "from_arg_list":
7475            function = constructor.__self__(**kwargs)  # type: ignore
7476        else:
7477            constructor = FUNCTION_BY_NAME.get(name.upper())
7478            if constructor:
7479                function = constructor(**kwargs)
7480            else:
7481                raise ValueError(
7482                    f"Unable to convert '{name}' into a Func. Either manually construct "
7483                    "the Func expression of interest or parse the function call."
7484                )
7485    else:
7486        kwargs = kwargs or {"expressions": converted}
7487        function = Anonymous(this=name, **kwargs)
7488
7489    for error_message in function.error_messages(converted):
7490        raise ValueError(error_message)
7491
7492    return function
7493
7494
7495def case(
7496    expression: t.Optional[ExpOrStr] = None,
7497    **opts,
7498) -> Case:
7499    """
7500    Initialize a CASE statement.
7501
7502    Example:
7503        case().when("a = 1", "foo").else_("bar")
7504
7505    Args:
7506        expression: Optionally, the input expression (not all dialects support this)
7507        **opts: Extra keyword arguments for parsing `expression`
7508    """
7509    if expression is not None:
7510        this = maybe_parse(expression, **opts)
7511    else:
7512        this = None
7513    return Case(this=this, ifs=[])
7514
7515
7516def array(
7517    *expressions: ExpOrStr, copy: bool = True, dialect: DialectType = None, **kwargs
7518) -> Array:
7519    """
7520    Returns an array.
7521
7522    Examples:
7523        >>> array(1, 'x').sql()
7524        'ARRAY(1, x)'
7525
7526    Args:
7527        expressions: the expressions to add to the array.
7528        copy: whether to copy the argument expressions.
7529        dialect: the source dialect.
7530        kwargs: the kwargs used to instantiate the function of interest.
7531
7532    Returns:
7533        An array expression.
7534    """
7535    return Array(
7536        expressions=[
7537            maybe_parse(expression, copy=copy, dialect=dialect, **kwargs)
7538            for expression in expressions
7539        ]
7540    )
7541
7542
7543def tuple_(
7544    *expressions: ExpOrStr, copy: bool = True, dialect: DialectType = None, **kwargs
7545) -> Tuple:
7546    """
7547    Returns an tuple.
7548
7549    Examples:
7550        >>> tuple_(1, 'x').sql()
7551        '(1, x)'
7552
7553    Args:
7554        expressions: the expressions to add to the tuple.
7555        copy: whether to copy the argument expressions.
7556        dialect: the source dialect.
7557        kwargs: the kwargs used to instantiate the function of interest.
7558
7559    Returns:
7560        A tuple expression.
7561    """
7562    return Tuple(
7563        expressions=[
7564            maybe_parse(expression, copy=copy, dialect=dialect, **kwargs)
7565            for expression in expressions
7566        ]
7567    )
7568
7569
7570def true() -> Boolean:
7571    """
7572    Returns a true Boolean expression.
7573    """
7574    return Boolean(this=True)
7575
7576
7577def false() -> Boolean:
7578    """
7579    Returns a false Boolean expression.
7580    """
7581    return Boolean(this=False)
7582
7583
7584def null() -> Null:
7585    """
7586    Returns a Null expression.
7587    """
7588    return Null()
7589
7590
7591NONNULL_CONSTANTS = (
7592    Literal,
7593    Boolean,
7594)
7595
7596CONSTANTS = (
7597    Literal,
7598    Boolean,
7599    Null,
7600)
SQLGLOT_META = 'sqlglot.meta'
TABLE_PARTS = ('this', 'db', 'catalog')
COLUMN_PARTS = ('this', 'table', 'db', 'catalog')
class Expression:
 65class Expression(metaclass=_Expression):
 66    """
 67    The base class for all expressions in a syntax tree. Each Expression encapsulates any necessary
 68    context, such as its child expressions, their names (arg keys), and whether a given child expression
 69    is optional or not.
 70
 71    Attributes:
 72        key: a unique key for each class in the Expression hierarchy. This is useful for hashing
 73            and representing expressions as strings.
 74        arg_types: determines the arguments (child nodes) supported by an expression. It maps
 75            arg keys to booleans that indicate whether the corresponding args are optional.
 76        parent: a reference to the parent expression (or None, in case of root expressions).
 77        arg_key: the arg key an expression is associated with, i.e. the name its parent expression
 78            uses to refer to it.
 79        index: the index of an expression if it is inside of a list argument in its parent.
 80        comments: a list of comments that are associated with a given expression. This is used in
 81            order to preserve comments when transpiling SQL code.
 82        type: the `sqlglot.expressions.DataType` type of an expression. This is inferred by the
 83            optimizer, in order to enable some transformations that require type information.
 84        meta: a dictionary that can be used to store useful metadata for a given expression.
 85
 86    Example:
 87        >>> class Foo(Expression):
 88        ...     arg_types = {"this": True, "expression": False}
 89
 90        The above definition informs us that Foo is an Expression that requires an argument called
 91        "this" and may also optionally receive an argument called "expression".
 92
 93    Args:
 94        args: a mapping used for retrieving the arguments of an expression, given their arg keys.
 95    """
 96
 97    key = "expression"
 98    arg_types = {"this": True}
 99    __slots__ = ("args", "parent", "arg_key", "index", "comments", "_type", "_meta", "_hash")
100
101    def __init__(self, **args: t.Any):
102        self.args: t.Dict[str, t.Any] = args
103        self.parent: t.Optional[Expression] = None
104        self.arg_key: t.Optional[str] = None
105        self.index: t.Optional[int] = None
106        self.comments: t.Optional[t.List[str]] = None
107        self._type: t.Optional[DataType] = None
108        self._meta: t.Optional[t.Dict[str, t.Any]] = None
109        self._hash: t.Optional[int] = None
110
111        for arg_key, value in self.args.items():
112            self._set_parent(arg_key, value)
113
114    def __eq__(self, other) -> bool:
115        return type(self) is type(other) and hash(self) == hash(other)
116
117    @property
118    def hashable_args(self) -> t.Any:
119        return frozenset(
120            (k, tuple(_norm_arg(a) for a in v) if type(v) is list else _norm_arg(v))
121            for k, v in self.args.items()
122            if not (v is None or v is False or (type(v) is list and not v))
123        )
124
125    def __hash__(self) -> int:
126        if self._hash is not None:
127            return self._hash
128
129        return hash((self.__class__, self.hashable_args))
130
131    @property
132    def this(self) -> t.Any:
133        """
134        Retrieves the argument with key "this".
135        """
136        return self.args.get("this")
137
138    @property
139    def expression(self) -> t.Any:
140        """
141        Retrieves the argument with key "expression".
142        """
143        return self.args.get("expression")
144
145    @property
146    def expressions(self) -> t.List[t.Any]:
147        """
148        Retrieves the argument with key "expressions".
149        """
150        return self.args.get("expressions") or []
151
152    def text(self, key) -> str:
153        """
154        Returns a textual representation of the argument corresponding to "key". This can only be used
155        for args that are strings or leaf Expression instances, such as identifiers and literals.
156        """
157        field = self.args.get(key)
158        if isinstance(field, str):
159            return field
160        if isinstance(field, (Identifier, Literal, Var)):
161            return field.this
162        if isinstance(field, (Star, Null)):
163            return field.name
164        return ""
165
166    @property
167    def is_string(self) -> bool:
168        """
169        Checks whether a Literal expression is a string.
170        """
171        return isinstance(self, Literal) and self.args["is_string"]
172
173    @property
174    def is_number(self) -> bool:
175        """
176        Checks whether a Literal expression is a number.
177        """
178        return isinstance(self, Literal) and not self.args["is_string"]
179
180    @property
181    def is_negative(self) -> bool:
182        """
183        Checks whether an expression is negative.
184
185        Handles both exp.Neg and Literal numbers with "-" which come from optimizer.simplify.
186        """
187        return isinstance(self, Neg) or (self.is_number and self.this.startswith("-"))
188
189    @property
190    def is_int(self) -> bool:
191        """
192        Checks whether a Literal expression is an integer.
193        """
194        return self.is_number and is_int(self.name)
195
196    @property
197    def is_star(self) -> bool:
198        """Checks whether an expression is a star."""
199        return isinstance(self, Star) or (isinstance(self, Column) and isinstance(self.this, Star))
200
201    @property
202    def alias(self) -> str:
203        """
204        Returns the alias of the expression, or an empty string if it's not aliased.
205        """
206        if isinstance(self.args.get("alias"), TableAlias):
207            return self.args["alias"].name
208        return self.text("alias")
209
210    @property
211    def alias_column_names(self) -> t.List[str]:
212        table_alias = self.args.get("alias")
213        if not table_alias:
214            return []
215        return [c.name for c in table_alias.args.get("columns") or []]
216
217    @property
218    def name(self) -> str:
219        return self.text("this")
220
221    @property
222    def alias_or_name(self) -> str:
223        return self.alias or self.name
224
225    @property
226    def output_name(self) -> str:
227        """
228        Name of the output column if this expression is a selection.
229
230        If the Expression has no output name, an empty string is returned.
231
232        Example:
233            >>> from sqlglot import parse_one
234            >>> parse_one("SELECT a").expressions[0].output_name
235            'a'
236            >>> parse_one("SELECT b AS c").expressions[0].output_name
237            'c'
238            >>> parse_one("SELECT 1 + 2").expressions[0].output_name
239            ''
240        """
241        return ""
242
243    @property
244    def type(self) -> t.Optional[DataType]:
245        return self._type
246
247    @type.setter
248    def type(self, dtype: t.Optional[DataType | DataType.Type | str]) -> None:
249        if dtype and not isinstance(dtype, DataType):
250            dtype = DataType.build(dtype)
251        self._type = dtype  # type: ignore
252
253    def is_type(self, *dtypes) -> bool:
254        return self.type is not None and self.type.is_type(*dtypes)
255
256    def is_leaf(self) -> bool:
257        return not any(isinstance(v, (Expression, list)) for v in self.args.values())
258
259    @property
260    def meta(self) -> t.Dict[str, t.Any]:
261        if self._meta is None:
262            self._meta = {}
263        return self._meta
264
265    def __deepcopy__(self, memo):
266        root = self.__class__()
267        stack = [(self, root)]
268
269        while stack:
270            node, copy = stack.pop()
271
272            if node.comments is not None:
273                copy.comments = deepcopy(node.comments)
274            if node._type is not None:
275                copy._type = deepcopy(node._type)
276            if node._meta is not None:
277                copy._meta = deepcopy(node._meta)
278            if node._hash is not None:
279                copy._hash = node._hash
280
281            for k, vs in node.args.items():
282                if hasattr(vs, "parent"):
283                    stack.append((vs, vs.__class__()))
284                    copy.set(k, stack[-1][-1])
285                elif type(vs) is list:
286                    copy.args[k] = []
287
288                    for v in vs:
289                        if hasattr(v, "parent"):
290                            stack.append((v, v.__class__()))
291                            copy.append(k, stack[-1][-1])
292                        else:
293                            copy.append(k, v)
294                else:
295                    copy.args[k] = vs
296
297        return root
298
299    def copy(self):
300        """
301        Returns a deep copy of the expression.
302        """
303        return deepcopy(self)
304
305    def add_comments(self, comments: t.Optional[t.List[str]] = None) -> None:
306        if self.comments is None:
307            self.comments = []
308
309        if comments:
310            for comment in comments:
311                _, *meta = comment.split(SQLGLOT_META)
312                if meta:
313                    for kv in "".join(meta).split(","):
314                        k, *v = kv.split("=")
315                        value = v[0].strip() if v else True
316                        self.meta[k.strip()] = value
317                self.comments.append(comment)
318
319    def pop_comments(self) -> t.List[str]:
320        comments = self.comments or []
321        self.comments = None
322        return comments
323
324    def append(self, arg_key: str, value: t.Any) -> None:
325        """
326        Appends value to arg_key if it's a list or sets it as a new list.
327
328        Args:
329            arg_key (str): name of the list expression arg
330            value (Any): value to append to the list
331        """
332        if type(self.args.get(arg_key)) is not list:
333            self.args[arg_key] = []
334        self._set_parent(arg_key, value)
335        values = self.args[arg_key]
336        if hasattr(value, "parent"):
337            value.index = len(values)
338        values.append(value)
339
340    def set(self, arg_key: str, value: t.Any, index: t.Optional[int] = None) -> None:
341        """
342        Sets arg_key to value.
343
344        Args:
345            arg_key: name of the expression arg.
346            value: value to set the arg to.
347            index: if the arg is a list, this specifies what position to add the value in it.
348        """
349        if index is not None:
350            expressions = self.args.get(arg_key) or []
351
352            if seq_get(expressions, index) is None:
353                return
354            if value is None:
355                expressions.pop(index)
356                for v in expressions[index:]:
357                    v.index = v.index - 1
358                return
359
360            if isinstance(value, list):
361                expressions.pop(index)
362                expressions[index:index] = value
363            else:
364                expressions[index] = value
365
366            value = expressions
367        elif value is None:
368            self.args.pop(arg_key, None)
369            return
370
371        self.args[arg_key] = value
372        self._set_parent(arg_key, value, index)
373
374    def _set_parent(self, arg_key: str, value: t.Any, index: t.Optional[int] = None) -> None:
375        if hasattr(value, "parent"):
376            value.parent = self
377            value.arg_key = arg_key
378            value.index = index
379        elif type(value) is list:
380            for index, v in enumerate(value):
381                if hasattr(v, "parent"):
382                    v.parent = self
383                    v.arg_key = arg_key
384                    v.index = index
385
386    @property
387    def depth(self) -> int:
388        """
389        Returns the depth of this tree.
390        """
391        if self.parent:
392            return self.parent.depth + 1
393        return 0
394
395    def iter_expressions(self, reverse: bool = False) -> t.Iterator[Expression]:
396        """Yields the key and expression for all arguments, exploding list args."""
397        # remove tuple when python 3.7 is deprecated
398        for vs in reversed(tuple(self.args.values())) if reverse else self.args.values():
399            if type(vs) is list:
400                for v in reversed(vs) if reverse else vs:
401                    if hasattr(v, "parent"):
402                        yield v
403            else:
404                if hasattr(vs, "parent"):
405                    yield vs
406
407    def find(self, *expression_types: t.Type[E], bfs: bool = True) -> t.Optional[E]:
408        """
409        Returns the first node in this tree which matches at least one of
410        the specified types.
411
412        Args:
413            expression_types: the expression type(s) to match.
414            bfs: whether to search the AST using the BFS algorithm (DFS is used if false).
415
416        Returns:
417            The node which matches the criteria or None if no such node was found.
418        """
419        return next(self.find_all(*expression_types, bfs=bfs), None)
420
421    def find_all(self, *expression_types: t.Type[E], bfs: bool = True) -> t.Iterator[E]:
422        """
423        Returns a generator object which visits all nodes in this tree and only
424        yields those that match at least one of the specified expression types.
425
426        Args:
427            expression_types: the expression type(s) to match.
428            bfs: whether to search the AST using the BFS algorithm (DFS is used if false).
429
430        Returns:
431            The generator object.
432        """
433        for expression in self.walk(bfs=bfs):
434            if isinstance(expression, expression_types):
435                yield expression
436
437    def find_ancestor(self, *expression_types: t.Type[E]) -> t.Optional[E]:
438        """
439        Returns a nearest parent matching expression_types.
440
441        Args:
442            expression_types: the expression type(s) to match.
443
444        Returns:
445            The parent node.
446        """
447        ancestor = self.parent
448        while ancestor and not isinstance(ancestor, expression_types):
449            ancestor = ancestor.parent
450        return ancestor  # type: ignore
451
452    @property
453    def parent_select(self) -> t.Optional[Select]:
454        """
455        Returns the parent select statement.
456        """
457        return self.find_ancestor(Select)
458
459    @property
460    def same_parent(self) -> bool:
461        """Returns if the parent is the same class as itself."""
462        return type(self.parent) is self.__class__
463
464    def root(self) -> Expression:
465        """
466        Returns the root expression of this tree.
467        """
468        expression = self
469        while expression.parent:
470            expression = expression.parent
471        return expression
472
473    def walk(
474        self, bfs: bool = True, prune: t.Optional[t.Callable[[Expression], bool]] = None
475    ) -> t.Iterator[Expression]:
476        """
477        Returns a generator object which visits all nodes in this tree.
478
479        Args:
480            bfs: if set to True the BFS traversal order will be applied,
481                otherwise the DFS traversal will be used instead.
482            prune: callable that returns True if the generator should stop traversing
483                this branch of the tree.
484
485        Returns:
486            the generator object.
487        """
488        if bfs:
489            yield from self.bfs(prune=prune)
490        else:
491            yield from self.dfs(prune=prune)
492
493    def dfs(
494        self, prune: t.Optional[t.Callable[[Expression], bool]] = None
495    ) -> t.Iterator[Expression]:
496        """
497        Returns a generator object which visits all nodes in this tree in
498        the DFS (Depth-first) order.
499
500        Returns:
501            The generator object.
502        """
503        stack = [self]
504
505        while stack:
506            node = stack.pop()
507
508            yield node
509
510            if prune and prune(node):
511                continue
512
513            for v in node.iter_expressions(reverse=True):
514                stack.append(v)
515
516    def bfs(
517        self, prune: t.Optional[t.Callable[[Expression], bool]] = None
518    ) -> t.Iterator[Expression]:
519        """
520        Returns a generator object which visits all nodes in this tree in
521        the BFS (Breadth-first) order.
522
523        Returns:
524            The generator object.
525        """
526        queue = deque([self])
527
528        while queue:
529            node = queue.popleft()
530
531            yield node
532
533            if prune and prune(node):
534                continue
535
536            for v in node.iter_expressions():
537                queue.append(v)
538
539    def unnest(self):
540        """
541        Returns the first non parenthesis child or self.
542        """
543        expression = self
544        while type(expression) is Paren:
545            expression = expression.this
546        return expression
547
548    def unalias(self):
549        """
550        Returns the inner expression if this is an Alias.
551        """
552        if isinstance(self, Alias):
553            return self.this
554        return self
555
556    def unnest_operands(self):
557        """
558        Returns unnested operands as a tuple.
559        """
560        return tuple(arg.unnest() for arg in self.iter_expressions())
561
562    def flatten(self, unnest=True):
563        """
564        Returns a generator which yields child nodes whose parents are the same class.
565
566        A AND B AND C -> [A, B, C]
567        """
568        for node in self.dfs(prune=lambda n: n.parent and type(n) is not self.__class__):
569            if type(node) is not self.__class__:
570                yield node.unnest() if unnest and not isinstance(node, Subquery) else node
571
572    def __str__(self) -> str:
573        return self.sql()
574
575    def __repr__(self) -> str:
576        return _to_s(self)
577
578    def to_s(self) -> str:
579        """
580        Same as __repr__, but includes additional information which can be useful
581        for debugging, like empty or missing args and the AST nodes' object IDs.
582        """
583        return _to_s(self, verbose=True)
584
585    def sql(self, dialect: DialectType = None, **opts) -> str:
586        """
587        Returns SQL string representation of this tree.
588
589        Args:
590            dialect: the dialect of the output SQL string (eg. "spark", "hive", "presto", "mysql").
591            opts: other `sqlglot.generator.Generator` options.
592
593        Returns:
594            The SQL string.
595        """
596        from sqlglot.dialects import Dialect
597
598        return Dialect.get_or_raise(dialect).generate(self, **opts)
599
600    def transform(self, fun: t.Callable, *args: t.Any, copy: bool = True, **kwargs) -> Expression:
601        """
602        Visits all tree nodes (excluding already transformed ones)
603        and applies the given transformation function to each node.
604
605        Args:
606            fun: a function which takes a node as an argument and returns a
607                new transformed node or the same node without modifications. If the function
608                returns None, then the corresponding node will be removed from the syntax tree.
609            copy: if set to True a new tree instance is constructed, otherwise the tree is
610                modified in place.
611
612        Returns:
613            The transformed tree.
614        """
615        root = None
616        new_node = None
617
618        for node in (self.copy() if copy else self).dfs(prune=lambda n: n is not new_node):
619            parent, arg_key, index = node.parent, node.arg_key, node.index
620            new_node = fun(node, *args, **kwargs)
621
622            if not root:
623                root = new_node
624            elif new_node is not node:
625                parent.set(arg_key, new_node, index)
626
627        assert root
628        return root.assert_is(Expression)
629
630    @t.overload
631    def replace(self, expression: E) -> E: ...
632
633    @t.overload
634    def replace(self, expression: None) -> None: ...
635
636    def replace(self, expression):
637        """
638        Swap out this expression with a new expression.
639
640        For example::
641
642            >>> tree = Select().select("x").from_("tbl")
643            >>> tree.find(Column).replace(column("y"))
644            Column(
645              this=Identifier(this=y, quoted=False))
646            >>> tree.sql()
647            'SELECT y FROM tbl'
648
649        Args:
650            expression: new node
651
652        Returns:
653            The new expression or expressions.
654        """
655        parent = self.parent
656
657        if not parent or parent is expression:
658            return expression
659
660        key = self.arg_key
661        value = parent.args.get(key)
662
663        if type(expression) is list and isinstance(value, Expression):
664            # We are trying to replace an Expression with a list, so it's assumed that
665            # the intention was to really replace the parent of this expression.
666            value.parent.replace(expression)
667        else:
668            parent.set(key, expression, self.index)
669
670        if expression is not self:
671            self.parent = None
672            self.arg_key = None
673            self.index = None
674
675        return expression
676
677    def pop(self: E) -> E:
678        """
679        Remove this expression from its AST.
680
681        Returns:
682            The popped expression.
683        """
684        self.replace(None)
685        return self
686
687    def assert_is(self, type_: t.Type[E]) -> E:
688        """
689        Assert that this `Expression` is an instance of `type_`.
690
691        If it is NOT an instance of `type_`, this raises an assertion error.
692        Otherwise, this returns this expression.
693
694        Examples:
695            This is useful for type security in chained expressions:
696
697            >>> import sqlglot
698            >>> sqlglot.parse_one("SELECT x from y").assert_is(Select).select("z").sql()
699            'SELECT x, z FROM y'
700        """
701        if not isinstance(self, type_):
702            raise AssertionError(f"{self} is not {type_}.")
703        return self
704
705    def error_messages(self, args: t.Optional[t.Sequence] = None) -> t.List[str]:
706        """
707        Checks if this expression is valid (e.g. all mandatory args are set).
708
709        Args:
710            args: a sequence of values that were used to instantiate a Func expression. This is used
711                to check that the provided arguments don't exceed the function argument limit.
712
713        Returns:
714            A list of error messages for all possible errors that were found.
715        """
716        errors: t.List[str] = []
717
718        for k in self.args:
719            if k not in self.arg_types:
720                errors.append(f"Unexpected keyword: '{k}' for {self.__class__}")
721        for k, mandatory in self.arg_types.items():
722            v = self.args.get(k)
723            if mandatory and (v is None or (isinstance(v, list) and not v)):
724                errors.append(f"Required keyword: '{k}' missing for {self.__class__}")
725
726        if (
727            args
728            and isinstance(self, Func)
729            and len(args) > len(self.arg_types)
730            and not self.is_var_len_args
731        ):
732            errors.append(
733                f"The number of provided arguments ({len(args)}) is greater than "
734                f"the maximum number of supported arguments ({len(self.arg_types)})"
735            )
736
737        return errors
738
739    def dump(self):
740        """
741        Dump this Expression to a JSON-serializable dict.
742        """
743        from sqlglot.serde import dump
744
745        return dump(self)
746
747    @classmethod
748    def load(cls, obj):
749        """
750        Load a dict (as returned by `Expression.dump`) into an Expression instance.
751        """
752        from sqlglot.serde import load
753
754        return load(obj)
755
756    def and_(
757        self,
758        *expressions: t.Optional[ExpOrStr],
759        dialect: DialectType = None,
760        copy: bool = True,
761        **opts,
762    ) -> Condition:
763        """
764        AND this condition with one or multiple expressions.
765
766        Example:
767            >>> condition("x=1").and_("y=1").sql()
768            'x = 1 AND y = 1'
769
770        Args:
771            *expressions: the SQL code strings to parse.
772                If an `Expression` instance is passed, it will be used as-is.
773            dialect: the dialect used to parse the input expression.
774            copy: whether to copy the involved expressions (only applies to Expressions).
775            opts: other options to use to parse the input expressions.
776
777        Returns:
778            The new And condition.
779        """
780        return and_(self, *expressions, dialect=dialect, copy=copy, **opts)
781
782    def or_(
783        self,
784        *expressions: t.Optional[ExpOrStr],
785        dialect: DialectType = None,
786        copy: bool = True,
787        **opts,
788    ) -> Condition:
789        """
790        OR this condition with one or multiple expressions.
791
792        Example:
793            >>> condition("x=1").or_("y=1").sql()
794            'x = 1 OR y = 1'
795
796        Args:
797            *expressions: the SQL code strings to parse.
798                If an `Expression` instance is passed, it will be used as-is.
799            dialect: the dialect used to parse the input expression.
800            copy: whether to copy the involved expressions (only applies to Expressions).
801            opts: other options to use to parse the input expressions.
802
803        Returns:
804            The new Or condition.
805        """
806        return or_(self, *expressions, dialect=dialect, copy=copy, **opts)
807
808    def not_(self, copy: bool = True):
809        """
810        Wrap this condition with NOT.
811
812        Example:
813            >>> condition("x=1").not_().sql()
814            'NOT x = 1'
815
816        Args:
817            copy: whether to copy this object.
818
819        Returns:
820            The new Not instance.
821        """
822        return not_(self, copy=copy)
823
824    def as_(
825        self,
826        alias: str | Identifier,
827        quoted: t.Optional[bool] = None,
828        dialect: DialectType = None,
829        copy: bool = True,
830        **opts,
831    ) -> Alias:
832        return alias_(self, alias, quoted=quoted, dialect=dialect, copy=copy, **opts)
833
834    def _binop(self, klass: t.Type[E], other: t.Any, reverse: bool = False) -> E:
835        this = self.copy()
836        other = convert(other, copy=True)
837        if not isinstance(this, klass) and not isinstance(other, klass):
838            this = _wrap(this, Binary)
839            other = _wrap(other, Binary)
840        if reverse:
841            return klass(this=other, expression=this)
842        return klass(this=this, expression=other)
843
844    def __getitem__(self, other: ExpOrStr | t.Tuple[ExpOrStr]) -> Bracket:
845        return Bracket(
846            this=self.copy(), expressions=[convert(e, copy=True) for e in ensure_list(other)]
847        )
848
849    def __iter__(self) -> t.Iterator:
850        if "expressions" in self.arg_types:
851            return iter(self.args.get("expressions") or [])
852        # We define this because __getitem__ converts Expression into an iterable, which is
853        # problematic because one can hit infinite loops if they do "for x in some_expr: ..."
854        # See: https://peps.python.org/pep-0234/
855        raise TypeError(f"'{self.__class__.__name__}' object is not iterable")
856
857    def isin(
858        self,
859        *expressions: t.Any,
860        query: t.Optional[ExpOrStr] = None,
861        unnest: t.Optional[ExpOrStr] | t.Collection[ExpOrStr] = None,
862        copy: bool = True,
863        **opts,
864    ) -> In:
865        subquery = maybe_parse(query, copy=copy, **opts) if query else None
866        if subquery and not isinstance(subquery, Subquery):
867            subquery = subquery.subquery(copy=False)
868
869        return In(
870            this=maybe_copy(self, copy),
871            expressions=[convert(e, copy=copy) for e in expressions],
872            query=subquery,
873            unnest=(
874                Unnest(
875                    expressions=[
876                        maybe_parse(t.cast(ExpOrStr, e), copy=copy, **opts)
877                        for e in ensure_list(unnest)
878                    ]
879                )
880                if unnest
881                else None
882            ),
883        )
884
885    def between(self, low: t.Any, high: t.Any, copy: bool = True, **opts) -> Between:
886        return Between(
887            this=maybe_copy(self, copy),
888            low=convert(low, copy=copy, **opts),
889            high=convert(high, copy=copy, **opts),
890        )
891
892    def is_(self, other: ExpOrStr) -> Is:
893        return self._binop(Is, other)
894
895    def like(self, other: ExpOrStr) -> Like:
896        return self._binop(Like, other)
897
898    def ilike(self, other: ExpOrStr) -> ILike:
899        return self._binop(ILike, other)
900
901    def eq(self, other: t.Any) -> EQ:
902        return self._binop(EQ, other)
903
904    def neq(self, other: t.Any) -> NEQ:
905        return self._binop(NEQ, other)
906
907    def rlike(self, other: ExpOrStr) -> RegexpLike:
908        return self._binop(RegexpLike, other)
909
910    def div(self, other: ExpOrStr, typed: bool = False, safe: bool = False) -> Div:
911        div = self._binop(Div, other)
912        div.args["typed"] = typed
913        div.args["safe"] = safe
914        return div
915
916    def asc(self, nulls_first: bool = True) -> Ordered:
917        return Ordered(this=self.copy(), nulls_first=nulls_first)
918
919    def desc(self, nulls_first: bool = False) -> Ordered:
920        return Ordered(this=self.copy(), desc=True, nulls_first=nulls_first)
921
922    def __lt__(self, other: t.Any) -> LT:
923        return self._binop(LT, other)
924
925    def __le__(self, other: t.Any) -> LTE:
926        return self._binop(LTE, other)
927
928    def __gt__(self, other: t.Any) -> GT:
929        return self._binop(GT, other)
930
931    def __ge__(self, other: t.Any) -> GTE:
932        return self._binop(GTE, other)
933
934    def __add__(self, other: t.Any) -> Add:
935        return self._binop(Add, other)
936
937    def __radd__(self, other: t.Any) -> Add:
938        return self._binop(Add, other, reverse=True)
939
940    def __sub__(self, other: t.Any) -> Sub:
941        return self._binop(Sub, other)
942
943    def __rsub__(self, other: t.Any) -> Sub:
944        return self._binop(Sub, other, reverse=True)
945
946    def __mul__(self, other: t.Any) -> Mul:
947        return self._binop(Mul, other)
948
949    def __rmul__(self, other: t.Any) -> Mul:
950        return self._binop(Mul, other, reverse=True)
951
952    def __truediv__(self, other: t.Any) -> Div:
953        return self._binop(Div, other)
954
955    def __rtruediv__(self, other: t.Any) -> Div:
956        return self._binop(Div, other, reverse=True)
957
958    def __floordiv__(self, other: t.Any) -> IntDiv:
959        return self._binop(IntDiv, other)
960
961    def __rfloordiv__(self, other: t.Any) -> IntDiv:
962        return self._binop(IntDiv, other, reverse=True)
963
964    def __mod__(self, other: t.Any) -> Mod:
965        return self._binop(Mod, other)
966
967    def __rmod__(self, other: t.Any) -> Mod:
968        return self._binop(Mod, other, reverse=True)
969
970    def __pow__(self, other: t.Any) -> Pow:
971        return self._binop(Pow, other)
972
973    def __rpow__(self, other: t.Any) -> Pow:
974        return self._binop(Pow, other, reverse=True)
975
976    def __and__(self, other: t.Any) -> And:
977        return self._binop(And, other)
978
979    def __rand__(self, other: t.Any) -> And:
980        return self._binop(And, other, reverse=True)
981
982    def __or__(self, other: t.Any) -> Or:
983        return self._binop(Or, other)
984
985    def __ror__(self, other: t.Any) -> Or:
986        return self._binop(Or, other, reverse=True)
987
988    def __neg__(self) -> Neg:
989        return Neg(this=_wrap(self.copy(), Binary))
990
991    def __invert__(self) -> Not:
992        return not_(self.copy())

The base class for all expressions in a syntax tree. Each Expression encapsulates any necessary context, such as its child expressions, their names (arg keys), and whether a given child expression is optional or not.

Attributes:
  • key: a unique key for each class in the Expression hierarchy. This is useful for hashing and representing expressions as strings.
  • arg_types: determines the arguments (child nodes) supported by an expression. It maps arg keys to booleans that indicate whether the corresponding args are optional.
  • parent: a reference to the parent expression (or None, in case of root expressions).
  • arg_key: the arg key an expression is associated with, i.e. the name its parent expression uses to refer to it.
  • index: the index of an expression if it is inside of a list argument in its parent.
  • comments: a list of comments that are associated with a given expression. This is used in order to preserve comments when transpiling SQL code.
  • type: the DataType type of an expression. This is inferred by the optimizer, in order to enable some transformations that require type information.
  • meta: a dictionary that can be used to store useful metadata for a given expression.
Example:
>>> class Foo(Expression):
...     arg_types = {"this": True, "expression": False}

The above definition informs us that Foo is an Expression that requires an argument called "this" and may also optionally receive an argument called "expression".

Arguments:
  • args: a mapping used for retrieving the arguments of an expression, given their arg keys.
Expression(**args: Any)
101    def __init__(self, **args: t.Any):
102        self.args: t.Dict[str, t.Any] = args
103        self.parent: t.Optional[Expression] = None
104        self.arg_key: t.Optional[str] = None
105        self.index: t.Optional[int] = None
106        self.comments: t.Optional[t.List[str]] = None
107        self._type: t.Optional[DataType] = None
108        self._meta: t.Optional[t.Dict[str, t.Any]] = None
109        self._hash: t.Optional[int] = None
110
111        for arg_key, value in self.args.items():
112            self._set_parent(arg_key, value)
key = 'expression'
arg_types = {'this': True}
args: Dict[str, Any]
parent: Optional[Expression]
arg_key: Optional[str]
index: Optional[int]
comments: Optional[List[str]]
hashable_args: Any
117    @property
118    def hashable_args(self) -> t.Any:
119        return frozenset(
120            (k, tuple(_norm_arg(a) for a in v) if type(v) is list else _norm_arg(v))
121            for k, v in self.args.items()
122            if not (v is None or v is False or (type(v) is list and not v))
123        )
this: Any
131    @property
132    def this(self) -> t.Any:
133        """
134        Retrieves the argument with key "this".
135        """
136        return self.args.get("this")

Retrieves the argument with key "this".

expression: Any
138    @property
139    def expression(self) -> t.Any:
140        """
141        Retrieves the argument with key "expression".
142        """
143        return self.args.get("expression")

Retrieves the argument with key "expression".

expressions: List[Any]
145    @property
146    def expressions(self) -> t.List[t.Any]:
147        """
148        Retrieves the argument with key "expressions".
149        """
150        return self.args.get("expressions") or []

Retrieves the argument with key "expressions".

def text(self, key) -> str:
152    def text(self, key) -> str:
153        """
154        Returns a textual representation of the argument corresponding to "key". This can only be used
155        for args that are strings or leaf Expression instances, such as identifiers and literals.
156        """
157        field = self.args.get(key)
158        if isinstance(field, str):
159            return field
160        if isinstance(field, (Identifier, Literal, Var)):
161            return field.this
162        if isinstance(field, (Star, Null)):
163            return field.name
164        return ""

Returns a textual representation of the argument corresponding to "key". This can only be used for args that are strings or leaf Expression instances, such as identifiers and literals.

is_string: bool
166    @property
167    def is_string(self) -> bool:
168        """
169        Checks whether a Literal expression is a string.
170        """
171        return isinstance(self, Literal) and self.args["is_string"]

Checks whether a Literal expression is a string.

is_number: bool
173    @property
174    def is_number(self) -> bool:
175        """
176        Checks whether a Literal expression is a number.
177        """
178        return isinstance(self, Literal) and not self.args["is_string"]

Checks whether a Literal expression is a number.

is_negative: bool
180    @property
181    def is_negative(self) -> bool:
182        """
183        Checks whether an expression is negative.
184
185        Handles both exp.Neg and Literal numbers with "-" which come from optimizer.simplify.
186        """
187        return isinstance(self, Neg) or (self.is_number and self.this.startswith("-"))

Checks whether an expression is negative.

Handles both exp.Neg and Literal numbers with "-" which come from optimizer.simplify.

is_int: bool
189    @property
190    def is_int(self) -> bool:
191        """
192        Checks whether a Literal expression is an integer.
193        """
194        return self.is_number and is_int(self.name)

Checks whether a Literal expression is an integer.

is_star: bool
196    @property
197    def is_star(self) -> bool:
198        """Checks whether an expression is a star."""
199        return isinstance(self, Star) or (isinstance(self, Column) and isinstance(self.this, Star))

Checks whether an expression is a star.

alias: str
201    @property
202    def alias(self) -> str:
203        """
204        Returns the alias of the expression, or an empty string if it's not aliased.
205        """
206        if isinstance(self.args.get("alias"), TableAlias):
207            return self.args["alias"].name
208        return self.text("alias")

Returns the alias of the expression, or an empty string if it's not aliased.

alias_column_names: List[str]
210    @property
211    def alias_column_names(self) -> t.List[str]:
212        table_alias = self.args.get("alias")
213        if not table_alias:
214            return []
215        return [c.name for c in table_alias.args.get("columns") or []]
name: str
217    @property
218    def name(self) -> str:
219        return self.text("this")
alias_or_name: str
221    @property
222    def alias_or_name(self) -> str:
223        return self.alias or self.name
output_name: str
225    @property
226    def output_name(self) -> str:
227        """
228        Name of the output column if this expression is a selection.
229
230        If the Expression has no output name, an empty string is returned.
231
232        Example:
233            >>> from sqlglot import parse_one
234            >>> parse_one("SELECT a").expressions[0].output_name
235            'a'
236            >>> parse_one("SELECT b AS c").expressions[0].output_name
237            'c'
238            >>> parse_one("SELECT 1 + 2").expressions[0].output_name
239            ''
240        """
241        return ""

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
type: Optional[DataType]
243    @property
244    def type(self) -> t.Optional[DataType]:
245        return self._type
def is_type(self, *dtypes) -> bool:
253    def is_type(self, *dtypes) -> bool:
254        return self.type is not None and self.type.is_type(*dtypes)
def is_leaf(self) -> bool:
256    def is_leaf(self) -> bool:
257        return not any(isinstance(v, (Expression, list)) for v in self.args.values())
meta: Dict[str, Any]
259    @property
260    def meta(self) -> t.Dict[str, t.Any]:
261        if self._meta is None:
262            self._meta = {}
263        return self._meta
def copy(self):
299    def copy(self):
300        """
301        Returns a deep copy of the expression.
302        """
303        return deepcopy(self)

Returns a deep copy of the expression.

def add_comments(self, comments: Optional[List[str]] = None) -> None:
305    def add_comments(self, comments: t.Optional[t.List[str]] = None) -> None:
306        if self.comments is None:
307            self.comments = []
308
309        if comments:
310            for comment in comments:
311                _, *meta = comment.split(SQLGLOT_META)
312                if meta:
313                    for kv in "".join(meta).split(","):
314                        k, *v = kv.split("=")
315                        value = v[0].strip() if v else True
316                        self.meta[k.strip()] = value
317                self.comments.append(comment)
def pop_comments(self) -> List[str]:
319    def pop_comments(self) -> t.List[str]:
320        comments = self.comments or []
321        self.comments = None
322        return comments
def append(self, arg_key: str, value: Any) -> None:
324    def append(self, arg_key: str, value: t.Any) -> None:
325        """
326        Appends value to arg_key if it's a list or sets it as a new list.
327
328        Args:
329            arg_key (str): name of the list expression arg
330            value (Any): value to append to the list
331        """
332        if type(self.args.get(arg_key)) is not list:
333            self.args[arg_key] = []
334        self._set_parent(arg_key, value)
335        values = self.args[arg_key]
336        if hasattr(value, "parent"):
337            value.index = len(values)
338        values.append(value)

Appends value to arg_key if it's a list or sets it as a new list.

Arguments:
  • arg_key (str): name of the list expression arg
  • value (Any): value to append to the list
def set(self, arg_key: str, value: Any, index: Optional[int] = None) -> None:
340    def set(self, arg_key: str, value: t.Any, index: t.Optional[int] = None) -> None:
341        """
342        Sets arg_key to value.
343
344        Args:
345            arg_key: name of the expression arg.
346            value: value to set the arg to.
347            index: if the arg is a list, this specifies what position to add the value in it.
348        """
349        if index is not None:
350            expressions = self.args.get(arg_key) or []
351
352            if seq_get(expressions, index) is None:
353                return
354            if value is None:
355                expressions.pop(index)
356                for v in expressions[index:]:
357                    v.index = v.index - 1
358                return
359
360            if isinstance(value, list):
361                expressions.pop(index)
362                expressions[index:index] = value
363            else:
364                expressions[index] = value
365
366            value = expressions
367        elif value is None:
368            self.args.pop(arg_key, None)
369            return
370
371        self.args[arg_key] = value
372        self._set_parent(arg_key, value, index)

Sets arg_key to value.

Arguments:
  • arg_key: name of the expression arg.
  • value: value to set the arg to.
  • index: if the arg is a list, this specifies what position to add the value in it.
depth: int
386    @property
387    def depth(self) -> int:
388        """
389        Returns the depth of this tree.
390        """
391        if self.parent:
392            return self.parent.depth + 1
393        return 0

Returns the depth of this tree.

def iter_expressions(self, reverse: bool = False) -> Iterator[Expression]:
395    def iter_expressions(self, reverse: bool = False) -> t.Iterator[Expression]:
396        """Yields the key and expression for all arguments, exploding list args."""
397        # remove tuple when python 3.7 is deprecated
398        for vs in reversed(tuple(self.args.values())) if reverse else self.args.values():
399            if type(vs) is list:
400                for v in reversed(vs) if reverse else vs:
401                    if hasattr(v, "parent"):
402                        yield v
403            else:
404                if hasattr(vs, "parent"):
405                    yield vs

Yields the key and expression for all arguments, exploding list args.

def find(self, *expression_types: Type[~E], bfs: bool = True) -> Optional[~E]:
407    def find(self, *expression_types: t.Type[E], bfs: bool = True) -> t.Optional[E]:
408        """
409        Returns the first node in this tree which matches at least one of
410        the specified types.
411
412        Args:
413            expression_types: the expression type(s) to match.
414            bfs: whether to search the AST using the BFS algorithm (DFS is used if false).
415
416        Returns:
417            The node which matches the criteria or None if no such node was found.
418        """
419        return next(self.find_all(*expression_types, bfs=bfs), None)

Returns the first node in this tree which matches at least one of the specified types.

Arguments:
  • expression_types: the expression type(s) to match.
  • bfs: whether to search the AST using the BFS algorithm (DFS is used if false).
Returns:

The node which matches the criteria or None if no such node was found.

def find_all(self, *expression_types: Type[~E], bfs: bool = True) -> Iterator[~E]:
421    def find_all(self, *expression_types: t.Type[E], bfs: bool = True) -> t.Iterator[E]:
422        """
423        Returns a generator object which visits all nodes in this tree and only
424        yields those that match at least one of the specified expression types.
425
426        Args:
427            expression_types: the expression type(s) to match.
428            bfs: whether to search the AST using the BFS algorithm (DFS is used if false).
429
430        Returns:
431            The generator object.
432        """
433        for expression in self.walk(bfs=bfs):
434            if isinstance(expression, expression_types):
435                yield expression

Returns a generator object which visits all nodes in this tree and only yields those that match at least one of the specified expression types.

Arguments:
  • expression_types: the expression type(s) to match.
  • bfs: whether to search the AST using the BFS algorithm (DFS is used if false).
Returns:

The generator object.

def find_ancestor(self, *expression_types: Type[~E]) -> Optional[~E]:
437    def find_ancestor(self, *expression_types: t.Type[E]) -> t.Optional[E]:
438        """
439        Returns a nearest parent matching expression_types.
440
441        Args:
442            expression_types: the expression type(s) to match.
443
444        Returns:
445            The parent node.
446        """
447        ancestor = self.parent
448        while ancestor and not isinstance(ancestor, expression_types):
449            ancestor = ancestor.parent
450        return ancestor  # type: ignore

Returns a nearest parent matching expression_types.

Arguments:
  • expression_types: the expression type(s) to match.
Returns:

The parent node.

parent_select: Optional[Select]
452    @property
453    def parent_select(self) -> t.Optional[Select]:
454        """
455        Returns the parent select statement.
456        """
457        return self.find_ancestor(Select)

Returns the parent select statement.

same_parent: bool
459    @property
460    def same_parent(self) -> bool:
461        """Returns if the parent is the same class as itself."""
462        return type(self.parent) is self.__class__

Returns if the parent is the same class as itself.

def root(self) -> Expression:
464    def root(self) -> Expression:
465        """
466        Returns the root expression of this tree.
467        """
468        expression = self
469        while expression.parent:
470            expression = expression.parent
471        return expression

Returns the root expression of this tree.

def walk( self, bfs: bool = True, prune: Optional[Callable[[Expression], bool]] = None) -> Iterator[Expression]:
473    def walk(
474        self, bfs: bool = True, prune: t.Optional[t.Callable[[Expression], bool]] = None
475    ) -> t.Iterator[Expression]:
476        """
477        Returns a generator object which visits all nodes in this tree.
478
479        Args:
480            bfs: if set to True the BFS traversal order will be applied,
481                otherwise the DFS traversal will be used instead.
482            prune: callable that returns True if the generator should stop traversing
483                this branch of the tree.
484
485        Returns:
486            the generator object.
487        """
488        if bfs:
489            yield from self.bfs(prune=prune)
490        else:
491            yield from self.dfs(prune=prune)

Returns a generator object which visits all nodes in this tree.

Arguments:
  • bfs: if set to True the BFS traversal order will be applied, otherwise the DFS traversal will be used instead.
  • prune: callable that returns True if the generator should stop traversing this branch of the tree.
Returns:

the generator object.

def dfs( self, prune: Optional[Callable[[Expression], bool]] = None) -> Iterator[Expression]:
493    def dfs(
494        self, prune: t.Optional[t.Callable[[Expression], bool]] = None
495    ) -> t.Iterator[Expression]:
496        """
497        Returns a generator object which visits all nodes in this tree in
498        the DFS (Depth-first) order.
499
500        Returns:
501            The generator object.
502        """
503        stack = [self]
504
505        while stack:
506            node = stack.pop()
507
508            yield node
509
510            if prune and prune(node):
511                continue
512
513            for v in node.iter_expressions(reverse=True):
514                stack.append(v)

Returns a generator object which visits all nodes in this tree in the DFS (Depth-first) order.

Returns:

The generator object.

def bfs( self, prune: Optional[Callable[[Expression], bool]] = None) -> Iterator[Expression]:
516    def bfs(
517        self, prune: t.Optional[t.Callable[[Expression], bool]] = None
518    ) -> t.Iterator[Expression]:
519        """
520        Returns a generator object which visits all nodes in this tree in
521        the BFS (Breadth-first) order.
522
523        Returns:
524            The generator object.
525        """
526        queue = deque([self])
527
528        while queue:
529            node = queue.popleft()
530
531            yield node
532
533            if prune and prune(node):
534                continue
535
536            for v in node.iter_expressions():
537                queue.append(v)

Returns a generator object which visits all nodes in this tree in the BFS (Breadth-first) order.

Returns:

The generator object.

def unnest(self):
539    def unnest(self):
540        """
541        Returns the first non parenthesis child or self.
542        """
543        expression = self
544        while type(expression) is Paren:
545            expression = expression.this
546        return expression

Returns the first non parenthesis child or self.

def unalias(self):
548    def unalias(self):
549        """
550        Returns the inner expression if this is an Alias.
551        """
552        if isinstance(self, Alias):
553            return self.this
554        return self

Returns the inner expression if this is an Alias.

def unnest_operands(self):
556    def unnest_operands(self):
557        """
558        Returns unnested operands as a tuple.
559        """
560        return tuple(arg.unnest() for arg in self.iter_expressions())

Returns unnested operands as a tuple.

def flatten(self, unnest=True):
562    def flatten(self, unnest=True):
563        """
564        Returns a generator which yields child nodes whose parents are the same class.
565
566        A AND B AND C -> [A, B, C]
567        """
568        for node in self.dfs(prune=lambda n: n.parent and type(n) is not self.__class__):
569            if type(node) is not self.__class__:
570                yield node.unnest() if unnest and not isinstance(node, Subquery) else node

Returns a generator which yields child nodes whose parents are the same class.

A AND B AND C -> [A, B, C]

def to_s(self) -> str:
578    def to_s(self) -> str:
579        """
580        Same as __repr__, but includes additional information which can be useful
581        for debugging, like empty or missing args and the AST nodes' object IDs.
582        """
583        return _to_s(self, verbose=True)

Same as __repr__, but includes additional information which can be useful for debugging, like empty or missing args and the AST nodes' object IDs.

def sql( self, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> str:
585    def sql(self, dialect: DialectType = None, **opts) -> str:
586        """
587        Returns SQL string representation of this tree.
588
589        Args:
590            dialect: the dialect of the output SQL string (eg. "spark", "hive", "presto", "mysql").
591            opts: other `sqlglot.generator.Generator` options.
592
593        Returns:
594            The SQL string.
595        """
596        from sqlglot.dialects import Dialect
597
598        return Dialect.get_or_raise(dialect).generate(self, **opts)

Returns SQL string representation of this tree.

Arguments:
  • dialect: the dialect of the output SQL string (eg. "spark", "hive", "presto", "mysql").
  • opts: other sqlglot.generator.Generator options.
Returns:

The SQL string.

def transform( self, fun: Callable, *args: Any, copy: bool = True, **kwargs) -> Expression:
600    def transform(self, fun: t.Callable, *args: t.Any, copy: bool = True, **kwargs) -> Expression:
601        """
602        Visits all tree nodes (excluding already transformed ones)
603        and applies the given transformation function to each node.
604
605        Args:
606            fun: a function which takes a node as an argument and returns a
607                new transformed node or the same node without modifications. If the function
608                returns None, then the corresponding node will be removed from the syntax tree.
609            copy: if set to True a new tree instance is constructed, otherwise the tree is
610                modified in place.
611
612        Returns:
613            The transformed tree.
614        """
615        root = None
616        new_node = None
617
618        for node in (self.copy() if copy else self).dfs(prune=lambda n: n is not new_node):
619            parent, arg_key, index = node.parent, node.arg_key, node.index
620            new_node = fun(node, *args, **kwargs)
621
622            if not root:
623                root = new_node
624            elif new_node is not node:
625                parent.set(arg_key, new_node, index)
626
627        assert root
628        return root.assert_is(Expression)

Visits all tree nodes (excluding already transformed ones) and applies the given transformation function to each node.

Arguments:
  • fun: a function which takes a node as an argument and returns a new transformed node or the same node without modifications. If the function returns None, then the corresponding node will be removed from the syntax tree.
  • copy: if set to True a new tree instance is constructed, otherwise the tree is modified in place.
Returns:

The transformed tree.

def replace(self, expression):
636    def replace(self, expression):
637        """
638        Swap out this expression with a new expression.
639
640        For example::
641
642            >>> tree = Select().select("x").from_("tbl")
643            >>> tree.find(Column).replace(column("y"))
644            Column(
645              this=Identifier(this=y, quoted=False))
646            >>> tree.sql()
647            'SELECT y FROM tbl'
648
649        Args:
650            expression: new node
651
652        Returns:
653            The new expression or expressions.
654        """
655        parent = self.parent
656
657        if not parent or parent is expression:
658            return expression
659
660        key = self.arg_key
661        value = parent.args.get(key)
662
663        if type(expression) is list and isinstance(value, Expression):
664            # We are trying to replace an Expression with a list, so it's assumed that
665            # the intention was to really replace the parent of this expression.
666            value.parent.replace(expression)
667        else:
668            parent.set(key, expression, self.index)
669
670        if expression is not self:
671            self.parent = None
672            self.arg_key = None
673            self.index = None
674
675        return expression

Swap out this expression with a new expression.

For example::

>>> tree = Select().select("x").from_("tbl")
>>> tree.find(Column).replace(column("y"))
Column(
  this=Identifier(this=y, quoted=False))
>>> tree.sql()
'SELECT y FROM tbl'
Arguments:
  • expression: new node
Returns:

The new expression or expressions.

def pop(self: ~E) -> ~E:
677    def pop(self: E) -> E:
678        """
679        Remove this expression from its AST.
680
681        Returns:
682            The popped expression.
683        """
684        self.replace(None)
685        return self

Remove this expression from its AST.

Returns:

The popped expression.

def assert_is(self, type_: Type[~E]) -> ~E:
687    def assert_is(self, type_: t.Type[E]) -> E:
688        """
689        Assert that this `Expression` is an instance of `type_`.
690
691        If it is NOT an instance of `type_`, this raises an assertion error.
692        Otherwise, this returns this expression.
693
694        Examples:
695            This is useful for type security in chained expressions:
696
697            >>> import sqlglot
698            >>> sqlglot.parse_one("SELECT x from y").assert_is(Select).select("z").sql()
699            'SELECT x, z FROM y'
700        """
701        if not isinstance(self, type_):
702            raise AssertionError(f"{self} is not {type_}.")
703        return self

Assert that this Expression is an instance of type_.

If it is NOT an instance of type_, this raises an assertion error. Otherwise, this returns this expression.

Examples:

This is useful for type security in chained expressions:

>>> import sqlglot
>>> sqlglot.parse_one("SELECT x from y").assert_is(Select).select("z").sql()
'SELECT x, z FROM y'
def error_messages(self, args: Optional[Sequence] = None) -> List[str]:
705    def error_messages(self, args: t.Optional[t.Sequence] = None) -> t.List[str]:
706        """
707        Checks if this expression is valid (e.g. all mandatory args are set).
708
709        Args:
710            args: a sequence of values that were used to instantiate a Func expression. This is used
711                to check that the provided arguments don't exceed the function argument limit.
712
713        Returns:
714            A list of error messages for all possible errors that were found.
715        """
716        errors: t.List[str] = []
717
718        for k in self.args:
719            if k not in self.arg_types:
720                errors.append(f"Unexpected keyword: '{k}' for {self.__class__}")
721        for k, mandatory in self.arg_types.items():
722            v = self.args.get(k)
723            if mandatory and (v is None or (isinstance(v, list) and not v)):
724                errors.append(f"Required keyword: '{k}' missing for {self.__class__}")
725
726        if (
727            args
728            and isinstance(self, Func)
729            and len(args) > len(self.arg_types)
730            and not self.is_var_len_args
731        ):
732            errors.append(
733                f"The number of provided arguments ({len(args)}) is greater than "
734                f"the maximum number of supported arguments ({len(self.arg_types)})"
735            )
736
737        return errors

Checks if this expression is valid (e.g. all mandatory args are set).

Arguments:
  • args: a sequence of values that were used to instantiate a Func expression. This is used to check that the provided arguments don't exceed the function argument limit.
Returns:

A list of error messages for all possible errors that were found.

def dump(self):
739    def dump(self):
740        """
741        Dump this Expression to a JSON-serializable dict.
742        """
743        from sqlglot.serde import dump
744
745        return dump(self)

Dump this Expression to a JSON-serializable dict.

@classmethod
def load(cls, obj):
747    @classmethod
748    def load(cls, obj):
749        """
750        Load a dict (as returned by `Expression.dump`) into an Expression instance.
751        """
752        from sqlglot.serde import load
753
754        return load(obj)

Load a dict (as returned by Expression.dump) into an Expression instance.

def and_( self, *expressions: Union[str, Expression, NoneType], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Condition:
756    def and_(
757        self,
758        *expressions: t.Optional[ExpOrStr],
759        dialect: DialectType = None,
760        copy: bool = True,
761        **opts,
762    ) -> Condition:
763        """
764        AND this condition with one or multiple expressions.
765
766        Example:
767            >>> condition("x=1").and_("y=1").sql()
768            'x = 1 AND y = 1'
769
770        Args:
771            *expressions: the SQL code strings to parse.
772                If an `Expression` instance is passed, it will be used as-is.
773            dialect: the dialect used to parse the input expression.
774            copy: whether to copy the involved expressions (only applies to Expressions).
775            opts: other options to use to parse the input expressions.
776
777        Returns:
778            The new And condition.
779        """
780        return and_(self, *expressions, dialect=dialect, copy=copy, **opts)

AND this condition with one or multiple expressions.

Example:
>>> condition("x=1").and_("y=1").sql()
'x = 1 AND y = 1'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy the involved expressions (only applies to Expressions).
  • opts: other options to use to parse the input expressions.
Returns:

The new And condition.

def or_( self, *expressions: Union[str, Expression, NoneType], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Condition:
782    def or_(
783        self,
784        *expressions: t.Optional[ExpOrStr],
785        dialect: DialectType = None,
786        copy: bool = True,
787        **opts,
788    ) -> Condition:
789        """
790        OR this condition with one or multiple expressions.
791
792        Example:
793            >>> condition("x=1").or_("y=1").sql()
794            'x = 1 OR y = 1'
795
796        Args:
797            *expressions: the SQL code strings to parse.
798                If an `Expression` instance is passed, it will be used as-is.
799            dialect: the dialect used to parse the input expression.
800            copy: whether to copy the involved expressions (only applies to Expressions).
801            opts: other options to use to parse the input expressions.
802
803        Returns:
804            The new Or condition.
805        """
806        return or_(self, *expressions, dialect=dialect, copy=copy, **opts)

OR this condition with one or multiple expressions.

Example:
>>> condition("x=1").or_("y=1").sql()
'x = 1 OR y = 1'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy the involved expressions (only applies to Expressions).
  • opts: other options to use to parse the input expressions.
Returns:

The new Or condition.

def not_(self, copy: bool = True):
808    def not_(self, copy: bool = True):
809        """
810        Wrap this condition with NOT.
811
812        Example:
813            >>> condition("x=1").not_().sql()
814            'NOT x = 1'
815
816        Args:
817            copy: whether to copy this object.
818
819        Returns:
820            The new Not instance.
821        """
822        return not_(self, copy=copy)

Wrap this condition with NOT.

Example:
>>> condition("x=1").not_().sql()
'NOT x = 1'
Arguments:
  • copy: whether to copy this object.
Returns:

The new Not instance.

def as_( self, alias: str | Identifier, quoted: Optional[bool] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Alias:
824    def as_(
825        self,
826        alias: str | Identifier,
827        quoted: t.Optional[bool] = None,
828        dialect: DialectType = None,
829        copy: bool = True,
830        **opts,
831    ) -> Alias:
832        return alias_(self, alias, quoted=quoted, dialect=dialect, copy=copy, **opts)
def isin( self, *expressions: Any, query: Union[str, Expression, NoneType] = None, unnest: Union[str, Expression, NoneType, Collection[Union[str, Expression]]] = None, copy: bool = True, **opts) -> In:
857    def isin(
858        self,
859        *expressions: t.Any,
860        query: t.Optional[ExpOrStr] = None,
861        unnest: t.Optional[ExpOrStr] | t.Collection[ExpOrStr] = None,
862        copy: bool = True,
863        **opts,
864    ) -> In:
865        subquery = maybe_parse(query, copy=copy, **opts) if query else None
866        if subquery and not isinstance(subquery, Subquery):
867            subquery = subquery.subquery(copy=False)
868
869        return In(
870            this=maybe_copy(self, copy),
871            expressions=[convert(e, copy=copy) for e in expressions],
872            query=subquery,
873            unnest=(
874                Unnest(
875                    expressions=[
876                        maybe_parse(t.cast(ExpOrStr, e), copy=copy, **opts)
877                        for e in ensure_list(unnest)
878                    ]
879                )
880                if unnest
881                else None
882            ),
883        )
def between( self, low: Any, high: Any, copy: bool = True, **opts) -> Between:
885    def between(self, low: t.Any, high: t.Any, copy: bool = True, **opts) -> Between:
886        return Between(
887            this=maybe_copy(self, copy),
888            low=convert(low, copy=copy, **opts),
889            high=convert(high, copy=copy, **opts),
890        )
def is_( self, other: Union[str, Expression]) -> Is:
892    def is_(self, other: ExpOrStr) -> Is:
893        return self._binop(Is, other)
def like( self, other: Union[str, Expression]) -> Like:
895    def like(self, other: ExpOrStr) -> Like:
896        return self._binop(Like, other)
def ilike( self, other: Union[str, Expression]) -> ILike:
898    def ilike(self, other: ExpOrStr) -> ILike:
899        return self._binop(ILike, other)
def eq(self, other: Any) -> EQ:
901    def eq(self, other: t.Any) -> EQ:
902        return self._binop(EQ, other)
def neq(self, other: Any) -> NEQ:
904    def neq(self, other: t.Any) -> NEQ:
905        return self._binop(NEQ, other)
def rlike( self, other: Union[str, Expression]) -> RegexpLike:
907    def rlike(self, other: ExpOrStr) -> RegexpLike:
908        return self._binop(RegexpLike, other)
def div( self, other: Union[str, Expression], typed: bool = False, safe: bool = False) -> Div:
910    def div(self, other: ExpOrStr, typed: bool = False, safe: bool = False) -> Div:
911        div = self._binop(Div, other)
912        div.args["typed"] = typed
913        div.args["safe"] = safe
914        return div
def asc(self, nulls_first: bool = True) -> Ordered:
916    def asc(self, nulls_first: bool = True) -> Ordered:
917        return Ordered(this=self.copy(), nulls_first=nulls_first)
def desc(self, nulls_first: bool = False) -> Ordered:
919    def desc(self, nulls_first: bool = False) -> Ordered:
920        return Ordered(this=self.copy(), desc=True, nulls_first=nulls_first)
IntoType = typing.Union[str, typing.Type[Expression], typing.Collection[typing.Union[str, typing.Type[Expression]]]]
ExpOrStr = typing.Union[str, Expression]
class Condition(Expression):
1003class Condition(Expression):
1004    """Logical conditions like x AND y, or simply x"""

Logical conditions like x AND y, or simply x

key = 'condition'
class Predicate(Condition):
1007class Predicate(Condition):
1008    """Relationships like x = y, x > 1, x >= y."""

Relationships like x = y, x > 1, x >= y.

key = 'predicate'
class DerivedTable(Expression):
1011class DerivedTable(Expression):
1012    @property
1013    def selects(self) -> t.List[Expression]:
1014        return self.this.selects if isinstance(self.this, Query) else []
1015
1016    @property
1017    def named_selects(self) -> t.List[str]:
1018        return [select.output_name for select in self.selects]
selects: List[Expression]
1012    @property
1013    def selects(self) -> t.List[Expression]:
1014        return self.this.selects if isinstance(self.this, Query) else []
named_selects: List[str]
1016    @property
1017    def named_selects(self) -> t.List[str]:
1018        return [select.output_name for select in self.selects]
key = 'derivedtable'
class Query(Expression):
1021class Query(Expression):
1022    def subquery(self, alias: t.Optional[ExpOrStr] = None, copy: bool = True) -> Subquery:
1023        """
1024        Returns a `Subquery` that wraps around this query.
1025
1026        Example:
1027            >>> subquery = Select().select("x").from_("tbl").subquery()
1028            >>> Select().select("x").from_(subquery).sql()
1029            'SELECT x FROM (SELECT x FROM tbl)'
1030
1031        Args:
1032            alias: an optional alias for the subquery.
1033            copy: if `False`, modify this expression instance in-place.
1034        """
1035        instance = maybe_copy(self, copy)
1036        if not isinstance(alias, Expression):
1037            alias = TableAlias(this=to_identifier(alias)) if alias else None
1038
1039        return Subquery(this=instance, alias=alias)
1040
1041    def limit(
1042        self: Q, expression: ExpOrStr | int, dialect: DialectType = None, copy: bool = True, **opts
1043    ) -> Q:
1044        """
1045        Adds a LIMIT clause to this query.
1046
1047        Example:
1048            >>> select("1").union(select("1")).limit(1).sql()
1049            'SELECT 1 UNION SELECT 1 LIMIT 1'
1050
1051        Args:
1052            expression: the SQL code string to parse.
1053                This can also be an integer.
1054                If a `Limit` instance is passed, it will be used as-is.
1055                If another `Expression` instance is passed, it will be wrapped in a `Limit`.
1056            dialect: the dialect used to parse the input expression.
1057            copy: if `False`, modify this expression instance in-place.
1058            opts: other options to use to parse the input expressions.
1059
1060        Returns:
1061            A limited Select expression.
1062        """
1063        return _apply_builder(
1064            expression=expression,
1065            instance=self,
1066            arg="limit",
1067            into=Limit,
1068            prefix="LIMIT",
1069            dialect=dialect,
1070            copy=copy,
1071            into_arg="expression",
1072            **opts,
1073        )
1074
1075    def offset(
1076        self: Q, expression: ExpOrStr | int, dialect: DialectType = None, copy: bool = True, **opts
1077    ) -> Q:
1078        """
1079        Set the OFFSET expression.
1080
1081        Example:
1082            >>> Select().from_("tbl").select("x").offset(10).sql()
1083            'SELECT x FROM tbl OFFSET 10'
1084
1085        Args:
1086            expression: the SQL code string to parse.
1087                This can also be an integer.
1088                If a `Offset` instance is passed, this is used as-is.
1089                If another `Expression` instance is passed, it will be wrapped in a `Offset`.
1090            dialect: the dialect used to parse the input expression.
1091            copy: if `False`, modify this expression instance in-place.
1092            opts: other options to use to parse the input expressions.
1093
1094        Returns:
1095            The modified Select expression.
1096        """
1097        return _apply_builder(
1098            expression=expression,
1099            instance=self,
1100            arg="offset",
1101            into=Offset,
1102            prefix="OFFSET",
1103            dialect=dialect,
1104            copy=copy,
1105            into_arg="expression",
1106            **opts,
1107        )
1108
1109    def order_by(
1110        self: Q,
1111        *expressions: t.Optional[ExpOrStr],
1112        append: bool = True,
1113        dialect: DialectType = None,
1114        copy: bool = True,
1115        **opts,
1116    ) -> Q:
1117        """
1118        Set the ORDER BY expression.
1119
1120        Example:
1121            >>> Select().from_("tbl").select("x").order_by("x DESC").sql()
1122            'SELECT x FROM tbl ORDER BY x DESC'
1123
1124        Args:
1125            *expressions: the SQL code strings to parse.
1126                If a `Group` instance is passed, this is used as-is.
1127                If another `Expression` instance is passed, it will be wrapped in a `Order`.
1128            append: if `True`, add to any existing expressions.
1129                Otherwise, this flattens all the `Order` expression into a single expression.
1130            dialect: the dialect used to parse the input expression.
1131            copy: if `False`, modify this expression instance in-place.
1132            opts: other options to use to parse the input expressions.
1133
1134        Returns:
1135            The modified Select expression.
1136        """
1137        return _apply_child_list_builder(
1138            *expressions,
1139            instance=self,
1140            arg="order",
1141            append=append,
1142            copy=copy,
1143            prefix="ORDER BY",
1144            into=Order,
1145            dialect=dialect,
1146            **opts,
1147        )
1148
1149    @property
1150    def ctes(self) -> t.List[CTE]:
1151        """Returns a list of all the CTEs attached to this query."""
1152        with_ = self.args.get("with")
1153        return with_.expressions if with_ else []
1154
1155    @property
1156    def selects(self) -> t.List[Expression]:
1157        """Returns the query's projections."""
1158        raise NotImplementedError("Query objects must implement `selects`")
1159
1160    @property
1161    def named_selects(self) -> t.List[str]:
1162        """Returns the output names of the query's projections."""
1163        raise NotImplementedError("Query objects must implement `named_selects`")
1164
1165    def select(
1166        self: Q,
1167        *expressions: t.Optional[ExpOrStr],
1168        append: bool = True,
1169        dialect: DialectType = None,
1170        copy: bool = True,
1171        **opts,
1172    ) -> Q:
1173        """
1174        Append to or set the SELECT expressions.
1175
1176        Example:
1177            >>> Select().select("x", "y").sql()
1178            'SELECT x, y'
1179
1180        Args:
1181            *expressions: the SQL code strings to parse.
1182                If an `Expression` instance is passed, it will be used as-is.
1183            append: if `True`, add to any existing expressions.
1184                Otherwise, this resets the expressions.
1185            dialect: the dialect used to parse the input expressions.
1186            copy: if `False`, modify this expression instance in-place.
1187            opts: other options to use to parse the input expressions.
1188
1189        Returns:
1190            The modified Query expression.
1191        """
1192        raise NotImplementedError("Query objects must implement `select`")
1193
1194    def with_(
1195        self: Q,
1196        alias: ExpOrStr,
1197        as_: ExpOrStr,
1198        recursive: t.Optional[bool] = None,
1199        append: bool = True,
1200        dialect: DialectType = None,
1201        copy: bool = True,
1202        **opts,
1203    ) -> Q:
1204        """
1205        Append to or set the common table expressions.
1206
1207        Example:
1208            >>> Select().with_("tbl2", as_="SELECT * FROM tbl").select("x").from_("tbl2").sql()
1209            'WITH tbl2 AS (SELECT * FROM tbl) SELECT x FROM tbl2'
1210
1211        Args:
1212            alias: the SQL code string to parse as the table name.
1213                If an `Expression` instance is passed, this is used as-is.
1214            as_: the SQL code string to parse as the table expression.
1215                If an `Expression` instance is passed, it will be used as-is.
1216            recursive: set the RECURSIVE part of the expression. Defaults to `False`.
1217            append: if `True`, add to any existing expressions.
1218                Otherwise, this resets the expressions.
1219            dialect: the dialect used to parse the input expression.
1220            copy: if `False`, modify this expression instance in-place.
1221            opts: other options to use to parse the input expressions.
1222
1223        Returns:
1224            The modified expression.
1225        """
1226        return _apply_cte_builder(
1227            self, alias, as_, recursive=recursive, append=append, dialect=dialect, copy=copy, **opts
1228        )
1229
1230    def union(
1231        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1232    ) -> Union:
1233        """
1234        Builds a UNION expression.
1235
1236        Example:
1237            >>> import sqlglot
1238            >>> sqlglot.parse_one("SELECT * FROM foo").union("SELECT * FROM bla").sql()
1239            'SELECT * FROM foo UNION SELECT * FROM bla'
1240
1241        Args:
1242            expression: the SQL code string.
1243                If an `Expression` instance is passed, it will be used as-is.
1244            distinct: set the DISTINCT flag if and only if this is true.
1245            dialect: the dialect used to parse the input expression.
1246            opts: other options to use to parse the input expressions.
1247
1248        Returns:
1249            The new Union expression.
1250        """
1251        return union(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)
1252
1253    def intersect(
1254        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1255    ) -> Intersect:
1256        """
1257        Builds an INTERSECT expression.
1258
1259        Example:
1260            >>> import sqlglot
1261            >>> sqlglot.parse_one("SELECT * FROM foo").intersect("SELECT * FROM bla").sql()
1262            'SELECT * FROM foo INTERSECT SELECT * FROM bla'
1263
1264        Args:
1265            expression: the SQL code string.
1266                If an `Expression` instance is passed, it will be used as-is.
1267            distinct: set the DISTINCT flag if and only if this is true.
1268            dialect: the dialect used to parse the input expression.
1269            opts: other options to use to parse the input expressions.
1270
1271        Returns:
1272            The new Intersect expression.
1273        """
1274        return intersect(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)
1275
1276    def except_(
1277        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1278    ) -> Except:
1279        """
1280        Builds an EXCEPT expression.
1281
1282        Example:
1283            >>> import sqlglot
1284            >>> sqlglot.parse_one("SELECT * FROM foo").except_("SELECT * FROM bla").sql()
1285            'SELECT * FROM foo EXCEPT SELECT * FROM bla'
1286
1287        Args:
1288            expression: the SQL code string.
1289                If an `Expression` instance is passed, it will be used as-is.
1290            distinct: set the DISTINCT flag if and only if this is true.
1291            dialect: the dialect used to parse the input expression.
1292            opts: other options to use to parse the input expressions.
1293
1294        Returns:
1295            The new Except expression.
1296        """
1297        return except_(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)
def subquery( self, alias: Union[str, Expression, NoneType] = None, copy: bool = True) -> Subquery:
1022    def subquery(self, alias: t.Optional[ExpOrStr] = None, copy: bool = True) -> Subquery:
1023        """
1024        Returns a `Subquery` that wraps around this query.
1025
1026        Example:
1027            >>> subquery = Select().select("x").from_("tbl").subquery()
1028            >>> Select().select("x").from_(subquery).sql()
1029            'SELECT x FROM (SELECT x FROM tbl)'
1030
1031        Args:
1032            alias: an optional alias for the subquery.
1033            copy: if `False`, modify this expression instance in-place.
1034        """
1035        instance = maybe_copy(self, copy)
1036        if not isinstance(alias, Expression):
1037            alias = TableAlias(this=to_identifier(alias)) if alias else None
1038
1039        return Subquery(this=instance, alias=alias)

Returns a Subquery that wraps around this query.

Example:
>>> subquery = Select().select("x").from_("tbl").subquery()
>>> Select().select("x").from_(subquery).sql()
'SELECT x FROM (SELECT x FROM tbl)'
Arguments:
  • alias: an optional alias for the subquery.
  • copy: if False, modify this expression instance in-place.
def limit( self: ~Q, expression: Union[str, Expression, int], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> ~Q:
1041    def limit(
1042        self: Q, expression: ExpOrStr | int, dialect: DialectType = None, copy: bool = True, **opts
1043    ) -> Q:
1044        """
1045        Adds a LIMIT clause to this query.
1046
1047        Example:
1048            >>> select("1").union(select("1")).limit(1).sql()
1049            'SELECT 1 UNION SELECT 1 LIMIT 1'
1050
1051        Args:
1052            expression: the SQL code string to parse.
1053                This can also be an integer.
1054                If a `Limit` instance is passed, it will be used as-is.
1055                If another `Expression` instance is passed, it will be wrapped in a `Limit`.
1056            dialect: the dialect used to parse the input expression.
1057            copy: if `False`, modify this expression instance in-place.
1058            opts: other options to use to parse the input expressions.
1059
1060        Returns:
1061            A limited Select expression.
1062        """
1063        return _apply_builder(
1064            expression=expression,
1065            instance=self,
1066            arg="limit",
1067            into=Limit,
1068            prefix="LIMIT",
1069            dialect=dialect,
1070            copy=copy,
1071            into_arg="expression",
1072            **opts,
1073        )

Adds a LIMIT clause to this query.

Example:
>>> select("1").union(select("1")).limit(1).sql()
'SELECT 1 UNION SELECT 1 LIMIT 1'
Arguments:
  • expression: the SQL code string to parse. This can also be an integer. If a Limit instance is passed, it will be used as-is. If another Expression instance is passed, it will be wrapped in a Limit.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

A limited Select expression.

def offset( self: ~Q, expression: Union[str, Expression, int], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> ~Q:
1075    def offset(
1076        self: Q, expression: ExpOrStr | int, dialect: DialectType = None, copy: bool = True, **opts
1077    ) -> Q:
1078        """
1079        Set the OFFSET expression.
1080
1081        Example:
1082            >>> Select().from_("tbl").select("x").offset(10).sql()
1083            'SELECT x FROM tbl OFFSET 10'
1084
1085        Args:
1086            expression: the SQL code string to parse.
1087                This can also be an integer.
1088                If a `Offset` instance is passed, this is used as-is.
1089                If another `Expression` instance is passed, it will be wrapped in a `Offset`.
1090            dialect: the dialect used to parse the input expression.
1091            copy: if `False`, modify this expression instance in-place.
1092            opts: other options to use to parse the input expressions.
1093
1094        Returns:
1095            The modified Select expression.
1096        """
1097        return _apply_builder(
1098            expression=expression,
1099            instance=self,
1100            arg="offset",
1101            into=Offset,
1102            prefix="OFFSET",
1103            dialect=dialect,
1104            copy=copy,
1105            into_arg="expression",
1106            **opts,
1107        )

Set the OFFSET expression.

Example:
>>> Select().from_("tbl").select("x").offset(10).sql()
'SELECT x FROM tbl OFFSET 10'
Arguments:
  • expression: the SQL code string to parse. This can also be an integer. If a Offset instance is passed, this is used as-is. If another Expression instance is passed, it will be wrapped in a Offset.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Select expression.

def order_by( self: ~Q, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> ~Q:
1109    def order_by(
1110        self: Q,
1111        *expressions: t.Optional[ExpOrStr],
1112        append: bool = True,
1113        dialect: DialectType = None,
1114        copy: bool = True,
1115        **opts,
1116    ) -> Q:
1117        """
1118        Set the ORDER BY expression.
1119
1120        Example:
1121            >>> Select().from_("tbl").select("x").order_by("x DESC").sql()
1122            'SELECT x FROM tbl ORDER BY x DESC'
1123
1124        Args:
1125            *expressions: the SQL code strings to parse.
1126                If a `Group` instance is passed, this is used as-is.
1127                If another `Expression` instance is passed, it will be wrapped in a `Order`.
1128            append: if `True`, add to any existing expressions.
1129                Otherwise, this flattens all the `Order` expression into a single expression.
1130            dialect: the dialect used to parse the input expression.
1131            copy: if `False`, modify this expression instance in-place.
1132            opts: other options to use to parse the input expressions.
1133
1134        Returns:
1135            The modified Select expression.
1136        """
1137        return _apply_child_list_builder(
1138            *expressions,
1139            instance=self,
1140            arg="order",
1141            append=append,
1142            copy=copy,
1143            prefix="ORDER BY",
1144            into=Order,
1145            dialect=dialect,
1146            **opts,
1147        )

Set the ORDER BY expression.

Example:
>>> Select().from_("tbl").select("x").order_by("x DESC").sql()
'SELECT x FROM tbl ORDER BY x DESC'
Arguments:
  • *expressions: the SQL code strings to parse. If a Group instance is passed, this is used as-is. If another Expression instance is passed, it will be wrapped in a Order.
  • append: if True, add to any existing expressions. Otherwise, this flattens all the Order expression into a single expression.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Select expression.

ctes: List[CTE]
1149    @property
1150    def ctes(self) -> t.List[CTE]:
1151        """Returns a list of all the CTEs attached to this query."""
1152        with_ = self.args.get("with")
1153        return with_.expressions if with_ else []

Returns a list of all the CTEs attached to this query.

selects: List[Expression]
1155    @property
1156    def selects(self) -> t.List[Expression]:
1157        """Returns the query's projections."""
1158        raise NotImplementedError("Query objects must implement `selects`")

Returns the query's projections.

named_selects: List[str]
1160    @property
1161    def named_selects(self) -> t.List[str]:
1162        """Returns the output names of the query's projections."""
1163        raise NotImplementedError("Query objects must implement `named_selects`")

Returns the output names of the query's projections.

def select( self: ~Q, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> ~Q:
1165    def select(
1166        self: Q,
1167        *expressions: t.Optional[ExpOrStr],
1168        append: bool = True,
1169        dialect: DialectType = None,
1170        copy: bool = True,
1171        **opts,
1172    ) -> Q:
1173        """
1174        Append to or set the SELECT expressions.
1175
1176        Example:
1177            >>> Select().select("x", "y").sql()
1178            'SELECT x, y'
1179
1180        Args:
1181            *expressions: the SQL code strings to parse.
1182                If an `Expression` instance is passed, it will be used as-is.
1183            append: if `True`, add to any existing expressions.
1184                Otherwise, this resets the expressions.
1185            dialect: the dialect used to parse the input expressions.
1186            copy: if `False`, modify this expression instance in-place.
1187            opts: other options to use to parse the input expressions.
1188
1189        Returns:
1190            The modified Query expression.
1191        """
1192        raise NotImplementedError("Query objects must implement `select`")

Append to or set the SELECT expressions.

Example:
>>> Select().select("x", "y").sql()
'SELECT x, y'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • append: if True, add to any existing expressions. Otherwise, this resets the expressions.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Query expression.

def with_( self: ~Q, alias: Union[str, Expression], as_: Union[str, Expression], recursive: Optional[bool] = None, append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> ~Q:
1194    def with_(
1195        self: Q,
1196        alias: ExpOrStr,
1197        as_: ExpOrStr,
1198        recursive: t.Optional[bool] = None,
1199        append: bool = True,
1200        dialect: DialectType = None,
1201        copy: bool = True,
1202        **opts,
1203    ) -> Q:
1204        """
1205        Append to or set the common table expressions.
1206
1207        Example:
1208            >>> Select().with_("tbl2", as_="SELECT * FROM tbl").select("x").from_("tbl2").sql()
1209            'WITH tbl2 AS (SELECT * FROM tbl) SELECT x FROM tbl2'
1210
1211        Args:
1212            alias: the SQL code string to parse as the table name.
1213                If an `Expression` instance is passed, this is used as-is.
1214            as_: the SQL code string to parse as the table expression.
1215                If an `Expression` instance is passed, it will be used as-is.
1216            recursive: set the RECURSIVE part of the expression. Defaults to `False`.
1217            append: if `True`, add to any existing expressions.
1218                Otherwise, this resets the expressions.
1219            dialect: the dialect used to parse the input expression.
1220            copy: if `False`, modify this expression instance in-place.
1221            opts: other options to use to parse the input expressions.
1222
1223        Returns:
1224            The modified expression.
1225        """
1226        return _apply_cte_builder(
1227            self, alias, as_, recursive=recursive, append=append, dialect=dialect, copy=copy, **opts
1228        )

Append to or set the common table expressions.

Example:
>>> Select().with_("tbl2", as_="SELECT * FROM tbl").select("x").from_("tbl2").sql()
'WITH tbl2 AS (SELECT * FROM tbl) SELECT x FROM tbl2'
Arguments:
  • alias: the SQL code string to parse as the table name. If an Expression instance is passed, this is used as-is.
  • as_: the SQL code string to parse as the table expression. If an Expression instance is passed, it will be used as-is.
  • recursive: set the RECURSIVE part of the expression. Defaults to False.
  • append: if True, add to any existing expressions. Otherwise, this resets the expressions.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified expression.

def union( self, expression: Union[str, Expression], distinct: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> Union:
1230    def union(
1231        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1232    ) -> Union:
1233        """
1234        Builds a UNION expression.
1235
1236        Example:
1237            >>> import sqlglot
1238            >>> sqlglot.parse_one("SELECT * FROM foo").union("SELECT * FROM bla").sql()
1239            'SELECT * FROM foo UNION SELECT * FROM bla'
1240
1241        Args:
1242            expression: the SQL code string.
1243                If an `Expression` instance is passed, it will be used as-is.
1244            distinct: set the DISTINCT flag if and only if this is true.
1245            dialect: the dialect used to parse the input expression.
1246            opts: other options to use to parse the input expressions.
1247
1248        Returns:
1249            The new Union expression.
1250        """
1251        return union(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)

Builds a UNION expression.

Example:
>>> import sqlglot
>>> sqlglot.parse_one("SELECT * FROM foo").union("SELECT * FROM bla").sql()
'SELECT * FROM foo UNION SELECT * FROM bla'
Arguments:
  • expression: the SQL code string. If an Expression instance is passed, it will be used as-is.
  • distinct: set the DISTINCT flag if and only if this is true.
  • dialect: the dialect used to parse the input expression.
  • opts: other options to use to parse the input expressions.
Returns:

The new Union expression.

def intersect( self, expression: Union[str, Expression], distinct: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> Intersect:
1253    def intersect(
1254        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1255    ) -> Intersect:
1256        """
1257        Builds an INTERSECT expression.
1258
1259        Example:
1260            >>> import sqlglot
1261            >>> sqlglot.parse_one("SELECT * FROM foo").intersect("SELECT * FROM bla").sql()
1262            'SELECT * FROM foo INTERSECT SELECT * FROM bla'
1263
1264        Args:
1265            expression: the SQL code string.
1266                If an `Expression` instance is passed, it will be used as-is.
1267            distinct: set the DISTINCT flag if and only if this is true.
1268            dialect: the dialect used to parse the input expression.
1269            opts: other options to use to parse the input expressions.
1270
1271        Returns:
1272            The new Intersect expression.
1273        """
1274        return intersect(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)

Builds an INTERSECT expression.

Example:
>>> import sqlglot
>>> sqlglot.parse_one("SELECT * FROM foo").intersect("SELECT * FROM bla").sql()
'SELECT * FROM foo INTERSECT SELECT * FROM bla'
Arguments:
  • expression: the SQL code string. If an Expression instance is passed, it will be used as-is.
  • distinct: set the DISTINCT flag if and only if this is true.
  • dialect: the dialect used to parse the input expression.
  • opts: other options to use to parse the input expressions.
Returns:

The new Intersect expression.

def except_( self, expression: Union[str, Expression], distinct: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> Except:
1276    def except_(
1277        self, expression: ExpOrStr, distinct: bool = True, dialect: DialectType = None, **opts
1278    ) -> Except:
1279        """
1280        Builds an EXCEPT expression.
1281
1282        Example:
1283            >>> import sqlglot
1284            >>> sqlglot.parse_one("SELECT * FROM foo").except_("SELECT * FROM bla").sql()
1285            'SELECT * FROM foo EXCEPT SELECT * FROM bla'
1286
1287        Args:
1288            expression: the SQL code string.
1289                If an `Expression` instance is passed, it will be used as-is.
1290            distinct: set the DISTINCT flag if and only if this is true.
1291            dialect: the dialect used to parse the input expression.
1292            opts: other options to use to parse the input expressions.
1293
1294        Returns:
1295            The new Except expression.
1296        """
1297        return except_(left=self, right=expression, distinct=distinct, dialect=dialect, **opts)

Builds an EXCEPT expression.

Example:
>>> import sqlglot
>>> sqlglot.parse_one("SELECT * FROM foo").except_("SELECT * FROM bla").sql()
'SELECT * FROM foo EXCEPT SELECT * FROM bla'
Arguments:
  • expression: the SQL code string. If an Expression instance is passed, it will be used as-is.
  • distinct: set the DISTINCT flag if and only if this is true.
  • dialect: the dialect used to parse the input expression.
  • opts: other options to use to parse the input expressions.
Returns:

The new Except expression.

key = 'query'
class UDTF(DerivedTable):
1300class UDTF(DerivedTable):
1301    @property
1302    def selects(self) -> t.List[Expression]:
1303        alias = self.args.get("alias")
1304        return alias.columns if alias else []
selects: List[Expression]
1301    @property
1302    def selects(self) -> t.List[Expression]:
1303        alias = self.args.get("alias")
1304        return alias.columns if alias else []
key = 'udtf'
class Cache(Expression):
1307class Cache(Expression):
1308    arg_types = {
1309        "this": True,
1310        "lazy": False,
1311        "options": False,
1312        "expression": False,
1313    }
arg_types = {'this': True, 'lazy': False, 'options': False, 'expression': False}
key = 'cache'
class Uncache(Expression):
1316class Uncache(Expression):
1317    arg_types = {"this": True, "exists": False}
arg_types = {'this': True, 'exists': False}
key = 'uncache'
class Refresh(Expression):
1320class Refresh(Expression):
1321    pass
key = 'refresh'
class DDL(Expression):
1324class DDL(Expression):
1325    @property
1326    def ctes(self) -> t.List[CTE]:
1327        """Returns a list of all the CTEs attached to this statement."""
1328        with_ = self.args.get("with")
1329        return with_.expressions if with_ else []
1330
1331    @property
1332    def selects(self) -> t.List[Expression]:
1333        """If this statement contains a query (e.g. a CTAS), this returns the query's projections."""
1334        return self.expression.selects if isinstance(self.expression, Query) else []
1335
1336    @property
1337    def named_selects(self) -> t.List[str]:
1338        """
1339        If this statement contains a query (e.g. a CTAS), this returns the output
1340        names of the query's projections.
1341        """
1342        return self.expression.named_selects if isinstance(self.expression, Query) else []
ctes: List[CTE]
1325    @property
1326    def ctes(self) -> t.List[CTE]:
1327        """Returns a list of all the CTEs attached to this statement."""
1328        with_ = self.args.get("with")
1329        return with_.expressions if with_ else []

Returns a list of all the CTEs attached to this statement.

selects: List[Expression]
1331    @property
1332    def selects(self) -> t.List[Expression]:
1333        """If this statement contains a query (e.g. a CTAS), this returns the query's projections."""
1334        return self.expression.selects if isinstance(self.expression, Query) else []

If this statement contains a query (e.g. a CTAS), this returns the query's projections.

named_selects: List[str]
1336    @property
1337    def named_selects(self) -> t.List[str]:
1338        """
1339        If this statement contains a query (e.g. a CTAS), this returns the output
1340        names of the query's projections.
1341        """
1342        return self.expression.named_selects if isinstance(self.expression, Query) else []

If this statement contains a query (e.g. a CTAS), this returns the output names of the query's projections.

key = 'ddl'
class DML(Expression):
1345class DML(Expression):
1346    def returning(
1347        self,
1348        expression: ExpOrStr,
1349        dialect: DialectType = None,
1350        copy: bool = True,
1351        **opts,
1352    ) -> DML:
1353        """
1354        Set the RETURNING expression. Not supported by all dialects.
1355
1356        Example:
1357            >>> delete("tbl").returning("*", dialect="postgres").sql()
1358            'DELETE FROM tbl RETURNING *'
1359
1360        Args:
1361            expression: the SQL code strings to parse.
1362                If an `Expression` instance is passed, it will be used as-is.
1363            dialect: the dialect used to parse the input expressions.
1364            copy: if `False`, modify this expression instance in-place.
1365            opts: other options to use to parse the input expressions.
1366
1367        Returns:
1368            Delete: the modified expression.
1369        """
1370        return _apply_builder(
1371            expression=expression,
1372            instance=self,
1373            arg="returning",
1374            prefix="RETURNING",
1375            dialect=dialect,
1376            copy=copy,
1377            into=Returning,
1378            **opts,
1379        )
def returning( self, expression: Union[str, Expression], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> DML:
1346    def returning(
1347        self,
1348        expression: ExpOrStr,
1349        dialect: DialectType = None,
1350        copy: bool = True,
1351        **opts,
1352    ) -> DML:
1353        """
1354        Set the RETURNING expression. Not supported by all dialects.
1355
1356        Example:
1357            >>> delete("tbl").returning("*", dialect="postgres").sql()
1358            'DELETE FROM tbl RETURNING *'
1359
1360        Args:
1361            expression: the SQL code strings to parse.
1362                If an `Expression` instance is passed, it will be used as-is.
1363            dialect: the dialect used to parse the input expressions.
1364            copy: if `False`, modify this expression instance in-place.
1365            opts: other options to use to parse the input expressions.
1366
1367        Returns:
1368            Delete: the modified expression.
1369        """
1370        return _apply_builder(
1371            expression=expression,
1372            instance=self,
1373            arg="returning",
1374            prefix="RETURNING",
1375            dialect=dialect,
1376            copy=copy,
1377            into=Returning,
1378            **opts,
1379        )

Set the RETURNING expression. Not supported by all dialects.

Example:
>>> delete("tbl").returning("*", dialect="postgres").sql()
'DELETE FROM tbl RETURNING *'
Arguments:
  • expression: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

Delete: the modified expression.

key = 'dml'
class Create(DDL):
1382class Create(DDL):
1383    arg_types = {
1384        "with": False,
1385        "this": True,
1386        "kind": True,
1387        "expression": False,
1388        "exists": False,
1389        "properties": False,
1390        "replace": False,
1391        "unique": False,
1392        "indexes": False,
1393        "no_schema_binding": False,
1394        "begin": False,
1395        "end": False,
1396        "clone": False,
1397    }
1398
1399    @property
1400    def kind(self) -> t.Optional[str]:
1401        kind = self.args.get("kind")
1402        return kind and kind.upper()
arg_types = {'with': False, 'this': True, 'kind': True, 'expression': False, 'exists': False, 'properties': False, 'replace': False, 'unique': False, 'indexes': False, 'no_schema_binding': False, 'begin': False, 'end': False, 'clone': False}
kind: Optional[str]
1399    @property
1400    def kind(self) -> t.Optional[str]:
1401        kind = self.args.get("kind")
1402        return kind and kind.upper()
key = 'create'
class SequenceProperties(Expression):
1405class SequenceProperties(Expression):
1406    arg_types = {
1407        "increment": False,
1408        "minvalue": False,
1409        "maxvalue": False,
1410        "cache": False,
1411        "start": False,
1412        "owned": False,
1413        "options": False,
1414    }
arg_types = {'increment': False, 'minvalue': False, 'maxvalue': False, 'cache': False, 'start': False, 'owned': False, 'options': False}
key = 'sequenceproperties'
class TruncateTable(Expression):
1417class TruncateTable(Expression):
1418    arg_types = {
1419        "expressions": True,
1420        "is_database": False,
1421        "exists": False,
1422        "only": False,
1423        "cluster": False,
1424        "identity": False,
1425        "option": False,
1426        "partition": False,
1427    }
arg_types = {'expressions': True, 'is_database': False, 'exists': False, 'only': False, 'cluster': False, 'identity': False, 'option': False, 'partition': False}
key = 'truncatetable'
class Clone(Expression):
1433class Clone(Expression):
1434    arg_types = {"this": True, "shallow": False, "copy": False}
arg_types = {'this': True, 'shallow': False, 'copy': False}
key = 'clone'
class Describe(Expression):
1437class Describe(Expression):
1438    arg_types = {"this": True, "style": False, "kind": False, "expressions": False}
arg_types = {'this': True, 'style': False, 'kind': False, 'expressions': False}
key = 'describe'
class Kill(Expression):
1441class Kill(Expression):
1442    arg_types = {"this": True, "kind": False}
arg_types = {'this': True, 'kind': False}
key = 'kill'
class Pragma(Expression):
1445class Pragma(Expression):
1446    pass
key = 'pragma'
class Set(Expression):
1449class Set(Expression):
1450    arg_types = {"expressions": False, "unset": False, "tag": False}
arg_types = {'expressions': False, 'unset': False, 'tag': False}
key = 'set'
class Heredoc(Expression):
1453class Heredoc(Expression):
1454    arg_types = {"this": True, "tag": False}
arg_types = {'this': True, 'tag': False}
key = 'heredoc'
class SetItem(Expression):
1457class SetItem(Expression):
1458    arg_types = {
1459        "this": False,
1460        "expressions": False,
1461        "kind": False,
1462        "collate": False,  # MySQL SET NAMES statement
1463        "global": False,
1464    }
arg_types = {'this': False, 'expressions': False, 'kind': False, 'collate': False, 'global': False}
key = 'setitem'
class Show(Expression):
1467class Show(Expression):
1468    arg_types = {
1469        "this": True,
1470        "history": False,
1471        "terse": False,
1472        "target": False,
1473        "offset": False,
1474        "starts_with": False,
1475        "limit": False,
1476        "from": False,
1477        "like": False,
1478        "where": False,
1479        "db": False,
1480        "scope": False,
1481        "scope_kind": False,
1482        "full": False,
1483        "mutex": False,
1484        "query": False,
1485        "channel": False,
1486        "global": False,
1487        "log": False,
1488        "position": False,
1489        "types": False,
1490    }
arg_types = {'this': True, 'history': False, 'terse': False, 'target': False, 'offset': False, 'starts_with': False, 'limit': False, 'from': False, 'like': False, 'where': False, 'db': False, 'scope': False, 'scope_kind': False, 'full': False, 'mutex': False, 'query': False, 'channel': False, 'global': False, 'log': False, 'position': False, 'types': False}
key = 'show'
class UserDefinedFunction(Expression):
1493class UserDefinedFunction(Expression):
1494    arg_types = {"this": True, "expressions": False, "wrapped": False}
arg_types = {'this': True, 'expressions': False, 'wrapped': False}
key = 'userdefinedfunction'
class CharacterSet(Expression):
1497class CharacterSet(Expression):
1498    arg_types = {"this": True, "default": False}
arg_types = {'this': True, 'default': False}
key = 'characterset'
class With(Expression):
1501class With(Expression):
1502    arg_types = {"expressions": True, "recursive": False}
1503
1504    @property
1505    def recursive(self) -> bool:
1506        return bool(self.args.get("recursive"))
arg_types = {'expressions': True, 'recursive': False}
recursive: bool
1504    @property
1505    def recursive(self) -> bool:
1506        return bool(self.args.get("recursive"))
key = 'with'
class WithinGroup(Expression):
1509class WithinGroup(Expression):
1510    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'withingroup'
class CTE(DerivedTable):
1515class CTE(DerivedTable):
1516    arg_types = {
1517        "this": True,
1518        "alias": True,
1519        "scalar": False,
1520        "materialized": False,
1521    }
arg_types = {'this': True, 'alias': True, 'scalar': False, 'materialized': False}
key = 'cte'
class TableAlias(Expression):
1524class TableAlias(Expression):
1525    arg_types = {"this": False, "columns": False}
1526
1527    @property
1528    def columns(self):
1529        return self.args.get("columns") or []
arg_types = {'this': False, 'columns': False}
columns
1527    @property
1528    def columns(self):
1529        return self.args.get("columns") or []
key = 'tablealias'
class BitString(Condition):
1532class BitString(Condition):
1533    pass
key = 'bitstring'
class HexString(Condition):
1536class HexString(Condition):
1537    pass
key = 'hexstring'
class ByteString(Condition):
1540class ByteString(Condition):
1541    pass
key = 'bytestring'
class RawString(Condition):
1544class RawString(Condition):
1545    pass
key = 'rawstring'
class UnicodeString(Condition):
1548class UnicodeString(Condition):
1549    arg_types = {"this": True, "escape": False}
arg_types = {'this': True, 'escape': False}
key = 'unicodestring'
class Column(Condition):
1552class Column(Condition):
1553    arg_types = {"this": True, "table": False, "db": False, "catalog": False, "join_mark": False}
1554
1555    @property
1556    def table(self) -> str:
1557        return self.text("table")
1558
1559    @property
1560    def db(self) -> str:
1561        return self.text("db")
1562
1563    @property
1564    def catalog(self) -> str:
1565        return self.text("catalog")
1566
1567    @property
1568    def output_name(self) -> str:
1569        return self.name
1570
1571    @property
1572    def parts(self) -> t.List[Identifier]:
1573        """Return the parts of a column in order catalog, db, table, name."""
1574        return [
1575            t.cast(Identifier, self.args[part])
1576            for part in ("catalog", "db", "table", "this")
1577            if self.args.get(part)
1578        ]
1579
1580    def to_dot(self) -> Dot | Identifier:
1581        """Converts the column into a dot expression."""
1582        parts = self.parts
1583        parent = self.parent
1584
1585        while parent:
1586            if isinstance(parent, Dot):
1587                parts.append(parent.expression)
1588            parent = parent.parent
1589
1590        return Dot.build(deepcopy(parts)) if len(parts) > 1 else parts[0]
arg_types = {'this': True, 'table': False, 'db': False, 'catalog': False, 'join_mark': False}
table: str
1555    @property
1556    def table(self) -> str:
1557        return self.text("table")
db: str
1559    @property
1560    def db(self) -> str:
1561        return self.text("db")
catalog: str
1563    @property
1564    def catalog(self) -> str:
1565        return self.text("catalog")
output_name: str
1567    @property
1568    def output_name(self) -> str:
1569        return self.name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
parts: List[Identifier]
1571    @property
1572    def parts(self) -> t.List[Identifier]:
1573        """Return the parts of a column in order catalog, db, table, name."""
1574        return [
1575            t.cast(Identifier, self.args[part])
1576            for part in ("catalog", "db", "table", "this")
1577            if self.args.get(part)
1578        ]

Return the parts of a column in order catalog, db, table, name.

def to_dot(self) -> Dot | Identifier:
1580    def to_dot(self) -> Dot | Identifier:
1581        """Converts the column into a dot expression."""
1582        parts = self.parts
1583        parent = self.parent
1584
1585        while parent:
1586            if isinstance(parent, Dot):
1587                parts.append(parent.expression)
1588            parent = parent.parent
1589
1590        return Dot.build(deepcopy(parts)) if len(parts) > 1 else parts[0]

Converts the column into a dot expression.

key = 'column'
class ColumnPosition(Expression):
1593class ColumnPosition(Expression):
1594    arg_types = {"this": False, "position": True}
arg_types = {'this': False, 'position': True}
key = 'columnposition'
class ColumnDef(Expression):
1597class ColumnDef(Expression):
1598    arg_types = {
1599        "this": True,
1600        "kind": False,
1601        "constraints": False,
1602        "exists": False,
1603        "position": False,
1604    }
1605
1606    @property
1607    def constraints(self) -> t.List[ColumnConstraint]:
1608        return self.args.get("constraints") or []
1609
1610    @property
1611    def kind(self) -> t.Optional[DataType]:
1612        return self.args.get("kind")
arg_types = {'this': True, 'kind': False, 'constraints': False, 'exists': False, 'position': False}
constraints: List[ColumnConstraint]
1606    @property
1607    def constraints(self) -> t.List[ColumnConstraint]:
1608        return self.args.get("constraints") or []
kind: Optional[DataType]
1610    @property
1611    def kind(self) -> t.Optional[DataType]:
1612        return self.args.get("kind")
key = 'columndef'
class AlterColumn(Expression):
1615class AlterColumn(Expression):
1616    arg_types = {
1617        "this": True,
1618        "dtype": False,
1619        "collate": False,
1620        "using": False,
1621        "default": False,
1622        "drop": False,
1623        "comment": False,
1624    }
arg_types = {'this': True, 'dtype': False, 'collate': False, 'using': False, 'default': False, 'drop': False, 'comment': False}
key = 'altercolumn'
class AlterDistStyle(Expression):
1628class AlterDistStyle(Expression):
1629    pass
key = 'alterdiststyle'
class AlterSortKey(Expression):
1632class AlterSortKey(Expression):
1633    arg_types = {"this": False, "expressions": False, "compound": False}
arg_types = {'this': False, 'expressions': False, 'compound': False}
key = 'altersortkey'
class RenameColumn(Expression):
1636class RenameColumn(Expression):
1637    arg_types = {"this": True, "to": True, "exists": False}
arg_types = {'this': True, 'to': True, 'exists': False}
key = 'renamecolumn'
class RenameTable(Expression):
1640class RenameTable(Expression):
1641    pass
key = 'renametable'
class SwapTable(Expression):
1644class SwapTable(Expression):
1645    pass
key = 'swaptable'
class Comment(Expression):
1648class Comment(Expression):
1649    arg_types = {
1650        "this": True,
1651        "kind": True,
1652        "expression": True,
1653        "exists": False,
1654        "materialized": False,
1655    }
arg_types = {'this': True, 'kind': True, 'expression': True, 'exists': False, 'materialized': False}
key = 'comment'
class Comprehension(Expression):
1658class Comprehension(Expression):
1659    arg_types = {"this": True, "expression": True, "iterator": True, "condition": False}
arg_types = {'this': True, 'expression': True, 'iterator': True, 'condition': False}
key = 'comprehension'
class MergeTreeTTLAction(Expression):
1663class MergeTreeTTLAction(Expression):
1664    arg_types = {
1665        "this": True,
1666        "delete": False,
1667        "recompress": False,
1668        "to_disk": False,
1669        "to_volume": False,
1670    }
arg_types = {'this': True, 'delete': False, 'recompress': False, 'to_disk': False, 'to_volume': False}
key = 'mergetreettlaction'
class MergeTreeTTL(Expression):
1674class MergeTreeTTL(Expression):
1675    arg_types = {
1676        "expressions": True,
1677        "where": False,
1678        "group": False,
1679        "aggregates": False,
1680    }
arg_types = {'expressions': True, 'where': False, 'group': False, 'aggregates': False}
key = 'mergetreettl'
class IndexConstraintOption(Expression):
1684class IndexConstraintOption(Expression):
1685    arg_types = {
1686        "key_block_size": False,
1687        "using": False,
1688        "parser": False,
1689        "comment": False,
1690        "visible": False,
1691        "engine_attr": False,
1692        "secondary_engine_attr": False,
1693    }
arg_types = {'key_block_size': False, 'using': False, 'parser': False, 'comment': False, 'visible': False, 'engine_attr': False, 'secondary_engine_attr': False}
key = 'indexconstraintoption'
class ColumnConstraint(Expression):
1696class ColumnConstraint(Expression):
1697    arg_types = {"this": False, "kind": True}
1698
1699    @property
1700    def kind(self) -> ColumnConstraintKind:
1701        return self.args["kind"]
arg_types = {'this': False, 'kind': True}
kind: ColumnConstraintKind
1699    @property
1700    def kind(self) -> ColumnConstraintKind:
1701        return self.args["kind"]
key = 'columnconstraint'
class ColumnConstraintKind(Expression):
1704class ColumnConstraintKind(Expression):
1705    pass
key = 'columnconstraintkind'
class AutoIncrementColumnConstraint(ColumnConstraintKind):
1708class AutoIncrementColumnConstraint(ColumnConstraintKind):
1709    pass
key = 'autoincrementcolumnconstraint'
class PeriodForSystemTimeConstraint(ColumnConstraintKind):
1712class PeriodForSystemTimeConstraint(ColumnConstraintKind):
1713    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'periodforsystemtimeconstraint'
class CaseSpecificColumnConstraint(ColumnConstraintKind):
1716class CaseSpecificColumnConstraint(ColumnConstraintKind):
1717    arg_types = {"not_": True}
arg_types = {'not_': True}
key = 'casespecificcolumnconstraint'
class CharacterSetColumnConstraint(ColumnConstraintKind):
1720class CharacterSetColumnConstraint(ColumnConstraintKind):
1721    arg_types = {"this": True}
arg_types = {'this': True}
key = 'charactersetcolumnconstraint'
class CheckColumnConstraint(ColumnConstraintKind):
1724class CheckColumnConstraint(ColumnConstraintKind):
1725    arg_types = {"this": True, "enforced": False}
arg_types = {'this': True, 'enforced': False}
key = 'checkcolumnconstraint'
class ClusteredColumnConstraint(ColumnConstraintKind):
1728class ClusteredColumnConstraint(ColumnConstraintKind):
1729    pass
key = 'clusteredcolumnconstraint'
class CollateColumnConstraint(ColumnConstraintKind):
1732class CollateColumnConstraint(ColumnConstraintKind):
1733    pass
key = 'collatecolumnconstraint'
class CommentColumnConstraint(ColumnConstraintKind):
1736class CommentColumnConstraint(ColumnConstraintKind):
1737    pass
key = 'commentcolumnconstraint'
class CompressColumnConstraint(ColumnConstraintKind):
1740class CompressColumnConstraint(ColumnConstraintKind):
1741    pass
key = 'compresscolumnconstraint'
class DateFormatColumnConstraint(ColumnConstraintKind):
1744class DateFormatColumnConstraint(ColumnConstraintKind):
1745    arg_types = {"this": True}
arg_types = {'this': True}
key = 'dateformatcolumnconstraint'
class DefaultColumnConstraint(ColumnConstraintKind):
1748class DefaultColumnConstraint(ColumnConstraintKind):
1749    pass
key = 'defaultcolumnconstraint'
class EncodeColumnConstraint(ColumnConstraintKind):
1752class EncodeColumnConstraint(ColumnConstraintKind):
1753    pass
key = 'encodecolumnconstraint'
class ExcludeColumnConstraint(ColumnConstraintKind):
1757class ExcludeColumnConstraint(ColumnConstraintKind):
1758    pass
key = 'excludecolumnconstraint'
class EphemeralColumnConstraint(ColumnConstraintKind):
1761class EphemeralColumnConstraint(ColumnConstraintKind):
1762    arg_types = {"this": False}
arg_types = {'this': False}
key = 'ephemeralcolumnconstraint'
class WithOperator(Expression):
1765class WithOperator(Expression):
1766    arg_types = {"this": True, "op": True}
arg_types = {'this': True, 'op': True}
key = 'withoperator'
class GeneratedAsIdentityColumnConstraint(ColumnConstraintKind):
1769class GeneratedAsIdentityColumnConstraint(ColumnConstraintKind):
1770    # this: True -> ALWAYS, this: False -> BY DEFAULT
1771    arg_types = {
1772        "this": False,
1773        "expression": False,
1774        "on_null": False,
1775        "start": False,
1776        "increment": False,
1777        "minvalue": False,
1778        "maxvalue": False,
1779        "cycle": False,
1780    }
arg_types = {'this': False, 'expression': False, 'on_null': False, 'start': False, 'increment': False, 'minvalue': False, 'maxvalue': False, 'cycle': False}
key = 'generatedasidentitycolumnconstraint'
class GeneratedAsRowColumnConstraint(ColumnConstraintKind):
1783class GeneratedAsRowColumnConstraint(ColumnConstraintKind):
1784    arg_types = {"start": False, "hidden": False}
arg_types = {'start': False, 'hidden': False}
key = 'generatedasrowcolumnconstraint'
class IndexColumnConstraint(ColumnConstraintKind):
1789class IndexColumnConstraint(ColumnConstraintKind):
1790    arg_types = {
1791        "this": False,
1792        "expressions": False,
1793        "kind": False,
1794        "index_type": False,
1795        "options": False,
1796        "expression": False,  # Clickhouse
1797        "granularity": False,
1798    }
arg_types = {'this': False, 'expressions': False, 'kind': False, 'index_type': False, 'options': False, 'expression': False, 'granularity': False}
key = 'indexcolumnconstraint'
class InlineLengthColumnConstraint(ColumnConstraintKind):
1801class InlineLengthColumnConstraint(ColumnConstraintKind):
1802    pass
key = 'inlinelengthcolumnconstraint'
class NonClusteredColumnConstraint(ColumnConstraintKind):
1805class NonClusteredColumnConstraint(ColumnConstraintKind):
1806    pass
key = 'nonclusteredcolumnconstraint'
class NotForReplicationColumnConstraint(ColumnConstraintKind):
1809class NotForReplicationColumnConstraint(ColumnConstraintKind):
1810    arg_types = {}
arg_types = {}
key = 'notforreplicationcolumnconstraint'
class NotNullColumnConstraint(ColumnConstraintKind):
1813class NotNullColumnConstraint(ColumnConstraintKind):
1814    arg_types = {"allow_null": False}
arg_types = {'allow_null': False}
key = 'notnullcolumnconstraint'
class OnUpdateColumnConstraint(ColumnConstraintKind):
1818class OnUpdateColumnConstraint(ColumnConstraintKind):
1819    pass
key = 'onupdatecolumnconstraint'
class TransformColumnConstraint(ColumnConstraintKind):
1823class TransformColumnConstraint(ColumnConstraintKind):
1824    pass
key = 'transformcolumnconstraint'
class PrimaryKeyColumnConstraint(ColumnConstraintKind):
1827class PrimaryKeyColumnConstraint(ColumnConstraintKind):
1828    arg_types = {"desc": False}
arg_types = {'desc': False}
key = 'primarykeycolumnconstraint'
class TitleColumnConstraint(ColumnConstraintKind):
1831class TitleColumnConstraint(ColumnConstraintKind):
1832    pass
key = 'titlecolumnconstraint'
class UniqueColumnConstraint(ColumnConstraintKind):
1835class UniqueColumnConstraint(ColumnConstraintKind):
1836    arg_types = {"this": False, "index_type": False, "on_conflict": False}
arg_types = {'this': False, 'index_type': False, 'on_conflict': False}
key = 'uniquecolumnconstraint'
class UppercaseColumnConstraint(ColumnConstraintKind):
1839class UppercaseColumnConstraint(ColumnConstraintKind):
1840    arg_types: t.Dict[str, t.Any] = {}
arg_types: Dict[str, Any] = {}
key = 'uppercasecolumnconstraint'
class PathColumnConstraint(ColumnConstraintKind):
1843class PathColumnConstraint(ColumnConstraintKind):
1844    pass
key = 'pathcolumnconstraint'
class ComputedColumnConstraint(ColumnConstraintKind):
1849class ComputedColumnConstraint(ColumnConstraintKind):
1850    arg_types = {"this": True, "persisted": False, "not_null": False}
arg_types = {'this': True, 'persisted': False, 'not_null': False}
key = 'computedcolumnconstraint'
class Constraint(Expression):
1853class Constraint(Expression):
1854    arg_types = {"this": True, "expressions": True}
arg_types = {'this': True, 'expressions': True}
key = 'constraint'
class Delete(DML):
1857class Delete(DML):
1858    arg_types = {
1859        "with": False,
1860        "this": False,
1861        "using": False,
1862        "where": False,
1863        "returning": False,
1864        "limit": False,
1865        "tables": False,  # Multiple-Table Syntax (MySQL)
1866    }
1867
1868    def delete(
1869        self,
1870        table: ExpOrStr,
1871        dialect: DialectType = None,
1872        copy: bool = True,
1873        **opts,
1874    ) -> Delete:
1875        """
1876        Create a DELETE expression or replace the table on an existing DELETE expression.
1877
1878        Example:
1879            >>> delete("tbl").sql()
1880            'DELETE FROM tbl'
1881
1882        Args:
1883            table: the table from which to delete.
1884            dialect: the dialect used to parse the input expression.
1885            copy: if `False`, modify this expression instance in-place.
1886            opts: other options to use to parse the input expressions.
1887
1888        Returns:
1889            Delete: the modified expression.
1890        """
1891        return _apply_builder(
1892            expression=table,
1893            instance=self,
1894            arg="this",
1895            dialect=dialect,
1896            into=Table,
1897            copy=copy,
1898            **opts,
1899        )
1900
1901    def where(
1902        self,
1903        *expressions: t.Optional[ExpOrStr],
1904        append: bool = True,
1905        dialect: DialectType = None,
1906        copy: bool = True,
1907        **opts,
1908    ) -> Delete:
1909        """
1910        Append to or set the WHERE expressions.
1911
1912        Example:
1913            >>> delete("tbl").where("x = 'a' OR x < 'b'").sql()
1914            "DELETE FROM tbl WHERE x = 'a' OR x < 'b'"
1915
1916        Args:
1917            *expressions: the SQL code strings to parse.
1918                If an `Expression` instance is passed, it will be used as-is.
1919                Multiple expressions are combined with an AND operator.
1920            append: if `True`, AND the new expressions to any existing expression.
1921                Otherwise, this resets the expression.
1922            dialect: the dialect used to parse the input expressions.
1923            copy: if `False`, modify this expression instance in-place.
1924            opts: other options to use to parse the input expressions.
1925
1926        Returns:
1927            Delete: the modified expression.
1928        """
1929        return _apply_conjunction_builder(
1930            *expressions,
1931            instance=self,
1932            arg="where",
1933            append=append,
1934            into=Where,
1935            dialect=dialect,
1936            copy=copy,
1937            **opts,
1938        )
arg_types = {'with': False, 'this': False, 'using': False, 'where': False, 'returning': False, 'limit': False, 'tables': False}
def delete( self, table: Union[str, Expression], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Delete:
1868    def delete(
1869        self,
1870        table: ExpOrStr,
1871        dialect: DialectType = None,
1872        copy: bool = True,
1873        **opts,
1874    ) -> Delete:
1875        """
1876        Create a DELETE expression or replace the table on an existing DELETE expression.
1877
1878        Example:
1879            >>> delete("tbl").sql()
1880            'DELETE FROM tbl'
1881
1882        Args:
1883            table: the table from which to delete.
1884            dialect: the dialect used to parse the input expression.
1885            copy: if `False`, modify this expression instance in-place.
1886            opts: other options to use to parse the input expressions.
1887
1888        Returns:
1889            Delete: the modified expression.
1890        """
1891        return _apply_builder(
1892            expression=table,
1893            instance=self,
1894            arg="this",
1895            dialect=dialect,
1896            into=Table,
1897            copy=copy,
1898            **opts,
1899        )

Create a DELETE expression or replace the table on an existing DELETE expression.

Example:
>>> delete("tbl").sql()
'DELETE FROM tbl'
Arguments:
  • table: the table from which to delete.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

Delete: the modified expression.

def where( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Delete:
1901    def where(
1902        self,
1903        *expressions: t.Optional[ExpOrStr],
1904        append: bool = True,
1905        dialect: DialectType = None,
1906        copy: bool = True,
1907        **opts,
1908    ) -> Delete:
1909        """
1910        Append to or set the WHERE expressions.
1911
1912        Example:
1913            >>> delete("tbl").where("x = 'a' OR x < 'b'").sql()
1914            "DELETE FROM tbl WHERE x = 'a' OR x < 'b'"
1915
1916        Args:
1917            *expressions: the SQL code strings to parse.
1918                If an `Expression` instance is passed, it will be used as-is.
1919                Multiple expressions are combined with an AND operator.
1920            append: if `True`, AND the new expressions to any existing expression.
1921                Otherwise, this resets the expression.
1922            dialect: the dialect used to parse the input expressions.
1923            copy: if `False`, modify this expression instance in-place.
1924            opts: other options to use to parse the input expressions.
1925
1926        Returns:
1927            Delete: the modified expression.
1928        """
1929        return _apply_conjunction_builder(
1930            *expressions,
1931            instance=self,
1932            arg="where",
1933            append=append,
1934            into=Where,
1935            dialect=dialect,
1936            copy=copy,
1937            **opts,
1938        )

Append to or set the WHERE expressions.

Example:
>>> delete("tbl").where("x = 'a' OR x < 'b'").sql()
"DELETE FROM tbl WHERE x = 'a' OR x < 'b'"
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is. Multiple expressions are combined with an AND operator.
  • append: if True, AND the new expressions to any existing expression. Otherwise, this resets the expression.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

Delete: the modified expression.

key = 'delete'
class Drop(Expression):
1941class Drop(Expression):
1942    arg_types = {
1943        "this": False,
1944        "kind": False,
1945        "expressions": False,
1946        "exists": False,
1947        "temporary": False,
1948        "materialized": False,
1949        "cascade": False,
1950        "constraints": False,
1951        "purge": False,
1952        "cluster": False,
1953    }
arg_types = {'this': False, 'kind': False, 'expressions': False, 'exists': False, 'temporary': False, 'materialized': False, 'cascade': False, 'constraints': False, 'purge': False, 'cluster': False}
key = 'drop'
class Filter(Expression):
1956class Filter(Expression):
1957    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'filter'
class Check(Expression):
1960class Check(Expression):
1961    pass
key = 'check'
class Connect(Expression):
1965class Connect(Expression):
1966    arg_types = {"start": False, "connect": True, "nocycle": False}
arg_types = {'start': False, 'connect': True, 'nocycle': False}
key = 'connect'
class CopyParameter(Expression):
1969class CopyParameter(Expression):
1970    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'copyparameter'
class Copy(Expression):
1973class Copy(Expression):
1974    arg_types = {
1975        "this": True,
1976        "kind": True,
1977        "files": True,
1978        "credentials": False,
1979        "format": False,
1980        "params": False,
1981    }
arg_types = {'this': True, 'kind': True, 'files': True, 'credentials': False, 'format': False, 'params': False}
key = 'copy'
class Credentials(Expression):
1984class Credentials(Expression):
1985    arg_types = {
1986        "credentials": False,
1987        "encryption": False,
1988        "storage": False,
1989        "iam_role": False,
1990        "region": False,
1991    }
arg_types = {'credentials': False, 'encryption': False, 'storage': False, 'iam_role': False, 'region': False}
key = 'credentials'
class Prior(Expression):
1994class Prior(Expression):
1995    pass
key = 'prior'
class Directory(Expression):
1998class Directory(Expression):
1999    # https://spark.apache.org/docs/3.0.0-preview/sql-ref-syntax-dml-insert-overwrite-directory-hive.html
2000    arg_types = {"this": True, "local": False, "row_format": False}
arg_types = {'this': True, 'local': False, 'row_format': False}
key = 'directory'
class ForeignKey(Expression):
2003class ForeignKey(Expression):
2004    arg_types = {
2005        "expressions": True,
2006        "reference": False,
2007        "delete": False,
2008        "update": False,
2009    }
arg_types = {'expressions': True, 'reference': False, 'delete': False, 'update': False}
key = 'foreignkey'
class ColumnPrefix(Expression):
2012class ColumnPrefix(Expression):
2013    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'columnprefix'
class PrimaryKey(Expression):
2016class PrimaryKey(Expression):
2017    arg_types = {"expressions": True, "options": False}
arg_types = {'expressions': True, 'options': False}
key = 'primarykey'
class Into(Expression):
2022class Into(Expression):
2023    arg_types = {"this": True, "temporary": False, "unlogged": False}
arg_types = {'this': True, 'temporary': False, 'unlogged': False}
key = 'into'
class From(Expression):
2026class From(Expression):
2027    @property
2028    def name(self) -> str:
2029        return self.this.name
2030
2031    @property
2032    def alias_or_name(self) -> str:
2033        return self.this.alias_or_name
name: str
2027    @property
2028    def name(self) -> str:
2029        return self.this.name
alias_or_name: str
2031    @property
2032    def alias_or_name(self) -> str:
2033        return self.this.alias_or_name
key = 'from'
class Having(Expression):
2036class Having(Expression):
2037    pass
key = 'having'
class Hint(Expression):
2040class Hint(Expression):
2041    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'hint'
class JoinHint(Expression):
2044class JoinHint(Expression):
2045    arg_types = {"this": True, "expressions": True}
arg_types = {'this': True, 'expressions': True}
key = 'joinhint'
class Identifier(Expression):
2048class Identifier(Expression):
2049    arg_types = {"this": True, "quoted": False, "global": False, "temporary": False}
2050
2051    @property
2052    def quoted(self) -> bool:
2053        return bool(self.args.get("quoted"))
2054
2055    @property
2056    def hashable_args(self) -> t.Any:
2057        return (self.this, self.quoted)
2058
2059    @property
2060    def output_name(self) -> str:
2061        return self.name
arg_types = {'this': True, 'quoted': False, 'global': False, 'temporary': False}
quoted: bool
2051    @property
2052    def quoted(self) -> bool:
2053        return bool(self.args.get("quoted"))
hashable_args: Any
2055    @property
2056    def hashable_args(self) -> t.Any:
2057        return (self.this, self.quoted)
output_name: str
2059    @property
2060    def output_name(self) -> str:
2061        return self.name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'identifier'
class Opclass(Expression):
2065class Opclass(Expression):
2066    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'opclass'
class Index(Expression):
2069class Index(Expression):
2070    arg_types = {
2071        "this": False,
2072        "table": False,
2073        "unique": False,
2074        "primary": False,
2075        "amp": False,  # teradata
2076        "params": False,
2077    }
arg_types = {'this': False, 'table': False, 'unique': False, 'primary': False, 'amp': False, 'params': False}
key = 'index'
class IndexParameters(Expression):
2080class IndexParameters(Expression):
2081    arg_types = {
2082        "using": False,
2083        "include": False,
2084        "columns": False,
2085        "with_storage": False,
2086        "partition_by": False,
2087        "tablespace": False,
2088        "where": False,
2089    }
arg_types = {'using': False, 'include': False, 'columns': False, 'with_storage': False, 'partition_by': False, 'tablespace': False, 'where': False}
key = 'indexparameters'
class Insert(DDL, DML):
2092class Insert(DDL, DML):
2093    arg_types = {
2094        "hint": False,
2095        "with": False,
2096        "is_function": False,
2097        "this": False,
2098        "expression": False,
2099        "conflict": False,
2100        "returning": False,
2101        "overwrite": False,
2102        "exists": False,
2103        "alternative": False,
2104        "where": False,
2105        "ignore": False,
2106        "by_name": False,
2107        "stored": False,
2108    }
2109
2110    def with_(
2111        self,
2112        alias: ExpOrStr,
2113        as_: ExpOrStr,
2114        recursive: t.Optional[bool] = None,
2115        append: bool = True,
2116        dialect: DialectType = None,
2117        copy: bool = True,
2118        **opts,
2119    ) -> Insert:
2120        """
2121        Append to or set the common table expressions.
2122
2123        Example:
2124            >>> insert("SELECT x FROM cte", "t").with_("cte", as_="SELECT * FROM tbl").sql()
2125            'WITH cte AS (SELECT * FROM tbl) INSERT INTO t SELECT x FROM cte'
2126
2127        Args:
2128            alias: the SQL code string to parse as the table name.
2129                If an `Expression` instance is passed, this is used as-is.
2130            as_: the SQL code string to parse as the table expression.
2131                If an `Expression` instance is passed, it will be used as-is.
2132            recursive: set the RECURSIVE part of the expression. Defaults to `False`.
2133            append: if `True`, add to any existing expressions.
2134                Otherwise, this resets the expressions.
2135            dialect: the dialect used to parse the input expression.
2136            copy: if `False`, modify this expression instance in-place.
2137            opts: other options to use to parse the input expressions.
2138
2139        Returns:
2140            The modified expression.
2141        """
2142        return _apply_cte_builder(
2143            self, alias, as_, recursive=recursive, append=append, dialect=dialect, copy=copy, **opts
2144        )
arg_types = {'hint': False, 'with': False, 'is_function': False, 'this': False, 'expression': False, 'conflict': False, 'returning': False, 'overwrite': False, 'exists': False, 'alternative': False, 'where': False, 'ignore': False, 'by_name': False, 'stored': False}
def with_( self, alias: Union[str, Expression], as_: Union[str, Expression], recursive: Optional[bool] = None, append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Insert:
2110    def with_(
2111        self,
2112        alias: ExpOrStr,
2113        as_: ExpOrStr,
2114        recursive: t.Optional[bool] = None,
2115        append: bool = True,
2116        dialect: DialectType = None,
2117        copy: bool = True,
2118        **opts,
2119    ) -> Insert:
2120        """
2121        Append to or set the common table expressions.
2122
2123        Example:
2124            >>> insert("SELECT x FROM cte", "t").with_("cte", as_="SELECT * FROM tbl").sql()
2125            'WITH cte AS (SELECT * FROM tbl) INSERT INTO t SELECT x FROM cte'
2126
2127        Args:
2128            alias: the SQL code string to parse as the table name.
2129                If an `Expression` instance is passed, this is used as-is.
2130            as_: the SQL code string to parse as the table expression.
2131                If an `Expression` instance is passed, it will be used as-is.
2132            recursive: set the RECURSIVE part of the expression. Defaults to `False`.
2133            append: if `True`, add to any existing expressions.
2134                Otherwise, this resets the expressions.
2135            dialect: the dialect used to parse the input expression.
2136            copy: if `False`, modify this expression instance in-place.
2137            opts: other options to use to parse the input expressions.
2138
2139        Returns:
2140            The modified expression.
2141        """
2142        return _apply_cte_builder(
2143            self, alias, as_, recursive=recursive, append=append, dialect=dialect, copy=copy, **opts
2144        )

Append to or set the common table expressions.

Example:
>>> insert("SELECT x FROM cte", "t").with_("cte", as_="SELECT * FROM tbl").sql()
'WITH cte AS (SELECT * FROM tbl) INSERT INTO t SELECT x FROM cte'
Arguments:
  • alias: the SQL code string to parse as the table name. If an Expression instance is passed, this is used as-is.
  • as_: the SQL code string to parse as the table expression. If an Expression instance is passed, it will be used as-is.
  • recursive: set the RECURSIVE part of the expression. Defaults to False.
  • append: if True, add to any existing expressions. Otherwise, this resets the expressions.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified expression.

key = 'insert'
class OnConflict(Expression):
2147class OnConflict(Expression):
2148    arg_types = {
2149        "duplicate": False,
2150        "expressions": False,
2151        "action": False,
2152        "conflict_keys": False,
2153        "constraint": False,
2154    }
arg_types = {'duplicate': False, 'expressions': False, 'action': False, 'conflict_keys': False, 'constraint': False}
key = 'onconflict'
class Returning(Expression):
2157class Returning(Expression):
2158    arg_types = {"expressions": True, "into": False}
arg_types = {'expressions': True, 'into': False}
key = 'returning'
class Introducer(Expression):
2162class Introducer(Expression):
2163    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'introducer'
class National(Expression):
2167class National(Expression):
2168    pass
key = 'national'
class LoadData(Expression):
2171class LoadData(Expression):
2172    arg_types = {
2173        "this": True,
2174        "local": False,
2175        "overwrite": False,
2176        "inpath": True,
2177        "partition": False,
2178        "input_format": False,
2179        "serde": False,
2180    }
arg_types = {'this': True, 'local': False, 'overwrite': False, 'inpath': True, 'partition': False, 'input_format': False, 'serde': False}
key = 'loaddata'
class Partition(Expression):
2183class Partition(Expression):
2184    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'partition'
class PartitionRange(Expression):
2187class PartitionRange(Expression):
2188    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'partitionrange'
class PartitionId(Expression):
2192class PartitionId(Expression):
2193    pass
key = 'partitionid'
class Fetch(Expression):
2196class Fetch(Expression):
2197    arg_types = {
2198        "direction": False,
2199        "count": False,
2200        "percent": False,
2201        "with_ties": False,
2202    }
arg_types = {'direction': False, 'count': False, 'percent': False, 'with_ties': False}
key = 'fetch'
class Group(Expression):
2205class Group(Expression):
2206    arg_types = {
2207        "expressions": False,
2208        "grouping_sets": False,
2209        "cube": False,
2210        "rollup": False,
2211        "totals": False,
2212        "all": False,
2213    }
arg_types = {'expressions': False, 'grouping_sets': False, 'cube': False, 'rollup': False, 'totals': False, 'all': False}
key = 'group'
class Lambda(Expression):
2216class Lambda(Expression):
2217    arg_types = {"this": True, "expressions": True}
arg_types = {'this': True, 'expressions': True}
key = 'lambda'
class Limit(Expression):
2220class Limit(Expression):
2221    arg_types = {"this": False, "expression": True, "offset": False, "expressions": False}
arg_types = {'this': False, 'expression': True, 'offset': False, 'expressions': False}
key = 'limit'
class Literal(Condition):
2224class Literal(Condition):
2225    arg_types = {"this": True, "is_string": True}
2226
2227    @property
2228    def hashable_args(self) -> t.Any:
2229        return (self.this, self.args.get("is_string"))
2230
2231    @classmethod
2232    def number(cls, number) -> Literal:
2233        return cls(this=str(number), is_string=False)
2234
2235    @classmethod
2236    def string(cls, string) -> Literal:
2237        return cls(this=str(string), is_string=True)
2238
2239    @property
2240    def output_name(self) -> str:
2241        return self.name
arg_types = {'this': True, 'is_string': True}
hashable_args: Any
2227    @property
2228    def hashable_args(self) -> t.Any:
2229        return (self.this, self.args.get("is_string"))
@classmethod
def number(cls, number) -> Literal:
2231    @classmethod
2232    def number(cls, number) -> Literal:
2233        return cls(this=str(number), is_string=False)
@classmethod
def string(cls, string) -> Literal:
2235    @classmethod
2236    def string(cls, string) -> Literal:
2237        return cls(this=str(string), is_string=True)
output_name: str
2239    @property
2240    def output_name(self) -> str:
2241        return self.name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'literal'
class Join(Expression):
2244class Join(Expression):
2245    arg_types = {
2246        "this": True,
2247        "on": False,
2248        "side": False,
2249        "kind": False,
2250        "using": False,
2251        "method": False,
2252        "global": False,
2253        "hint": False,
2254        "match_condition": False,  # Snowflake
2255    }
2256
2257    @property
2258    def method(self) -> str:
2259        return self.text("method").upper()
2260
2261    @property
2262    def kind(self) -> str:
2263        return self.text("kind").upper()
2264
2265    @property
2266    def side(self) -> str:
2267        return self.text("side").upper()
2268
2269    @property
2270    def hint(self) -> str:
2271        return self.text("hint").upper()
2272
2273    @property
2274    def alias_or_name(self) -> str:
2275        return self.this.alias_or_name
2276
2277    def on(
2278        self,
2279        *expressions: t.Optional[ExpOrStr],
2280        append: bool = True,
2281        dialect: DialectType = None,
2282        copy: bool = True,
2283        **opts,
2284    ) -> Join:
2285        """
2286        Append to or set the ON expressions.
2287
2288        Example:
2289            >>> import sqlglot
2290            >>> sqlglot.parse_one("JOIN x", into=Join).on("y = 1").sql()
2291            'JOIN x ON y = 1'
2292
2293        Args:
2294            *expressions: the SQL code strings to parse.
2295                If an `Expression` instance is passed, it will be used as-is.
2296                Multiple expressions are combined with an AND operator.
2297            append: if `True`, AND the new expressions to any existing expression.
2298                Otherwise, this resets the expression.
2299            dialect: the dialect used to parse the input expressions.
2300            copy: if `False`, modify this expression instance in-place.
2301            opts: other options to use to parse the input expressions.
2302
2303        Returns:
2304            The modified Join expression.
2305        """
2306        join = _apply_conjunction_builder(
2307            *expressions,
2308            instance=self,
2309            arg="on",
2310            append=append,
2311            dialect=dialect,
2312            copy=copy,
2313            **opts,
2314        )
2315
2316        if join.kind == "CROSS":
2317            join.set("kind", None)
2318
2319        return join
2320
2321    def using(
2322        self,
2323        *expressions: t.Optional[ExpOrStr],
2324        append: bool = True,
2325        dialect: DialectType = None,
2326        copy: bool = True,
2327        **opts,
2328    ) -> Join:
2329        """
2330        Append to or set the USING expressions.
2331
2332        Example:
2333            >>> import sqlglot
2334            >>> sqlglot.parse_one("JOIN x", into=Join).using("foo", "bla").sql()
2335            'JOIN x USING (foo, bla)'
2336
2337        Args:
2338            *expressions: the SQL code strings to parse.
2339                If an `Expression` instance is passed, it will be used as-is.
2340            append: if `True`, concatenate the new expressions to the existing "using" list.
2341                Otherwise, this resets the expression.
2342            dialect: the dialect used to parse the input expressions.
2343            copy: if `False`, modify this expression instance in-place.
2344            opts: other options to use to parse the input expressions.
2345
2346        Returns:
2347            The modified Join expression.
2348        """
2349        join = _apply_list_builder(
2350            *expressions,
2351            instance=self,
2352            arg="using",
2353            append=append,
2354            dialect=dialect,
2355            copy=copy,
2356            **opts,
2357        )
2358
2359        if join.kind == "CROSS":
2360            join.set("kind", None)
2361
2362        return join
arg_types = {'this': True, 'on': False, 'side': False, 'kind': False, 'using': False, 'method': False, 'global': False, 'hint': False, 'match_condition': False}
method: str
2257    @property
2258    def method(self) -> str:
2259        return self.text("method").upper()
kind: str
2261    @property
2262    def kind(self) -> str:
2263        return self.text("kind").upper()
side: str
2265    @property
2266    def side(self) -> str:
2267        return self.text("side").upper()
hint: str
2269    @property
2270    def hint(self) -> str:
2271        return self.text("hint").upper()
alias_or_name: str
2273    @property
2274    def alias_or_name(self) -> str:
2275        return self.this.alias_or_name
def on( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Join:
2277    def on(
2278        self,
2279        *expressions: t.Optional[ExpOrStr],
2280        append: bool = True,
2281        dialect: DialectType = None,
2282        copy: bool = True,
2283        **opts,
2284    ) -> Join:
2285        """
2286        Append to or set the ON expressions.
2287
2288        Example:
2289            >>> import sqlglot
2290            >>> sqlglot.parse_one("JOIN x", into=Join).on("y = 1").sql()
2291            'JOIN x ON y = 1'
2292
2293        Args:
2294            *expressions: the SQL code strings to parse.
2295                If an `Expression` instance is passed, it will be used as-is.
2296                Multiple expressions are combined with an AND operator.
2297            append: if `True`, AND the new expressions to any existing expression.
2298                Otherwise, this resets the expression.
2299            dialect: the dialect used to parse the input expressions.
2300            copy: if `False`, modify this expression instance in-place.
2301            opts: other options to use to parse the input expressions.
2302
2303        Returns:
2304            The modified Join expression.
2305        """
2306        join = _apply_conjunction_builder(
2307            *expressions,
2308            instance=self,
2309            arg="on",
2310            append=append,
2311            dialect=dialect,
2312            copy=copy,
2313            **opts,
2314        )
2315
2316        if join.kind == "CROSS":
2317            join.set("kind", None)
2318
2319        return join

Append to or set the ON expressions.

Example:
>>> import sqlglot
>>> sqlglot.parse_one("JOIN x", into=Join).on("y = 1").sql()
'JOIN x ON y = 1'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is. Multiple expressions are combined with an AND operator.
  • append: if True, AND the new expressions to any existing expression. Otherwise, this resets the expression.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Join expression.

def using( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Join:
2321    def using(
2322        self,
2323        *expressions: t.Optional[ExpOrStr],
2324        append: bool = True,
2325        dialect: DialectType = None,
2326        copy: bool = True,
2327        **opts,
2328    ) -> Join:
2329        """
2330        Append to or set the USING expressions.
2331
2332        Example:
2333            >>> import sqlglot
2334            >>> sqlglot.parse_one("JOIN x", into=Join).using("foo", "bla").sql()
2335            'JOIN x USING (foo, bla)'
2336
2337        Args:
2338            *expressions: the SQL code strings to parse.
2339                If an `Expression` instance is passed, it will be used as-is.
2340            append: if `True`, concatenate the new expressions to the existing "using" list.
2341                Otherwise, this resets the expression.
2342            dialect: the dialect used to parse the input expressions.
2343            copy: if `False`, modify this expression instance in-place.
2344            opts: other options to use to parse the input expressions.
2345
2346        Returns:
2347            The modified Join expression.
2348        """
2349        join = _apply_list_builder(
2350            *expressions,
2351            instance=self,
2352            arg="using",
2353            append=append,
2354            dialect=dialect,
2355            copy=copy,
2356            **opts,
2357        )
2358
2359        if join.kind == "CROSS":
2360            join.set("kind", None)
2361
2362        return join

Append to or set the USING expressions.

Example:
>>> import sqlglot
>>> sqlglot.parse_one("JOIN x", into=Join).using("foo", "bla").sql()
'JOIN x USING (foo, bla)'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • append: if True, concatenate the new expressions to the existing "using" list. Otherwise, this resets the expression.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Join expression.

key = 'join'
class Lateral(UDTF):
2365class Lateral(UDTF):
2366    arg_types = {
2367        "this": True,
2368        "view": False,
2369        "outer": False,
2370        "alias": False,
2371        "cross_apply": False,  # True -> CROSS APPLY, False -> OUTER APPLY
2372    }
arg_types = {'this': True, 'view': False, 'outer': False, 'alias': False, 'cross_apply': False}
key = 'lateral'
class MatchRecognizeMeasure(Expression):
2375class MatchRecognizeMeasure(Expression):
2376    arg_types = {
2377        "this": True,
2378        "window_frame": False,
2379    }
arg_types = {'this': True, 'window_frame': False}
key = 'matchrecognizemeasure'
class MatchRecognize(Expression):
2382class MatchRecognize(Expression):
2383    arg_types = {
2384        "partition_by": False,
2385        "order": False,
2386        "measures": False,
2387        "rows": False,
2388        "after": False,
2389        "pattern": False,
2390        "define": False,
2391        "alias": False,
2392    }
arg_types = {'partition_by': False, 'order': False, 'measures': False, 'rows': False, 'after': False, 'pattern': False, 'define': False, 'alias': False}
key = 'matchrecognize'
class Final(Expression):
2397class Final(Expression):
2398    pass
key = 'final'
class Offset(Expression):
2401class Offset(Expression):
2402    arg_types = {"this": False, "expression": True, "expressions": False}
arg_types = {'this': False, 'expression': True, 'expressions': False}
key = 'offset'
class Order(Expression):
2405class Order(Expression):
2406    arg_types = {
2407        "this": False,
2408        "expressions": True,
2409        "interpolate": False,
2410        "siblings": False,
2411    }
arg_types = {'this': False, 'expressions': True, 'interpolate': False, 'siblings': False}
key = 'order'
class WithFill(Expression):
2415class WithFill(Expression):
2416    arg_types = {"from": False, "to": False, "step": False}
arg_types = {'from': False, 'to': False, 'step': False}
key = 'withfill'
class Cluster(Order):
2421class Cluster(Order):
2422    pass
key = 'cluster'
class Distribute(Order):
2425class Distribute(Order):
2426    pass
key = 'distribute'
class Sort(Order):
2429class Sort(Order):
2430    pass
key = 'sort'
class Ordered(Expression):
2433class Ordered(Expression):
2434    arg_types = {"this": True, "desc": False, "nulls_first": True, "with_fill": False}
arg_types = {'this': True, 'desc': False, 'nulls_first': True, 'with_fill': False}
key = 'ordered'
class Property(Expression):
2437class Property(Expression):
2438    arg_types = {"this": True, "value": True}
arg_types = {'this': True, 'value': True}
key = 'property'
class AlgorithmProperty(Property):
2441class AlgorithmProperty(Property):
2442    arg_types = {"this": True}
arg_types = {'this': True}
key = 'algorithmproperty'
class AutoIncrementProperty(Property):
2445class AutoIncrementProperty(Property):
2446    arg_types = {"this": True}
arg_types = {'this': True}
key = 'autoincrementproperty'
class AutoRefreshProperty(Property):
2450class AutoRefreshProperty(Property):
2451    arg_types = {"this": True}
arg_types = {'this': True}
key = 'autorefreshproperty'
class BackupProperty(Property):
2454class BackupProperty(Property):
2455    arg_types = {"this": True}
arg_types = {'this': True}
key = 'backupproperty'
class BlockCompressionProperty(Property):
2458class BlockCompressionProperty(Property):
2459    arg_types = {
2460        "autotemp": False,
2461        "always": False,
2462        "default": False,
2463        "manual": False,
2464        "never": False,
2465    }
arg_types = {'autotemp': False, 'always': False, 'default': False, 'manual': False, 'never': False}
key = 'blockcompressionproperty'
class CharacterSetProperty(Property):
2468class CharacterSetProperty(Property):
2469    arg_types = {"this": True, "default": True}
arg_types = {'this': True, 'default': True}
key = 'charactersetproperty'
class ChecksumProperty(Property):
2472class ChecksumProperty(Property):
2473    arg_types = {"on": False, "default": False}
arg_types = {'on': False, 'default': False}
key = 'checksumproperty'
class CollateProperty(Property):
2476class CollateProperty(Property):
2477    arg_types = {"this": True, "default": False}
arg_types = {'this': True, 'default': False}
key = 'collateproperty'
class CopyGrantsProperty(Property):
2480class CopyGrantsProperty(Property):
2481    arg_types = {}
arg_types = {}
key = 'copygrantsproperty'
class DataBlocksizeProperty(Property):
2484class DataBlocksizeProperty(Property):
2485    arg_types = {
2486        "size": False,
2487        "units": False,
2488        "minimum": False,
2489        "maximum": False,
2490        "default": False,
2491    }
arg_types = {'size': False, 'units': False, 'minimum': False, 'maximum': False, 'default': False}
key = 'datablocksizeproperty'
class DefinerProperty(Property):
2494class DefinerProperty(Property):
2495    arg_types = {"this": True}
arg_types = {'this': True}
key = 'definerproperty'
class DistKeyProperty(Property):
2498class DistKeyProperty(Property):
2499    arg_types = {"this": True}
arg_types = {'this': True}
key = 'distkeyproperty'
class DistStyleProperty(Property):
2502class DistStyleProperty(Property):
2503    arg_types = {"this": True}
arg_types = {'this': True}
key = 'diststyleproperty'
class EngineProperty(Property):
2506class EngineProperty(Property):
2507    arg_types = {"this": True}
arg_types = {'this': True}
key = 'engineproperty'
class HeapProperty(Property):
2510class HeapProperty(Property):
2511    arg_types = {}
arg_types = {}
key = 'heapproperty'
class ToTableProperty(Property):
2514class ToTableProperty(Property):
2515    arg_types = {"this": True}
arg_types = {'this': True}
key = 'totableproperty'
class ExecuteAsProperty(Property):
2518class ExecuteAsProperty(Property):
2519    arg_types = {"this": True}
arg_types = {'this': True}
key = 'executeasproperty'
class ExternalProperty(Property):
2522class ExternalProperty(Property):
2523    arg_types = {"this": False}
arg_types = {'this': False}
key = 'externalproperty'
class FallbackProperty(Property):
2526class FallbackProperty(Property):
2527    arg_types = {"no": True, "protection": False}
arg_types = {'no': True, 'protection': False}
key = 'fallbackproperty'
class FileFormatProperty(Property):
2530class FileFormatProperty(Property):
2531    arg_types = {"this": True}
arg_types = {'this': True}
key = 'fileformatproperty'
class FreespaceProperty(Property):
2534class FreespaceProperty(Property):
2535    arg_types = {"this": True, "percent": False}
arg_types = {'this': True, 'percent': False}
key = 'freespaceproperty'
class GlobalProperty(Property):
2538class GlobalProperty(Property):
2539    arg_types = {}
arg_types = {}
key = 'globalproperty'
class IcebergProperty(Property):
2542class IcebergProperty(Property):
2543    arg_types = {}
arg_types = {}
key = 'icebergproperty'
class InheritsProperty(Property):
2546class InheritsProperty(Property):
2547    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'inheritsproperty'
class InputModelProperty(Property):
2550class InputModelProperty(Property):
2551    arg_types = {"this": True}
arg_types = {'this': True}
key = 'inputmodelproperty'
class OutputModelProperty(Property):
2554class OutputModelProperty(Property):
2555    arg_types = {"this": True}
arg_types = {'this': True}
key = 'outputmodelproperty'
class IsolatedLoadingProperty(Property):
2558class IsolatedLoadingProperty(Property):
2559    arg_types = {"no": False, "concurrent": False, "target": False}
arg_types = {'no': False, 'concurrent': False, 'target': False}
key = 'isolatedloadingproperty'
class JournalProperty(Property):
2562class JournalProperty(Property):
2563    arg_types = {
2564        "no": False,
2565        "dual": False,
2566        "before": False,
2567        "local": False,
2568        "after": False,
2569    }
arg_types = {'no': False, 'dual': False, 'before': False, 'local': False, 'after': False}
key = 'journalproperty'
class LanguageProperty(Property):
2572class LanguageProperty(Property):
2573    arg_types = {"this": True}
arg_types = {'this': True}
key = 'languageproperty'
class ClusteredByProperty(Property):
2577class ClusteredByProperty(Property):
2578    arg_types = {"expressions": True, "sorted_by": False, "buckets": True}
arg_types = {'expressions': True, 'sorted_by': False, 'buckets': True}
key = 'clusteredbyproperty'
class DictProperty(Property):
2581class DictProperty(Property):
2582    arg_types = {"this": True, "kind": True, "settings": False}
arg_types = {'this': True, 'kind': True, 'settings': False}
key = 'dictproperty'
class DictSubProperty(Property):
2585class DictSubProperty(Property):
2586    pass
key = 'dictsubproperty'
class DictRange(Property):
2589class DictRange(Property):
2590    arg_types = {"this": True, "min": True, "max": True}
arg_types = {'this': True, 'min': True, 'max': True}
key = 'dictrange'
class OnCluster(Property):
2595class OnCluster(Property):
2596    arg_types = {"this": True}
arg_types = {'this': True}
key = 'oncluster'
class LikeProperty(Property):
2599class LikeProperty(Property):
2600    arg_types = {"this": True, "expressions": False}
arg_types = {'this': True, 'expressions': False}
key = 'likeproperty'
class LocationProperty(Property):
2603class LocationProperty(Property):
2604    arg_types = {"this": True}
arg_types = {'this': True}
key = 'locationproperty'
class LockProperty(Property):
2607class LockProperty(Property):
2608    arg_types = {"this": True}
arg_types = {'this': True}
key = 'lockproperty'
class LockingProperty(Property):
2611class LockingProperty(Property):
2612    arg_types = {
2613        "this": False,
2614        "kind": True,
2615        "for_or_in": False,
2616        "lock_type": True,
2617        "override": False,
2618    }
arg_types = {'this': False, 'kind': True, 'for_or_in': False, 'lock_type': True, 'override': False}
key = 'lockingproperty'
class LogProperty(Property):
2621class LogProperty(Property):
2622    arg_types = {"no": True}
arg_types = {'no': True}
key = 'logproperty'
class MaterializedProperty(Property):
2625class MaterializedProperty(Property):
2626    arg_types = {"this": False}
arg_types = {'this': False}
key = 'materializedproperty'
class MergeBlockRatioProperty(Property):
2629class MergeBlockRatioProperty(Property):
2630    arg_types = {"this": False, "no": False, "default": False, "percent": False}
arg_types = {'this': False, 'no': False, 'default': False, 'percent': False}
key = 'mergeblockratioproperty'
class NoPrimaryIndexProperty(Property):
2633class NoPrimaryIndexProperty(Property):
2634    arg_types = {}
arg_types = {}
key = 'noprimaryindexproperty'
class OnProperty(Property):
2637class OnProperty(Property):
2638    arg_types = {"this": True}
arg_types = {'this': True}
key = 'onproperty'
class OnCommitProperty(Property):
2641class OnCommitProperty(Property):
2642    arg_types = {"delete": False}
arg_types = {'delete': False}
key = 'oncommitproperty'
class PartitionedByProperty(Property):
2645class PartitionedByProperty(Property):
2646    arg_types = {"this": True}
arg_types = {'this': True}
key = 'partitionedbyproperty'
class PartitionBoundSpec(Expression):
2650class PartitionBoundSpec(Expression):
2651    # this -> IN / MODULUS, expression -> REMAINDER, from_expressions -> FROM (...), to_expressions -> TO (...)
2652    arg_types = {
2653        "this": False,
2654        "expression": False,
2655        "from_expressions": False,
2656        "to_expressions": False,
2657    }
arg_types = {'this': False, 'expression': False, 'from_expressions': False, 'to_expressions': False}
key = 'partitionboundspec'
class PartitionedOfProperty(Property):
2660class PartitionedOfProperty(Property):
2661    # this -> parent_table (schema), expression -> FOR VALUES ... / DEFAULT
2662    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'partitionedofproperty'
class RemoteWithConnectionModelProperty(Property):
2665class RemoteWithConnectionModelProperty(Property):
2666    arg_types = {"this": True}
arg_types = {'this': True}
key = 'remotewithconnectionmodelproperty'
class ReturnsProperty(Property):
2669class ReturnsProperty(Property):
2670    arg_types = {"this": True, "is_table": False, "table": False}
arg_types = {'this': True, 'is_table': False, 'table': False}
key = 'returnsproperty'
class RowFormatProperty(Property):
2673class RowFormatProperty(Property):
2674    arg_types = {"this": True}
arg_types = {'this': True}
key = 'rowformatproperty'
class RowFormatDelimitedProperty(Property):
2677class RowFormatDelimitedProperty(Property):
2678    # https://cwiki.apache.org/confluence/display/hive/languagemanual+dml
2679    arg_types = {
2680        "fields": False,
2681        "escaped": False,
2682        "collection_items": False,
2683        "map_keys": False,
2684        "lines": False,
2685        "null": False,
2686        "serde": False,
2687    }
arg_types = {'fields': False, 'escaped': False, 'collection_items': False, 'map_keys': False, 'lines': False, 'null': False, 'serde': False}
key = 'rowformatdelimitedproperty'
class RowFormatSerdeProperty(Property):
2690class RowFormatSerdeProperty(Property):
2691    arg_types = {"this": True, "serde_properties": False}
arg_types = {'this': True, 'serde_properties': False}
key = 'rowformatserdeproperty'
class QueryTransform(Expression):
2695class QueryTransform(Expression):
2696    arg_types = {
2697        "expressions": True,
2698        "command_script": True,
2699        "schema": False,
2700        "row_format_before": False,
2701        "record_writer": False,
2702        "row_format_after": False,
2703        "record_reader": False,
2704    }
arg_types = {'expressions': True, 'command_script': True, 'schema': False, 'row_format_before': False, 'record_writer': False, 'row_format_after': False, 'record_reader': False}
key = 'querytransform'
class SampleProperty(Property):
2707class SampleProperty(Property):
2708    arg_types = {"this": True}
arg_types = {'this': True}
key = 'sampleproperty'
class SchemaCommentProperty(Property):
2711class SchemaCommentProperty(Property):
2712    arg_types = {"this": True}
arg_types = {'this': True}
key = 'schemacommentproperty'
class SerdeProperties(Property):
2715class SerdeProperties(Property):
2716    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'serdeproperties'
class SetProperty(Property):
2719class SetProperty(Property):
2720    arg_types = {"multi": True}
arg_types = {'multi': True}
key = 'setproperty'
class SharingProperty(Property):
2723class SharingProperty(Property):
2724    arg_types = {"this": False}
arg_types = {'this': False}
key = 'sharingproperty'
class SetConfigProperty(Property):
2727class SetConfigProperty(Property):
2728    arg_types = {"this": True}
arg_types = {'this': True}
key = 'setconfigproperty'
class SettingsProperty(Property):
2731class SettingsProperty(Property):
2732    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'settingsproperty'
class SortKeyProperty(Property):
2735class SortKeyProperty(Property):
2736    arg_types = {"this": True, "compound": False}
arg_types = {'this': True, 'compound': False}
key = 'sortkeyproperty'
class SqlReadWriteProperty(Property):
2739class SqlReadWriteProperty(Property):
2740    arg_types = {"this": True}
arg_types = {'this': True}
key = 'sqlreadwriteproperty'
class SqlSecurityProperty(Property):
2743class SqlSecurityProperty(Property):
2744    arg_types = {"definer": True}
arg_types = {'definer': True}
key = 'sqlsecurityproperty'
class StabilityProperty(Property):
2747class StabilityProperty(Property):
2748    arg_types = {"this": True}
arg_types = {'this': True}
key = 'stabilityproperty'
class TemporaryProperty(Property):
2751class TemporaryProperty(Property):
2752    arg_types = {"this": False}
arg_types = {'this': False}
key = 'temporaryproperty'
class TransformModelProperty(Property):
2755class TransformModelProperty(Property):
2756    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'transformmodelproperty'
class TransientProperty(Property):
2759class TransientProperty(Property):
2760    arg_types = {"this": False}
arg_types = {'this': False}
key = 'transientproperty'
class UnloggedProperty(Property):
2763class UnloggedProperty(Property):
2764    arg_types = {}
arg_types = {}
key = 'unloggedproperty'
class ViewAttributeProperty(Property):
2768class ViewAttributeProperty(Property):
2769    arg_types = {"this": True}
arg_types = {'this': True}
key = 'viewattributeproperty'
class VolatileProperty(Property):
2772class VolatileProperty(Property):
2773    arg_types = {"this": False}
arg_types = {'this': False}
key = 'volatileproperty'
class WithDataProperty(Property):
2776class WithDataProperty(Property):
2777    arg_types = {"no": True, "statistics": False}
arg_types = {'no': True, 'statistics': False}
key = 'withdataproperty'
class WithJournalTableProperty(Property):
2780class WithJournalTableProperty(Property):
2781    arg_types = {"this": True}
arg_types = {'this': True}
key = 'withjournaltableproperty'
class WithSystemVersioningProperty(Property):
2784class WithSystemVersioningProperty(Property):
2785    # this -> history table name, expression -> data consistency check
2786    arg_types = {"this": False, "expression": False}
arg_types = {'this': False, 'expression': False}
key = 'withsystemversioningproperty'
class Properties(Expression):
2789class Properties(Expression):
2790    arg_types = {"expressions": True}
2791
2792    NAME_TO_PROPERTY = {
2793        "ALGORITHM": AlgorithmProperty,
2794        "AUTO_INCREMENT": AutoIncrementProperty,
2795        "CHARACTER SET": CharacterSetProperty,
2796        "CLUSTERED_BY": ClusteredByProperty,
2797        "COLLATE": CollateProperty,
2798        "COMMENT": SchemaCommentProperty,
2799        "DEFINER": DefinerProperty,
2800        "DISTKEY": DistKeyProperty,
2801        "DISTSTYLE": DistStyleProperty,
2802        "ENGINE": EngineProperty,
2803        "EXECUTE AS": ExecuteAsProperty,
2804        "FORMAT": FileFormatProperty,
2805        "LANGUAGE": LanguageProperty,
2806        "LOCATION": LocationProperty,
2807        "LOCK": LockProperty,
2808        "PARTITIONED_BY": PartitionedByProperty,
2809        "RETURNS": ReturnsProperty,
2810        "ROW_FORMAT": RowFormatProperty,
2811        "SORTKEY": SortKeyProperty,
2812    }
2813
2814    PROPERTY_TO_NAME = {v: k for k, v in NAME_TO_PROPERTY.items()}
2815
2816    # CREATE property locations
2817    # Form: schema specified
2818    #   create [POST_CREATE]
2819    #     table a [POST_NAME]
2820    #     (b int) [POST_SCHEMA]
2821    #     with ([POST_WITH])
2822    #     index (b) [POST_INDEX]
2823    #
2824    # Form: alias selection
2825    #   create [POST_CREATE]
2826    #     table a [POST_NAME]
2827    #     as [POST_ALIAS] (select * from b) [POST_EXPRESSION]
2828    #     index (c) [POST_INDEX]
2829    class Location(AutoName):
2830        POST_CREATE = auto()
2831        POST_NAME = auto()
2832        POST_SCHEMA = auto()
2833        POST_WITH = auto()
2834        POST_ALIAS = auto()
2835        POST_EXPRESSION = auto()
2836        POST_INDEX = auto()
2837        UNSUPPORTED = auto()
2838
2839    @classmethod
2840    def from_dict(cls, properties_dict: t.Dict) -> Properties:
2841        expressions = []
2842        for key, value in properties_dict.items():
2843            property_cls = cls.NAME_TO_PROPERTY.get(key.upper())
2844            if property_cls:
2845                expressions.append(property_cls(this=convert(value)))
2846            else:
2847                expressions.append(Property(this=Literal.string(key), value=convert(value)))
2848
2849        return cls(expressions=expressions)
arg_types = {'expressions': True}
NAME_TO_PROPERTY = {'ALGORITHM': <class 'AlgorithmProperty'>, 'AUTO_INCREMENT': <class 'AutoIncrementProperty'>, 'CHARACTER SET': <class 'CharacterSetProperty'>, 'CLUSTERED_BY': <class 'ClusteredByProperty'>, 'COLLATE': <class 'CollateProperty'>, 'COMMENT': <class 'SchemaCommentProperty'>, 'DEFINER': <class 'DefinerProperty'>, 'DISTKEY': <class 'DistKeyProperty'>, 'DISTSTYLE': <class 'DistStyleProperty'>, 'ENGINE': <class 'EngineProperty'>, 'EXECUTE AS': <class 'ExecuteAsProperty'>, 'FORMAT': <class 'FileFormatProperty'>, 'LANGUAGE': <class 'LanguageProperty'>, 'LOCATION': <class 'LocationProperty'>, 'LOCK': <class 'LockProperty'>, 'PARTITIONED_BY': <class 'PartitionedByProperty'>, 'RETURNS': <class 'ReturnsProperty'>, 'ROW_FORMAT': <class 'RowFormatProperty'>, 'SORTKEY': <class 'SortKeyProperty'>}
PROPERTY_TO_NAME = {<class 'AlgorithmProperty'>: 'ALGORITHM', <class 'AutoIncrementProperty'>: 'AUTO_INCREMENT', <class 'CharacterSetProperty'>: 'CHARACTER SET', <class 'ClusteredByProperty'>: 'CLUSTERED_BY', <class 'CollateProperty'>: 'COLLATE', <class 'SchemaCommentProperty'>: 'COMMENT', <class 'DefinerProperty'>: 'DEFINER', <class 'DistKeyProperty'>: 'DISTKEY', <class 'DistStyleProperty'>: 'DISTSTYLE', <class 'EngineProperty'>: 'ENGINE', <class 'ExecuteAsProperty'>: 'EXECUTE AS', <class 'FileFormatProperty'>: 'FORMAT', <class 'LanguageProperty'>: 'LANGUAGE', <class 'LocationProperty'>: 'LOCATION', <class 'LockProperty'>: 'LOCK', <class 'PartitionedByProperty'>: 'PARTITIONED_BY', <class 'ReturnsProperty'>: 'RETURNS', <class 'RowFormatProperty'>: 'ROW_FORMAT', <class 'SortKeyProperty'>: 'SORTKEY'}
@classmethod
def from_dict(cls, properties_dict: Dict) -> Properties:
2839    @classmethod
2840    def from_dict(cls, properties_dict: t.Dict) -> Properties:
2841        expressions = []
2842        for key, value in properties_dict.items():
2843            property_cls = cls.NAME_TO_PROPERTY.get(key.upper())
2844            if property_cls:
2845                expressions.append(property_cls(this=convert(value)))
2846            else:
2847                expressions.append(Property(this=Literal.string(key), value=convert(value)))
2848
2849        return cls(expressions=expressions)
key = 'properties'
class Properties.Location(sqlglot.helper.AutoName):
2829    class Location(AutoName):
2830        POST_CREATE = auto()
2831        POST_NAME = auto()
2832        POST_SCHEMA = auto()
2833        POST_WITH = auto()
2834        POST_ALIAS = auto()
2835        POST_EXPRESSION = auto()
2836        POST_INDEX = auto()
2837        UNSUPPORTED = auto()

An enumeration.

POST_CREATE = <Location.POST_CREATE: 'POST_CREATE'>
POST_NAME = <Location.POST_NAME: 'POST_NAME'>
POST_SCHEMA = <Location.POST_SCHEMA: 'POST_SCHEMA'>
POST_WITH = <Location.POST_WITH: 'POST_WITH'>
POST_ALIAS = <Location.POST_ALIAS: 'POST_ALIAS'>
POST_EXPRESSION = <Location.POST_EXPRESSION: 'POST_EXPRESSION'>
POST_INDEX = <Location.POST_INDEX: 'POST_INDEX'>
UNSUPPORTED = <Location.UNSUPPORTED: 'UNSUPPORTED'>
Inherited Members
enum.Enum
name
value
class Qualify(Expression):
2852class Qualify(Expression):
2853    pass
key = 'qualify'
class InputOutputFormat(Expression):
2856class InputOutputFormat(Expression):
2857    arg_types = {"input_format": False, "output_format": False}
arg_types = {'input_format': False, 'output_format': False}
key = 'inputoutputformat'
class Return(Expression):
2861class Return(Expression):
2862    pass
key = 'return'
class Reference(Expression):
2865class Reference(Expression):
2866    arg_types = {"this": True, "expressions": False, "options": False}
arg_types = {'this': True, 'expressions': False, 'options': False}
key = 'reference'
class Tuple(Expression):
2869class Tuple(Expression):
2870    arg_types = {"expressions": False}
2871
2872    def isin(
2873        self,
2874        *expressions: t.Any,
2875        query: t.Optional[ExpOrStr] = None,
2876        unnest: t.Optional[ExpOrStr] | t.Collection[ExpOrStr] = None,
2877        copy: bool = True,
2878        **opts,
2879    ) -> In:
2880        return In(
2881            this=maybe_copy(self, copy),
2882            expressions=[convert(e, copy=copy) for e in expressions],
2883            query=maybe_parse(query, copy=copy, **opts) if query else None,
2884            unnest=(
2885                Unnest(
2886                    expressions=[
2887                        maybe_parse(t.cast(ExpOrStr, e), copy=copy, **opts)
2888                        for e in ensure_list(unnest)
2889                    ]
2890                )
2891                if unnest
2892                else None
2893            ),
2894        )
arg_types = {'expressions': False}
def isin( self, *expressions: Any, query: Union[str, Expression, NoneType] = None, unnest: Union[str, Expression, NoneType, Collection[Union[str, Expression]]] = None, copy: bool = True, **opts) -> In:
2872    def isin(
2873        self,
2874        *expressions: t.Any,
2875        query: t.Optional[ExpOrStr] = None,
2876        unnest: t.Optional[ExpOrStr] | t.Collection[ExpOrStr] = None,
2877        copy: bool = True,
2878        **opts,
2879    ) -> In:
2880        return In(
2881            this=maybe_copy(self, copy),
2882            expressions=[convert(e, copy=copy) for e in expressions],
2883            query=maybe_parse(query, copy=copy, **opts) if query else None,
2884            unnest=(
2885                Unnest(
2886                    expressions=[
2887                        maybe_parse(t.cast(ExpOrStr, e), copy=copy, **opts)
2888                        for e in ensure_list(unnest)
2889                    ]
2890                )
2891                if unnest
2892                else None
2893            ),
2894        )
key = 'tuple'
QUERY_MODIFIERS = {'match': False, 'laterals': False, 'joins': False, 'connect': False, 'pivots': False, 'prewhere': False, 'where': False, 'group': False, 'having': False, 'qualify': False, 'windows': False, 'distribute': False, 'sort': False, 'cluster': False, 'order': False, 'limit': False, 'offset': False, 'locks': False, 'sample': False, 'settings': False, 'format': False, 'options': False}
class QueryOption(Expression):
2925class QueryOption(Expression):
2926    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'queryoption'
class WithTableHint(Expression):
2930class WithTableHint(Expression):
2931    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'withtablehint'
class IndexTableHint(Expression):
2935class IndexTableHint(Expression):
2936    arg_types = {"this": True, "expressions": False, "target": False}
arg_types = {'this': True, 'expressions': False, 'target': False}
key = 'indextablehint'
class HistoricalData(Expression):
2940class HistoricalData(Expression):
2941    arg_types = {"this": True, "kind": True, "expression": True}
arg_types = {'this': True, 'kind': True, 'expression': True}
key = 'historicaldata'
class Table(Expression):
2944class Table(Expression):
2945    arg_types = {
2946        "this": False,
2947        "alias": False,
2948        "db": False,
2949        "catalog": False,
2950        "laterals": False,
2951        "joins": False,
2952        "pivots": False,
2953        "hints": False,
2954        "system_time": False,
2955        "version": False,
2956        "format": False,
2957        "pattern": False,
2958        "ordinality": False,
2959        "when": False,
2960        "only": False,
2961        "partition": False,
2962    }
2963
2964    @property
2965    def name(self) -> str:
2966        if isinstance(self.this, Func):
2967            return ""
2968        return self.this.name
2969
2970    @property
2971    def db(self) -> str:
2972        return self.text("db")
2973
2974    @property
2975    def catalog(self) -> str:
2976        return self.text("catalog")
2977
2978    @property
2979    def selects(self) -> t.List[Expression]:
2980        return []
2981
2982    @property
2983    def named_selects(self) -> t.List[str]:
2984        return []
2985
2986    @property
2987    def parts(self) -> t.List[Expression]:
2988        """Return the parts of a table in order catalog, db, table."""
2989        parts: t.List[Expression] = []
2990
2991        for arg in ("catalog", "db", "this"):
2992            part = self.args.get(arg)
2993
2994            if isinstance(part, Dot):
2995                parts.extend(part.flatten())
2996            elif isinstance(part, Expression):
2997                parts.append(part)
2998
2999        return parts
3000
3001    def to_column(self, copy: bool = True) -> Alias | Column | Dot:
3002        parts = self.parts
3003        col = column(*reversed(parts[0:4]), fields=parts[4:], copy=copy)  # type: ignore
3004        alias = self.args.get("alias")
3005        if alias:
3006            col = alias_(col, alias.this, copy=copy)
3007        return col
arg_types = {'this': False, 'alias': False, 'db': False, 'catalog': False, 'laterals': False, 'joins': False, 'pivots': False, 'hints': False, 'system_time': False, 'version': False, 'format': False, 'pattern': False, 'ordinality': False, 'when': False, 'only': False, 'partition': False}
name: str
2964    @property
2965    def name(self) -> str:
2966        if isinstance(self.this, Func):
2967            return ""
2968        return self.this.name
db: str
2970    @property
2971    def db(self) -> str:
2972        return self.text("db")
catalog: str
2974    @property
2975    def catalog(self) -> str:
2976        return self.text("catalog")
selects: List[Expression]
2978    @property
2979    def selects(self) -> t.List[Expression]:
2980        return []
named_selects: List[str]
2982    @property
2983    def named_selects(self) -> t.List[str]:
2984        return []
parts: List[Expression]
2986    @property
2987    def parts(self) -> t.List[Expression]:
2988        """Return the parts of a table in order catalog, db, table."""
2989        parts: t.List[Expression] = []
2990
2991        for arg in ("catalog", "db", "this"):
2992            part = self.args.get(arg)
2993
2994            if isinstance(part, Dot):
2995                parts.extend(part.flatten())
2996            elif isinstance(part, Expression):
2997                parts.append(part)
2998
2999        return parts

Return the parts of a table in order catalog, db, table.

def to_column( self, copy: bool = True) -> Alias | Column | Dot:
3001    def to_column(self, copy: bool = True) -> Alias | Column | Dot:
3002        parts = self.parts
3003        col = column(*reversed(parts[0:4]), fields=parts[4:], copy=copy)  # type: ignore
3004        alias = self.args.get("alias")
3005        if alias:
3006            col = alias_(col, alias.this, copy=copy)
3007        return col
key = 'table'
class Union(Query):
3010class Union(Query):
3011    arg_types = {
3012        "with": False,
3013        "this": True,
3014        "expression": True,
3015        "distinct": False,
3016        "by_name": False,
3017        **QUERY_MODIFIERS,
3018    }
3019
3020    def select(
3021        self,
3022        *expressions: t.Optional[ExpOrStr],
3023        append: bool = True,
3024        dialect: DialectType = None,
3025        copy: bool = True,
3026        **opts,
3027    ) -> Union:
3028        this = maybe_copy(self, copy)
3029        this.this.unnest().select(*expressions, append=append, dialect=dialect, copy=False, **opts)
3030        this.expression.unnest().select(
3031            *expressions, append=append, dialect=dialect, copy=False, **opts
3032        )
3033        return this
3034
3035    @property
3036    def named_selects(self) -> t.List[str]:
3037        return self.this.unnest().named_selects
3038
3039    @property
3040    def is_star(self) -> bool:
3041        return self.this.is_star or self.expression.is_star
3042
3043    @property
3044    def selects(self) -> t.List[Expression]:
3045        return self.this.unnest().selects
3046
3047    @property
3048    def left(self) -> Expression:
3049        return self.this
3050
3051    @property
3052    def right(self) -> Expression:
3053        return self.expression
arg_types = {'with': False, 'this': True, 'expression': True, 'distinct': False, 'by_name': False, 'match': False, 'laterals': False, 'joins': False, 'connect': False, 'pivots': False, 'prewhere': False, 'where': False, 'group': False, 'having': False, 'qualify': False, 'windows': False, 'distribute': False, 'sort': False, 'cluster': False, 'order': False, 'limit': False, 'offset': False, 'locks': False, 'sample': False, 'settings': False, 'format': False, 'options': False}
def select( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Union:
3020    def select(
3021        self,
3022        *expressions: t.Optional[ExpOrStr],
3023        append: bool = True,
3024        dialect: DialectType = None,
3025        copy: bool = True,
3026        **opts,
3027    ) -> Union:
3028        this = maybe_copy(self, copy)
3029        this.this.unnest().select(*expressions, append=append, dialect=dialect, copy=False, **opts)
3030        this.expression.unnest().select(
3031            *expressions, append=append, dialect=dialect, copy=False, **opts
3032        )
3033        return this

Append to or set the SELECT expressions.

Example:
>>> Select().select("x", "y").sql()
'SELECT x, y'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • append: if True, add to any existing expressions. Otherwise, this resets the expressions.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Query expression.

named_selects: List[str]
3035    @property
3036    def named_selects(self) -> t.List[str]:
3037        return self.this.unnest().named_selects

Returns the output names of the query's projections.

is_star: bool
3039    @property
3040    def is_star(self) -> bool:
3041        return self.this.is_star or self.expression.is_star

Checks whether an expression is a star.

selects: List[Expression]
3043    @property
3044    def selects(self) -> t.List[Expression]:
3045        return self.this.unnest().selects

Returns the query's projections.

left: Expression
3047    @property
3048    def left(self) -> Expression:
3049        return self.this
right: Expression
3051    @property
3052    def right(self) -> Expression:
3053        return self.expression
key = 'union'
class Except(Union):
3056class Except(Union):
3057    pass
key = 'except'
class Intersect(Union):
3060class Intersect(Union):
3061    pass
key = 'intersect'
class Unnest(UDTF):
3064class Unnest(UDTF):
3065    arg_types = {
3066        "expressions": True,
3067        "alias": False,
3068        "offset": False,
3069    }
3070
3071    @property
3072    def selects(self) -> t.List[Expression]:
3073        columns = super().selects
3074        offset = self.args.get("offset")
3075        if offset:
3076            columns = columns + [to_identifier("offset") if offset is True else offset]
3077        return columns
arg_types = {'expressions': True, 'alias': False, 'offset': False}
selects: List[Expression]
3071    @property
3072    def selects(self) -> t.List[Expression]:
3073        columns = super().selects
3074        offset = self.args.get("offset")
3075        if offset:
3076            columns = columns + [to_identifier("offset") if offset is True else offset]
3077        return columns
key = 'unnest'
class Update(Expression):
3080class Update(Expression):
3081    arg_types = {
3082        "with": False,
3083        "this": False,
3084        "expressions": True,
3085        "from": False,
3086        "where": False,
3087        "returning": False,
3088        "order": False,
3089        "limit": False,
3090    }
arg_types = {'with': False, 'this': False, 'expressions': True, 'from': False, 'where': False, 'returning': False, 'order': False, 'limit': False}
key = 'update'
class Values(UDTF):
3093class Values(UDTF):
3094    arg_types = {"expressions": True, "alias": False}
arg_types = {'expressions': True, 'alias': False}
key = 'values'
class Var(Expression):
3097class Var(Expression):
3098    pass
key = 'var'
class Version(Expression):
3101class Version(Expression):
3102    """
3103    Time travel, iceberg, bigquery etc
3104    https://trino.io/docs/current/connector/iceberg.html?highlight=snapshot#using-snapshots
3105    https://www.databricks.com/blog/2019/02/04/introducing-delta-time-travel-for-large-scale-data-lakes.html
3106    https://cloud.google.com/bigquery/docs/reference/standard-sql/query-syntax#for_system_time_as_of
3107    https://learn.microsoft.com/en-us/sql/relational-databases/tables/querying-data-in-a-system-versioned-temporal-table?view=sql-server-ver16
3108    this is either TIMESTAMP or VERSION
3109    kind is ("AS OF", "BETWEEN")
3110    """
3111
3112    arg_types = {"this": True, "kind": True, "expression": False}
arg_types = {'this': True, 'kind': True, 'expression': False}
key = 'version'
class Schema(Expression):
3115class Schema(Expression):
3116    arg_types = {"this": False, "expressions": False}
arg_types = {'this': False, 'expressions': False}
key = 'schema'
class Lock(Expression):
3121class Lock(Expression):
3122    arg_types = {"update": True, "expressions": False, "wait": False}
arg_types = {'update': True, 'expressions': False, 'wait': False}
key = 'lock'
class Select(Query):
3125class Select(Query):
3126    arg_types = {
3127        "with": False,
3128        "kind": False,
3129        "expressions": False,
3130        "hint": False,
3131        "distinct": False,
3132        "into": False,
3133        "from": False,
3134        **QUERY_MODIFIERS,
3135    }
3136
3137    def from_(
3138        self, expression: ExpOrStr, dialect: DialectType = None, copy: bool = True, **opts
3139    ) -> Select:
3140        """
3141        Set the FROM expression.
3142
3143        Example:
3144            >>> Select().from_("tbl").select("x").sql()
3145            'SELECT x FROM tbl'
3146
3147        Args:
3148            expression : the SQL code strings to parse.
3149                If a `From` instance is passed, this is used as-is.
3150                If another `Expression` instance is passed, it will be wrapped in a `From`.
3151            dialect: the dialect used to parse the input expression.
3152            copy: if `False`, modify this expression instance in-place.
3153            opts: other options to use to parse the input expressions.
3154
3155        Returns:
3156            The modified Select expression.
3157        """
3158        return _apply_builder(
3159            expression=expression,
3160            instance=self,
3161            arg="from",
3162            into=From,
3163            prefix="FROM",
3164            dialect=dialect,
3165            copy=copy,
3166            **opts,
3167        )
3168
3169    def group_by(
3170        self,
3171        *expressions: t.Optional[ExpOrStr],
3172        append: bool = True,
3173        dialect: DialectType = None,
3174        copy: bool = True,
3175        **opts,
3176    ) -> Select:
3177        """
3178        Set the GROUP BY expression.
3179
3180        Example:
3181            >>> Select().from_("tbl").select("x", "COUNT(1)").group_by("x").sql()
3182            'SELECT x, COUNT(1) FROM tbl GROUP BY x'
3183
3184        Args:
3185            *expressions: the SQL code strings to parse.
3186                If a `Group` instance is passed, this is used as-is.
3187                If another `Expression` instance is passed, it will be wrapped in a `Group`.
3188                If nothing is passed in then a group by is not applied to the expression
3189            append: if `True`, add to any existing expressions.
3190                Otherwise, this flattens all the `Group` expression into a single expression.
3191            dialect: the dialect used to parse the input expression.
3192            copy: if `False`, modify this expression instance in-place.
3193            opts: other options to use to parse the input expressions.
3194
3195        Returns:
3196            The modified Select expression.
3197        """
3198        if not expressions:
3199            return self if not copy else self.copy()
3200
3201        return _apply_child_list_builder(
3202            *expressions,
3203            instance=self,
3204            arg="group",
3205            append=append,
3206            copy=copy,
3207            prefix="GROUP BY",
3208            into=Group,
3209            dialect=dialect,
3210            **opts,
3211        )
3212
3213    def sort_by(
3214        self,
3215        *expressions: t.Optional[ExpOrStr],
3216        append: bool = True,
3217        dialect: DialectType = None,
3218        copy: bool = True,
3219        **opts,
3220    ) -> Select:
3221        """
3222        Set the SORT BY expression.
3223
3224        Example:
3225            >>> Select().from_("tbl").select("x").sort_by("x DESC").sql(dialect="hive")
3226            'SELECT x FROM tbl SORT BY x DESC'
3227
3228        Args:
3229            *expressions: the SQL code strings to parse.
3230                If a `Group` instance is passed, this is used as-is.
3231                If another `Expression` instance is passed, it will be wrapped in a `SORT`.
3232            append: if `True`, add to any existing expressions.
3233                Otherwise, this flattens all the `Order` expression into a single expression.
3234            dialect: the dialect used to parse the input expression.
3235            copy: if `False`, modify this expression instance in-place.
3236            opts: other options to use to parse the input expressions.
3237
3238        Returns:
3239            The modified Select expression.
3240        """
3241        return _apply_child_list_builder(
3242            *expressions,
3243            instance=self,
3244            arg="sort",
3245            append=append,
3246            copy=copy,
3247            prefix="SORT BY",
3248            into=Sort,
3249            dialect=dialect,
3250            **opts,
3251        )
3252
3253    def cluster_by(
3254        self,
3255        *expressions: t.Optional[ExpOrStr],
3256        append: bool = True,
3257        dialect: DialectType = None,
3258        copy: bool = True,
3259        **opts,
3260    ) -> Select:
3261        """
3262        Set the CLUSTER BY expression.
3263
3264        Example:
3265            >>> Select().from_("tbl").select("x").cluster_by("x DESC").sql(dialect="hive")
3266            'SELECT x FROM tbl CLUSTER BY x DESC'
3267
3268        Args:
3269            *expressions: the SQL code strings to parse.
3270                If a `Group` instance is passed, this is used as-is.
3271                If another `Expression` instance is passed, it will be wrapped in a `Cluster`.
3272            append: if `True`, add to any existing expressions.
3273                Otherwise, this flattens all the `Order` expression into a single expression.
3274            dialect: the dialect used to parse the input expression.
3275            copy: if `False`, modify this expression instance in-place.
3276            opts: other options to use to parse the input expressions.
3277
3278        Returns:
3279            The modified Select expression.
3280        """
3281        return _apply_child_list_builder(
3282            *expressions,
3283            instance=self,
3284            arg="cluster",
3285            append=append,
3286            copy=copy,
3287            prefix="CLUSTER BY",
3288            into=Cluster,
3289            dialect=dialect,
3290            **opts,
3291        )
3292
3293    def select(
3294        self,
3295        *expressions: t.Optional[ExpOrStr],
3296        append: bool = True,
3297        dialect: DialectType = None,
3298        copy: bool = True,
3299        **opts,
3300    ) -> Select:
3301        return _apply_list_builder(
3302            *expressions,
3303            instance=self,
3304            arg="expressions",
3305            append=append,
3306            dialect=dialect,
3307            into=Expression,
3308            copy=copy,
3309            **opts,
3310        )
3311
3312    def lateral(
3313        self,
3314        *expressions: t.Optional[ExpOrStr],
3315        append: bool = True,
3316        dialect: DialectType = None,
3317        copy: bool = True,
3318        **opts,
3319    ) -> Select:
3320        """
3321        Append to or set the LATERAL expressions.
3322
3323        Example:
3324            >>> Select().select("x").lateral("OUTER explode(y) tbl2 AS z").from_("tbl").sql()
3325            'SELECT x FROM tbl LATERAL VIEW OUTER EXPLODE(y) tbl2 AS z'
3326
3327        Args:
3328            *expressions: the SQL code strings to parse.
3329                If an `Expression` instance is passed, it will be used as-is.
3330            append: if `True`, add to any existing expressions.
3331                Otherwise, this resets the expressions.
3332            dialect: the dialect used to parse the input expressions.
3333            copy: if `False`, modify this expression instance in-place.
3334            opts: other options to use to parse the input expressions.
3335
3336        Returns:
3337            The modified Select expression.
3338        """
3339        return _apply_list_builder(
3340            *expressions,
3341            instance=self,
3342            arg="laterals",
3343            append=append,
3344            into=Lateral,
3345            prefix="LATERAL VIEW",
3346            dialect=dialect,
3347            copy=copy,
3348            **opts,
3349        )
3350
3351    def join(
3352        self,
3353        expression: ExpOrStr,
3354        on: t.Optional[ExpOrStr] = None,
3355        using: t.Optional[ExpOrStr | t.Collection[ExpOrStr]] = None,
3356        append: bool = True,
3357        join_type: t.Optional[str] = None,
3358        join_alias: t.Optional[Identifier | str] = None,
3359        dialect: DialectType = None,
3360        copy: bool = True,
3361        **opts,
3362    ) -> Select:
3363        """
3364        Append to or set the JOIN expressions.
3365
3366        Example:
3367            >>> Select().select("*").from_("tbl").join("tbl2", on="tbl1.y = tbl2.y").sql()
3368            'SELECT * FROM tbl JOIN tbl2 ON tbl1.y = tbl2.y'
3369
3370            >>> Select().select("1").from_("a").join("b", using=["x", "y", "z"]).sql()
3371            'SELECT 1 FROM a JOIN b USING (x, y, z)'
3372
3373            Use `join_type` to change the type of join:
3374
3375            >>> Select().select("*").from_("tbl").join("tbl2", on="tbl1.y = tbl2.y", join_type="left outer").sql()
3376            'SELECT * FROM tbl LEFT OUTER JOIN tbl2 ON tbl1.y = tbl2.y'
3377
3378        Args:
3379            expression: the SQL code string to parse.
3380                If an `Expression` instance is passed, it will be used as-is.
3381            on: optionally specify the join "on" criteria as a SQL string.
3382                If an `Expression` instance is passed, it will be used as-is.
3383            using: optionally specify the join "using" criteria as a SQL string.
3384                If an `Expression` instance is passed, it will be used as-is.
3385            append: if `True`, add to any existing expressions.
3386                Otherwise, this resets the expressions.
3387            join_type: if set, alter the parsed join type.
3388            join_alias: an optional alias for the joined source.
3389            dialect: the dialect used to parse the input expressions.
3390            copy: if `False`, modify this expression instance in-place.
3391            opts: other options to use to parse the input expressions.
3392
3393        Returns:
3394            Select: the modified expression.
3395        """
3396        parse_args: t.Dict[str, t.Any] = {"dialect": dialect, **opts}
3397
3398        try:
3399            expression = maybe_parse(expression, into=Join, prefix="JOIN", **parse_args)
3400        except ParseError:
3401            expression = maybe_parse(expression, into=(Join, Expression), **parse_args)
3402
3403        join = expression if isinstance(expression, Join) else Join(this=expression)
3404
3405        if isinstance(join.this, Select):
3406            join.this.replace(join.this.subquery())
3407
3408        if join_type:
3409            method: t.Optional[Token]
3410            side: t.Optional[Token]
3411            kind: t.Optional[Token]
3412
3413            method, side, kind = maybe_parse(join_type, into="JOIN_TYPE", **parse_args)  # type: ignore
3414
3415            if method:
3416                join.set("method", method.text)
3417            if side:
3418                join.set("side", side.text)
3419            if kind:
3420                join.set("kind", kind.text)
3421
3422        if on:
3423            on = and_(*ensure_list(on), dialect=dialect, copy=copy, **opts)
3424            join.set("on", on)
3425
3426        if using:
3427            join = _apply_list_builder(
3428                *ensure_list(using),
3429                instance=join,
3430                arg="using",
3431                append=append,
3432                copy=copy,
3433                into=Identifier,
3434                **opts,
3435            )
3436
3437        if join_alias:
3438            join.set("this", alias_(join.this, join_alias, table=True))
3439
3440        return _apply_list_builder(
3441            join,
3442            instance=self,
3443            arg="joins",
3444            append=append,
3445            copy=copy,
3446            **opts,
3447        )
3448
3449    def where(
3450        self,
3451        *expressions: t.Optional[ExpOrStr],
3452        append: bool = True,
3453        dialect: DialectType = None,
3454        copy: bool = True,
3455        **opts,
3456    ) -> Select:
3457        """
3458        Append to or set the WHERE expressions.
3459
3460        Example:
3461            >>> Select().select("x").from_("tbl").where("x = 'a' OR x < 'b'").sql()
3462            "SELECT x FROM tbl WHERE x = 'a' OR x < 'b'"
3463
3464        Args:
3465            *expressions: the SQL code strings to parse.
3466                If an `Expression` instance is passed, it will be used as-is.
3467                Multiple expressions are combined with an AND operator.
3468            append: if `True`, AND the new expressions to any existing expression.
3469                Otherwise, this resets the expression.
3470            dialect: the dialect used to parse the input expressions.
3471            copy: if `False`, modify this expression instance in-place.
3472            opts: other options to use to parse the input expressions.
3473
3474        Returns:
3475            Select: the modified expression.
3476        """
3477        return _apply_conjunction_builder(
3478            *expressions,
3479            instance=self,
3480            arg="where",
3481            append=append,
3482            into=Where,
3483            dialect=dialect,
3484            copy=copy,
3485            **opts,
3486        )
3487
3488    def having(
3489        self,
3490        *expressions: t.Optional[ExpOrStr],
3491        append: bool = True,
3492        dialect: DialectType = None,
3493        copy: bool = True,
3494        **opts,
3495    ) -> Select:
3496        """
3497        Append to or set the HAVING expressions.
3498
3499        Example:
3500            >>> Select().select("x", "COUNT(y)").from_("tbl").group_by("x").having("COUNT(y) > 3").sql()
3501            'SELECT x, COUNT(y) FROM tbl GROUP BY x HAVING COUNT(y) > 3'
3502
3503        Args:
3504            *expressions: the SQL code strings to parse.
3505                If an `Expression` instance is passed, it will be used as-is.
3506                Multiple expressions are combined with an AND operator.
3507            append: if `True`, AND the new expressions to any existing expression.
3508                Otherwise, this resets the expression.
3509            dialect: the dialect used to parse the input expressions.
3510            copy: if `False`, modify this expression instance in-place.
3511            opts: other options to use to parse the input expressions.
3512
3513        Returns:
3514            The modified Select expression.
3515        """
3516        return _apply_conjunction_builder(
3517            *expressions,
3518            instance=self,
3519            arg="having",
3520            append=append,
3521            into=Having,
3522            dialect=dialect,
3523            copy=copy,
3524            **opts,
3525        )
3526
3527    def window(
3528        self,
3529        *expressions: t.Optional[ExpOrStr],
3530        append: bool = True,
3531        dialect: DialectType = None,
3532        copy: bool = True,
3533        **opts,
3534    ) -> Select:
3535        return _apply_list_builder(
3536            *expressions,
3537            instance=self,
3538            arg="windows",
3539            append=append,
3540            into=Window,
3541            dialect=dialect,
3542            copy=copy,
3543            **opts,
3544        )
3545
3546    def qualify(
3547        self,
3548        *expressions: t.Optional[ExpOrStr],
3549        append: bool = True,
3550        dialect: DialectType = None,
3551        copy: bool = True,
3552        **opts,
3553    ) -> Select:
3554        return _apply_conjunction_builder(
3555            *expressions,
3556            instance=self,
3557            arg="qualify",
3558            append=append,
3559            into=Qualify,
3560            dialect=dialect,
3561            copy=copy,
3562            **opts,
3563        )
3564
3565    def distinct(
3566        self, *ons: t.Optional[ExpOrStr], distinct: bool = True, copy: bool = True
3567    ) -> Select:
3568        """
3569        Set the OFFSET expression.
3570
3571        Example:
3572            >>> Select().from_("tbl").select("x").distinct().sql()
3573            'SELECT DISTINCT x FROM tbl'
3574
3575        Args:
3576            ons: the expressions to distinct on
3577            distinct: whether the Select should be distinct
3578            copy: if `False`, modify this expression instance in-place.
3579
3580        Returns:
3581            Select: the modified expression.
3582        """
3583        instance = maybe_copy(self, copy)
3584        on = Tuple(expressions=[maybe_parse(on, copy=copy) for on in ons if on]) if ons else None
3585        instance.set("distinct", Distinct(on=on) if distinct else None)
3586        return instance
3587
3588    def ctas(
3589        self,
3590        table: ExpOrStr,
3591        properties: t.Optional[t.Dict] = None,
3592        dialect: DialectType = None,
3593        copy: bool = True,
3594        **opts,
3595    ) -> Create:
3596        """
3597        Convert this expression to a CREATE TABLE AS statement.
3598
3599        Example:
3600            >>> Select().select("*").from_("tbl").ctas("x").sql()
3601            'CREATE TABLE x AS SELECT * FROM tbl'
3602
3603        Args:
3604            table: the SQL code string to parse as the table name.
3605                If another `Expression` instance is passed, it will be used as-is.
3606            properties: an optional mapping of table properties
3607            dialect: the dialect used to parse the input table.
3608            copy: if `False`, modify this expression instance in-place.
3609            opts: other options to use to parse the input table.
3610
3611        Returns:
3612            The new Create expression.
3613        """
3614        instance = maybe_copy(self, copy)
3615        table_expression = maybe_parse(table, into=Table, dialect=dialect, **opts)
3616
3617        properties_expression = None
3618        if properties:
3619            properties_expression = Properties.from_dict(properties)
3620
3621        return Create(
3622            this=table_expression,
3623            kind="TABLE",
3624            expression=instance,
3625            properties=properties_expression,
3626        )
3627
3628    def lock(self, update: bool = True, copy: bool = True) -> Select:
3629        """
3630        Set the locking read mode for this expression.
3631
3632        Examples:
3633            >>> Select().select("x").from_("tbl").where("x = 'a'").lock().sql("mysql")
3634            "SELECT x FROM tbl WHERE x = 'a' FOR UPDATE"
3635
3636            >>> Select().select("x").from_("tbl").where("x = 'a'").lock(update=False).sql("mysql")
3637            "SELECT x FROM tbl WHERE x = 'a' FOR SHARE"
3638
3639        Args:
3640            update: if `True`, the locking type will be `FOR UPDATE`, else it will be `FOR SHARE`.
3641            copy: if `False`, modify this expression instance in-place.
3642
3643        Returns:
3644            The modified expression.
3645        """
3646        inst = maybe_copy(self, copy)
3647        inst.set("locks", [Lock(update=update)])
3648
3649        return inst
3650
3651    def hint(self, *hints: ExpOrStr, dialect: DialectType = None, copy: bool = True) -> Select:
3652        """
3653        Set hints for this expression.
3654
3655        Examples:
3656            >>> Select().select("x").from_("tbl").hint("BROADCAST(y)").sql(dialect="spark")
3657            'SELECT /*+ BROADCAST(y) */ x FROM tbl'
3658
3659        Args:
3660            hints: The SQL code strings to parse as the hints.
3661                If an `Expression` instance is passed, it will be used as-is.
3662            dialect: The dialect used to parse the hints.
3663            copy: If `False`, modify this expression instance in-place.
3664
3665        Returns:
3666            The modified expression.
3667        """
3668        inst = maybe_copy(self, copy)
3669        inst.set(
3670            "hint", Hint(expressions=[maybe_parse(h, copy=copy, dialect=dialect) for h in hints])
3671        )
3672
3673        return inst
3674
3675    @property
3676    def named_selects(self) -> t.List[str]:
3677        return [e.output_name for e in self.expressions if e.alias_or_name]
3678
3679    @property
3680    def is_star(self) -> bool:
3681        return any(expression.is_star for expression in self.expressions)
3682
3683    @property
3684    def selects(self) -> t.List[Expression]:
3685        return self.expressions
arg_types = {'with': False, 'kind': False, 'expressions': False, 'hint': False, 'distinct': False, 'into': False, 'from': False, 'match': False, 'laterals': False, 'joins': False, 'connect': False, 'pivots': False, 'prewhere': False, 'where': False, 'group': False, 'having': False, 'qualify': False, 'windows': False, 'distribute': False, 'sort': False, 'cluster': False, 'order': False, 'limit': False, 'offset': False, 'locks': False, 'sample': False, 'settings': False, 'format': False, 'options': False}
def from_( self, expression: Union[str, Expression], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3137    def from_(
3138        self, expression: ExpOrStr, dialect: DialectType = None, copy: bool = True, **opts
3139    ) -> Select:
3140        """
3141        Set the FROM expression.
3142
3143        Example:
3144            >>> Select().from_("tbl").select("x").sql()
3145            'SELECT x FROM tbl'
3146
3147        Args:
3148            expression : the SQL code strings to parse.
3149                If a `From` instance is passed, this is used as-is.
3150                If another `Expression` instance is passed, it will be wrapped in a `From`.
3151            dialect: the dialect used to parse the input expression.
3152            copy: if `False`, modify this expression instance in-place.
3153            opts: other options to use to parse the input expressions.
3154
3155        Returns:
3156            The modified Select expression.
3157        """
3158        return _apply_builder(
3159            expression=expression,
3160            instance=self,
3161            arg="from",
3162            into=From,
3163            prefix="FROM",
3164            dialect=dialect,
3165            copy=copy,
3166            **opts,
3167        )

Set the FROM expression.

Example:
>>> Select().from_("tbl").select("x").sql()
'SELECT x FROM tbl'
Arguments:
  • expression : the SQL code strings to parse. If a From instance is passed, this is used as-is. If another Expression instance is passed, it will be wrapped in a From.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Select expression.

def group_by( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3169    def group_by(
3170        self,
3171        *expressions: t.Optional[ExpOrStr],
3172        append: bool = True,
3173        dialect: DialectType = None,
3174        copy: bool = True,
3175        **opts,
3176    ) -> Select:
3177        """
3178        Set the GROUP BY expression.
3179
3180        Example:
3181            >>> Select().from_("tbl").select("x", "COUNT(1)").group_by("x").sql()
3182            'SELECT x, COUNT(1) FROM tbl GROUP BY x'
3183
3184        Args:
3185            *expressions: the SQL code strings to parse.
3186                If a `Group` instance is passed, this is used as-is.
3187                If another `Expression` instance is passed, it will be wrapped in a `Group`.
3188                If nothing is passed in then a group by is not applied to the expression
3189            append: if `True`, add to any existing expressions.
3190                Otherwise, this flattens all the `Group` expression into a single expression.
3191            dialect: the dialect used to parse the input expression.
3192            copy: if `False`, modify this expression instance in-place.
3193            opts: other options to use to parse the input expressions.
3194
3195        Returns:
3196            The modified Select expression.
3197        """
3198        if not expressions:
3199            return self if not copy else self.copy()
3200
3201        return _apply_child_list_builder(
3202            *expressions,
3203            instance=self,
3204            arg="group",
3205            append=append,
3206            copy=copy,
3207            prefix="GROUP BY",
3208            into=Group,
3209            dialect=dialect,
3210            **opts,
3211        )

Set the GROUP BY expression.

Example:
>>> Select().from_("tbl").select("x", "COUNT(1)").group_by("x").sql()
'SELECT x, COUNT(1) FROM tbl GROUP BY x'
Arguments:
  • *expressions: the SQL code strings to parse. If a Group instance is passed, this is used as-is. If another Expression instance is passed, it will be wrapped in a Group. If nothing is passed in then a group by is not applied to the expression
  • append: if True, add to any existing expressions. Otherwise, this flattens all the Group expression into a single expression.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Select expression.

def sort_by( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3213    def sort_by(
3214        self,
3215        *expressions: t.Optional[ExpOrStr],
3216        append: bool = True,
3217        dialect: DialectType = None,
3218        copy: bool = True,
3219        **opts,
3220    ) -> Select:
3221        """
3222        Set the SORT BY expression.
3223
3224        Example:
3225            >>> Select().from_("tbl").select("x").sort_by("x DESC").sql(dialect="hive")
3226            'SELECT x FROM tbl SORT BY x DESC'
3227
3228        Args:
3229            *expressions: the SQL code strings to parse.
3230                If a `Group` instance is passed, this is used as-is.
3231                If another `Expression` instance is passed, it will be wrapped in a `SORT`.
3232            append: if `True`, add to any existing expressions.
3233                Otherwise, this flattens all the `Order` expression into a single expression.
3234            dialect: the dialect used to parse the input expression.
3235            copy: if `False`, modify this expression instance in-place.
3236            opts: other options to use to parse the input expressions.
3237
3238        Returns:
3239            The modified Select expression.
3240        """
3241        return _apply_child_list_builder(
3242            *expressions,
3243            instance=self,
3244            arg="sort",
3245            append=append,
3246            copy=copy,
3247            prefix="SORT BY",
3248            into=Sort,
3249            dialect=dialect,
3250            **opts,
3251        )

Set the SORT BY expression.

Example:
>>> Select().from_("tbl").select("x").sort_by("x DESC").sql(dialect="hive")
'SELECT x FROM tbl SORT BY x DESC'
Arguments:
  • *expressions: the SQL code strings to parse. If a Group instance is passed, this is used as-is. If another Expression instance is passed, it will be wrapped in a SORT.
  • append: if True, add to any existing expressions. Otherwise, this flattens all the Order expression into a single expression.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Select expression.

def cluster_by( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3253    def cluster_by(
3254        self,
3255        *expressions: t.Optional[ExpOrStr],
3256        append: bool = True,
3257        dialect: DialectType = None,
3258        copy: bool = True,
3259        **opts,
3260    ) -> Select:
3261        """
3262        Set the CLUSTER BY expression.
3263
3264        Example:
3265            >>> Select().from_("tbl").select("x").cluster_by("x DESC").sql(dialect="hive")
3266            'SELECT x FROM tbl CLUSTER BY x DESC'
3267
3268        Args:
3269            *expressions: the SQL code strings to parse.
3270                If a `Group` instance is passed, this is used as-is.
3271                If another `Expression` instance is passed, it will be wrapped in a `Cluster`.
3272            append: if `True`, add to any existing expressions.
3273                Otherwise, this flattens all the `Order` expression into a single expression.
3274            dialect: the dialect used to parse the input expression.
3275            copy: if `False`, modify this expression instance in-place.
3276            opts: other options to use to parse the input expressions.
3277
3278        Returns:
3279            The modified Select expression.
3280        """
3281        return _apply_child_list_builder(
3282            *expressions,
3283            instance=self,
3284            arg="cluster",
3285            append=append,
3286            copy=copy,
3287            prefix="CLUSTER BY",
3288            into=Cluster,
3289            dialect=dialect,
3290            **opts,
3291        )

Set the CLUSTER BY expression.

Example:
>>> Select().from_("tbl").select("x").cluster_by("x DESC").sql(dialect="hive")
'SELECT x FROM tbl CLUSTER BY x DESC'
Arguments:
  • *expressions: the SQL code strings to parse. If a Group instance is passed, this is used as-is. If another Expression instance is passed, it will be wrapped in a Cluster.
  • append: if True, add to any existing expressions. Otherwise, this flattens all the Order expression into a single expression.
  • dialect: the dialect used to parse the input expression.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Select expression.

def select( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3293    def select(
3294        self,
3295        *expressions: t.Optional[ExpOrStr],
3296        append: bool = True,
3297        dialect: DialectType = None,
3298        copy: bool = True,
3299        **opts,
3300    ) -> Select:
3301        return _apply_list_builder(
3302            *expressions,
3303            instance=self,
3304            arg="expressions",
3305            append=append,
3306            dialect=dialect,
3307            into=Expression,
3308            copy=copy,
3309            **opts,
3310        )

Append to or set the SELECT expressions.

Example:
>>> Select().select("x", "y").sql()
'SELECT x, y'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • append: if True, add to any existing expressions. Otherwise, this resets the expressions.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Query expression.

def lateral( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3312    def lateral(
3313        self,
3314        *expressions: t.Optional[ExpOrStr],
3315        append: bool = True,
3316        dialect: DialectType = None,
3317        copy: bool = True,
3318        **opts,
3319    ) -> Select:
3320        """
3321        Append to or set the LATERAL expressions.
3322
3323        Example:
3324            >>> Select().select("x").lateral("OUTER explode(y) tbl2 AS z").from_("tbl").sql()
3325            'SELECT x FROM tbl LATERAL VIEW OUTER EXPLODE(y) tbl2 AS z'
3326
3327        Args:
3328            *expressions: the SQL code strings to parse.
3329                If an `Expression` instance is passed, it will be used as-is.
3330            append: if `True`, add to any existing expressions.
3331                Otherwise, this resets the expressions.
3332            dialect: the dialect used to parse the input expressions.
3333            copy: if `False`, modify this expression instance in-place.
3334            opts: other options to use to parse the input expressions.
3335
3336        Returns:
3337            The modified Select expression.
3338        """
3339        return _apply_list_builder(
3340            *expressions,
3341            instance=self,
3342            arg="laterals",
3343            append=append,
3344            into=Lateral,
3345            prefix="LATERAL VIEW",
3346            dialect=dialect,
3347            copy=copy,
3348            **opts,
3349        )

Append to or set the LATERAL expressions.

Example:
>>> Select().select("x").lateral("OUTER explode(y) tbl2 AS z").from_("tbl").sql()
'SELECT x FROM tbl LATERAL VIEW OUTER EXPLODE(y) tbl2 AS z'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • append: if True, add to any existing expressions. Otherwise, this resets the expressions.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Select expression.

def join( self, expression: Union[str, Expression], on: Union[str, Expression, NoneType] = None, using: Union[str, Expression, Collection[Union[str, Expression]], NoneType] = None, append: bool = True, join_type: Optional[str] = None, join_alias: Union[Identifier, str, NoneType] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3351    def join(
3352        self,
3353        expression: ExpOrStr,
3354        on: t.Optional[ExpOrStr] = None,
3355        using: t.Optional[ExpOrStr | t.Collection[ExpOrStr]] = None,
3356        append: bool = True,
3357        join_type: t.Optional[str] = None,
3358        join_alias: t.Optional[Identifier | str] = None,
3359        dialect: DialectType = None,
3360        copy: bool = True,
3361        **opts,
3362    ) -> Select:
3363        """
3364        Append to or set the JOIN expressions.
3365
3366        Example:
3367            >>> Select().select("*").from_("tbl").join("tbl2", on="tbl1.y = tbl2.y").sql()
3368            'SELECT * FROM tbl JOIN tbl2 ON tbl1.y = tbl2.y'
3369
3370            >>> Select().select("1").from_("a").join("b", using=["x", "y", "z"]).sql()
3371            'SELECT 1 FROM a JOIN b USING (x, y, z)'
3372
3373            Use `join_type` to change the type of join:
3374
3375            >>> Select().select("*").from_("tbl").join("tbl2", on="tbl1.y = tbl2.y", join_type="left outer").sql()
3376            'SELECT * FROM tbl LEFT OUTER JOIN tbl2 ON tbl1.y = tbl2.y'
3377
3378        Args:
3379            expression: the SQL code string to parse.
3380                If an `Expression` instance is passed, it will be used as-is.
3381            on: optionally specify the join "on" criteria as a SQL string.
3382                If an `Expression` instance is passed, it will be used as-is.
3383            using: optionally specify the join "using" criteria as a SQL string.
3384                If an `Expression` instance is passed, it will be used as-is.
3385            append: if `True`, add to any existing expressions.
3386                Otherwise, this resets the expressions.
3387            join_type: if set, alter the parsed join type.
3388            join_alias: an optional alias for the joined source.
3389            dialect: the dialect used to parse the input expressions.
3390            copy: if `False`, modify this expression instance in-place.
3391            opts: other options to use to parse the input expressions.
3392
3393        Returns:
3394            Select: the modified expression.
3395        """
3396        parse_args: t.Dict[str, t.Any] = {"dialect": dialect, **opts}
3397
3398        try:
3399            expression = maybe_parse(expression, into=Join, prefix="JOIN", **parse_args)
3400        except ParseError:
3401            expression = maybe_parse(expression, into=(Join, Expression), **parse_args)
3402
3403        join = expression if isinstance(expression, Join) else Join(this=expression)
3404
3405        if isinstance(join.this, Select):
3406            join.this.replace(join.this.subquery())
3407
3408        if join_type:
3409            method: t.Optional[Token]
3410            side: t.Optional[Token]
3411            kind: t.Optional[Token]
3412
3413            method, side, kind = maybe_parse(join_type, into="JOIN_TYPE", **parse_args)  # type: ignore
3414
3415            if method:
3416                join.set("method", method.text)
3417            if side:
3418                join.set("side", side.text)
3419            if kind:
3420                join.set("kind", kind.text)
3421
3422        if on:
3423            on = and_(*ensure_list(on), dialect=dialect, copy=copy, **opts)
3424            join.set("on", on)
3425
3426        if using:
3427            join = _apply_list_builder(
3428                *ensure_list(using),
3429                instance=join,
3430                arg="using",
3431                append=append,
3432                copy=copy,
3433                into=Identifier,
3434                **opts,
3435            )
3436
3437        if join_alias:
3438            join.set("this", alias_(join.this, join_alias, table=True))
3439
3440        return _apply_list_builder(
3441            join,
3442            instance=self,
3443            arg="joins",
3444            append=append,
3445            copy=copy,
3446            **opts,
3447        )

Append to or set the JOIN expressions.

Example:
>>> Select().select("*").from_("tbl").join("tbl2", on="tbl1.y = tbl2.y").sql()
'SELECT * FROM tbl JOIN tbl2 ON tbl1.y = tbl2.y'
>>> Select().select("1").from_("a").join("b", using=["x", "y", "z"]).sql()
'SELECT 1 FROM a JOIN b USING (x, y, z)'

Use join_type to change the type of join:

>>> Select().select("*").from_("tbl").join("tbl2", on="tbl1.y = tbl2.y", join_type="left outer").sql()
'SELECT * FROM tbl LEFT OUTER JOIN tbl2 ON tbl1.y = tbl2.y'
Arguments:
  • expression: the SQL code string to parse. If an Expression instance is passed, it will be used as-is.
  • on: optionally specify the join "on" criteria as a SQL string. If an Expression instance is passed, it will be used as-is.
  • using: optionally specify the join "using" criteria as a SQL string. If an Expression instance is passed, it will be used as-is.
  • append: if True, add to any existing expressions. Otherwise, this resets the expressions.
  • join_type: if set, alter the parsed join type.
  • join_alias: an optional alias for the joined source.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

Select: the modified expression.

def where( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3449    def where(
3450        self,
3451        *expressions: t.Optional[ExpOrStr],
3452        append: bool = True,
3453        dialect: DialectType = None,
3454        copy: bool = True,
3455        **opts,
3456    ) -> Select:
3457        """
3458        Append to or set the WHERE expressions.
3459
3460        Example:
3461            >>> Select().select("x").from_("tbl").where("x = 'a' OR x < 'b'").sql()
3462            "SELECT x FROM tbl WHERE x = 'a' OR x < 'b'"
3463
3464        Args:
3465            *expressions: the SQL code strings to parse.
3466                If an `Expression` instance is passed, it will be used as-is.
3467                Multiple expressions are combined with an AND operator.
3468            append: if `True`, AND the new expressions to any existing expression.
3469                Otherwise, this resets the expression.
3470            dialect: the dialect used to parse the input expressions.
3471            copy: if `False`, modify this expression instance in-place.
3472            opts: other options to use to parse the input expressions.
3473
3474        Returns:
3475            Select: the modified expression.
3476        """
3477        return _apply_conjunction_builder(
3478            *expressions,
3479            instance=self,
3480            arg="where",
3481            append=append,
3482            into=Where,
3483            dialect=dialect,
3484            copy=copy,
3485            **opts,
3486        )

Append to or set the WHERE expressions.

Example:
>>> Select().select("x").from_("tbl").where("x = 'a' OR x < 'b'").sql()
"SELECT x FROM tbl WHERE x = 'a' OR x < 'b'"
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is. Multiple expressions are combined with an AND operator.
  • append: if True, AND the new expressions to any existing expression. Otherwise, this resets the expression.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

Select: the modified expression.

def having( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3488    def having(
3489        self,
3490        *expressions: t.Optional[ExpOrStr],
3491        append: bool = True,
3492        dialect: DialectType = None,
3493        copy: bool = True,
3494        **opts,
3495    ) -> Select:
3496        """
3497        Append to or set the HAVING expressions.
3498
3499        Example:
3500            >>> Select().select("x", "COUNT(y)").from_("tbl").group_by("x").having("COUNT(y) > 3").sql()
3501            'SELECT x, COUNT(y) FROM tbl GROUP BY x HAVING COUNT(y) > 3'
3502
3503        Args:
3504            *expressions: the SQL code strings to parse.
3505                If an `Expression` instance is passed, it will be used as-is.
3506                Multiple expressions are combined with an AND operator.
3507            append: if `True`, AND the new expressions to any existing expression.
3508                Otherwise, this resets the expression.
3509            dialect: the dialect used to parse the input expressions.
3510            copy: if `False`, modify this expression instance in-place.
3511            opts: other options to use to parse the input expressions.
3512
3513        Returns:
3514            The modified Select expression.
3515        """
3516        return _apply_conjunction_builder(
3517            *expressions,
3518            instance=self,
3519            arg="having",
3520            append=append,
3521            into=Having,
3522            dialect=dialect,
3523            copy=copy,
3524            **opts,
3525        )

Append to or set the HAVING expressions.

Example:
>>> Select().select("x", "COUNT(y)").from_("tbl").group_by("x").having("COUNT(y) > 3").sql()
'SELECT x, COUNT(y) FROM tbl GROUP BY x HAVING COUNT(y) > 3'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is. Multiple expressions are combined with an AND operator.
  • append: if True, AND the new expressions to any existing expression. Otherwise, this resets the expression.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Select expression.

def window( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3527    def window(
3528        self,
3529        *expressions: t.Optional[ExpOrStr],
3530        append: bool = True,
3531        dialect: DialectType = None,
3532        copy: bool = True,
3533        **opts,
3534    ) -> Select:
3535        return _apply_list_builder(
3536            *expressions,
3537            instance=self,
3538            arg="windows",
3539            append=append,
3540            into=Window,
3541            dialect=dialect,
3542            copy=copy,
3543            **opts,
3544        )
def qualify( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Select:
3546    def qualify(
3547        self,
3548        *expressions: t.Optional[ExpOrStr],
3549        append: bool = True,
3550        dialect: DialectType = None,
3551        copy: bool = True,
3552        **opts,
3553    ) -> Select:
3554        return _apply_conjunction_builder(
3555            *expressions,
3556            instance=self,
3557            arg="qualify",
3558            append=append,
3559            into=Qualify,
3560            dialect=dialect,
3561            copy=copy,
3562            **opts,
3563        )
def distinct( self, *ons: Union[str, Expression, NoneType], distinct: bool = True, copy: bool = True) -> Select:
3565    def distinct(
3566        self, *ons: t.Optional[ExpOrStr], distinct: bool = True, copy: bool = True
3567    ) -> Select:
3568        """
3569        Set the OFFSET expression.
3570
3571        Example:
3572            >>> Select().from_("tbl").select("x").distinct().sql()
3573            'SELECT DISTINCT x FROM tbl'
3574
3575        Args:
3576            ons: the expressions to distinct on
3577            distinct: whether the Select should be distinct
3578            copy: if `False`, modify this expression instance in-place.
3579
3580        Returns:
3581            Select: the modified expression.
3582        """
3583        instance = maybe_copy(self, copy)
3584        on = Tuple(expressions=[maybe_parse(on, copy=copy) for on in ons if on]) if ons else None
3585        instance.set("distinct", Distinct(on=on) if distinct else None)
3586        return instance

Set the OFFSET expression.

Example:
>>> Select().from_("tbl").select("x").distinct().sql()
'SELECT DISTINCT x FROM tbl'
Arguments:
  • ons: the expressions to distinct on
  • distinct: whether the Select should be distinct
  • copy: if False, modify this expression instance in-place.
Returns:

Select: the modified expression.

def ctas( self, table: Union[str, Expression], properties: Optional[Dict] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Create:
3588    def ctas(
3589        self,
3590        table: ExpOrStr,
3591        properties: t.Optional[t.Dict] = None,
3592        dialect: DialectType = None,
3593        copy: bool = True,
3594        **opts,
3595    ) -> Create:
3596        """
3597        Convert this expression to a CREATE TABLE AS statement.
3598
3599        Example:
3600            >>> Select().select("*").from_("tbl").ctas("x").sql()
3601            'CREATE TABLE x AS SELECT * FROM tbl'
3602
3603        Args:
3604            table: the SQL code string to parse as the table name.
3605                If another `Expression` instance is passed, it will be used as-is.
3606            properties: an optional mapping of table properties
3607            dialect: the dialect used to parse the input table.
3608            copy: if `False`, modify this expression instance in-place.
3609            opts: other options to use to parse the input table.
3610
3611        Returns:
3612            The new Create expression.
3613        """
3614        instance = maybe_copy(self, copy)
3615        table_expression = maybe_parse(table, into=Table, dialect=dialect, **opts)
3616
3617        properties_expression = None
3618        if properties:
3619            properties_expression = Properties.from_dict(properties)
3620
3621        return Create(
3622            this=table_expression,
3623            kind="TABLE",
3624            expression=instance,
3625            properties=properties_expression,
3626        )

Convert this expression to a CREATE TABLE AS statement.

Example:
>>> Select().select("*").from_("tbl").ctas("x").sql()
'CREATE TABLE x AS SELECT * FROM tbl'
Arguments:
  • table: the SQL code string to parse as the table name. If another Expression instance is passed, it will be used as-is.
  • properties: an optional mapping of table properties
  • dialect: the dialect used to parse the input table.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input table.
Returns:

The new Create expression.

def lock( self, update: bool = True, copy: bool = True) -> Select:
3628    def lock(self, update: bool = True, copy: bool = True) -> Select:
3629        """
3630        Set the locking read mode for this expression.
3631
3632        Examples:
3633            >>> Select().select("x").from_("tbl").where("x = 'a'").lock().sql("mysql")
3634            "SELECT x FROM tbl WHERE x = 'a' FOR UPDATE"
3635
3636            >>> Select().select("x").from_("tbl").where("x = 'a'").lock(update=False).sql("mysql")
3637            "SELECT x FROM tbl WHERE x = 'a' FOR SHARE"
3638
3639        Args:
3640            update: if `True`, the locking type will be `FOR UPDATE`, else it will be `FOR SHARE`.
3641            copy: if `False`, modify this expression instance in-place.
3642
3643        Returns:
3644            The modified expression.
3645        """
3646        inst = maybe_copy(self, copy)
3647        inst.set("locks", [Lock(update=update)])
3648
3649        return inst

Set the locking read mode for this expression.

Examples:
>>> Select().select("x").from_("tbl").where("x = 'a'").lock().sql("mysql")
"SELECT x FROM tbl WHERE x = 'a' FOR UPDATE"
>>> Select().select("x").from_("tbl").where("x = 'a'").lock(update=False).sql("mysql")
"SELECT x FROM tbl WHERE x = 'a' FOR SHARE"
Arguments:
  • update: if True, the locking type will be FOR UPDATE, else it will be FOR SHARE.
  • copy: if False, modify this expression instance in-place.
Returns:

The modified expression.

def hint( self, *hints: Union[str, Expression], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True) -> Select:
3651    def hint(self, *hints: ExpOrStr, dialect: DialectType = None, copy: bool = True) -> Select:
3652        """
3653        Set hints for this expression.
3654
3655        Examples:
3656            >>> Select().select("x").from_("tbl").hint("BROADCAST(y)").sql(dialect="spark")
3657            'SELECT /*+ BROADCAST(y) */ x FROM tbl'
3658
3659        Args:
3660            hints: The SQL code strings to parse as the hints.
3661                If an `Expression` instance is passed, it will be used as-is.
3662            dialect: The dialect used to parse the hints.
3663            copy: If `False`, modify this expression instance in-place.
3664
3665        Returns:
3666            The modified expression.
3667        """
3668        inst = maybe_copy(self, copy)
3669        inst.set(
3670            "hint", Hint(expressions=[maybe_parse(h, copy=copy, dialect=dialect) for h in hints])
3671        )
3672
3673        return inst

Set hints for this expression.

Examples:
>>> Select().select("x").from_("tbl").hint("BROADCAST(y)").sql(dialect="spark")
'SELECT /*+ BROADCAST(y) */ x FROM tbl'
Arguments:
  • hints: The SQL code strings to parse as the hints. If an Expression instance is passed, it will be used as-is.
  • dialect: The dialect used to parse the hints.
  • copy: If False, modify this expression instance in-place.
Returns:

The modified expression.

named_selects: List[str]
3675    @property
3676    def named_selects(self) -> t.List[str]:
3677        return [e.output_name for e in self.expressions if e.alias_or_name]

Returns the output names of the query's projections.

is_star: bool
3679    @property
3680    def is_star(self) -> bool:
3681        return any(expression.is_star for expression in self.expressions)

Checks whether an expression is a star.

selects: List[Expression]
3683    @property
3684    def selects(self) -> t.List[Expression]:
3685        return self.expressions

Returns the query's projections.

key = 'select'
UNWRAPPED_QUERIES = (<class 'Select'>, <class 'Union'>)
class Subquery(DerivedTable, Query):
3691class Subquery(DerivedTable, Query):
3692    arg_types = {
3693        "this": True,
3694        "alias": False,
3695        "with": False,
3696        **QUERY_MODIFIERS,
3697    }
3698
3699    def unnest(self):
3700        """Returns the first non subquery."""
3701        expression = self
3702        while isinstance(expression, Subquery):
3703            expression = expression.this
3704        return expression
3705
3706    def unwrap(self) -> Subquery:
3707        expression = self
3708        while expression.same_parent and expression.is_wrapper:
3709            expression = t.cast(Subquery, expression.parent)
3710        return expression
3711
3712    def select(
3713        self,
3714        *expressions: t.Optional[ExpOrStr],
3715        append: bool = True,
3716        dialect: DialectType = None,
3717        copy: bool = True,
3718        **opts,
3719    ) -> Subquery:
3720        this = maybe_copy(self, copy)
3721        this.unnest().select(*expressions, append=append, dialect=dialect, copy=False, **opts)
3722        return this
3723
3724    @property
3725    def is_wrapper(self) -> bool:
3726        """
3727        Whether this Subquery acts as a simple wrapper around another expression.
3728
3729        SELECT * FROM (((SELECT * FROM t)))
3730                      ^
3731                      This corresponds to a "wrapper" Subquery node
3732        """
3733        return all(v is None for k, v in self.args.items() if k != "this")
3734
3735    @property
3736    def is_star(self) -> bool:
3737        return self.this.is_star
3738
3739    @property
3740    def output_name(self) -> str:
3741        return self.alias
arg_types = {'this': True, 'alias': False, 'with': False, 'match': False, 'laterals': False, 'joins': False, 'connect': False, 'pivots': False, 'prewhere': False, 'where': False, 'group': False, 'having': False, 'qualify': False, 'windows': False, 'distribute': False, 'sort': False, 'cluster': False, 'order': False, 'limit': False, 'offset': False, 'locks': False, 'sample': False, 'settings': False, 'format': False, 'options': False}
def unnest(self):
3699    def unnest(self):
3700        """Returns the first non subquery."""
3701        expression = self
3702        while isinstance(expression, Subquery):
3703            expression = expression.this
3704        return expression

Returns the first non subquery.

def unwrap(self) -> Subquery:
3706    def unwrap(self) -> Subquery:
3707        expression = self
3708        while expression.same_parent and expression.is_wrapper:
3709            expression = t.cast(Subquery, expression.parent)
3710        return expression
def select( self, *expressions: Union[str, Expression, NoneType], append: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Subquery:
3712    def select(
3713        self,
3714        *expressions: t.Optional[ExpOrStr],
3715        append: bool = True,
3716        dialect: DialectType = None,
3717        copy: bool = True,
3718        **opts,
3719    ) -> Subquery:
3720        this = maybe_copy(self, copy)
3721        this.unnest().select(*expressions, append=append, dialect=dialect, copy=False, **opts)
3722        return this

Append to or set the SELECT expressions.

Example:
>>> Select().select("x", "y").sql()
'SELECT x, y'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, it will be used as-is.
  • append: if True, add to any existing expressions. Otherwise, this resets the expressions.
  • dialect: the dialect used to parse the input expressions.
  • copy: if False, modify this expression instance in-place.
  • opts: other options to use to parse the input expressions.
Returns:

The modified Query expression.

is_wrapper: bool
3724    @property
3725    def is_wrapper(self) -> bool:
3726        """
3727        Whether this Subquery acts as a simple wrapper around another expression.
3728
3729        SELECT * FROM (((SELECT * FROM t)))
3730                      ^
3731                      This corresponds to a "wrapper" Subquery node
3732        """
3733        return all(v is None for k, v in self.args.items() if k != "this")

Whether this Subquery acts as a simple wrapper around another expression.

SELECT * FROM (((SELECT * FROM t))) ^ This corresponds to a "wrapper" Subquery node

is_star: bool
3735    @property
3736    def is_star(self) -> bool:
3737        return self.this.is_star

Checks whether an expression is a star.

output_name: str
3739    @property
3740    def output_name(self) -> str:
3741        return self.alias

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'subquery'
class TableSample(Expression):
3744class TableSample(Expression):
3745    arg_types = {
3746        "this": False,
3747        "expressions": False,
3748        "method": False,
3749        "bucket_numerator": False,
3750        "bucket_denominator": False,
3751        "bucket_field": False,
3752        "percent": False,
3753        "rows": False,
3754        "size": False,
3755        "seed": False,
3756    }
arg_types = {'this': False, 'expressions': False, 'method': False, 'bucket_numerator': False, 'bucket_denominator': False, 'bucket_field': False, 'percent': False, 'rows': False, 'size': False, 'seed': False}
key = 'tablesample'
class Tag(Expression):
3759class Tag(Expression):
3760    """Tags are used for generating arbitrary sql like SELECT <span>x</span>."""
3761
3762    arg_types = {
3763        "this": False,
3764        "prefix": False,
3765        "postfix": False,
3766    }

Tags are used for generating arbitrary sql like SELECT x.

arg_types = {'this': False, 'prefix': False, 'postfix': False}
key = 'tag'
class Pivot(Expression):
3771class Pivot(Expression):
3772    arg_types = {
3773        "this": False,
3774        "alias": False,
3775        "expressions": False,
3776        "field": False,
3777        "unpivot": False,
3778        "using": False,
3779        "group": False,
3780        "columns": False,
3781        "include_nulls": False,
3782    }
3783
3784    @property
3785    def unpivot(self) -> bool:
3786        return bool(self.args.get("unpivot"))
arg_types = {'this': False, 'alias': False, 'expressions': False, 'field': False, 'unpivot': False, 'using': False, 'group': False, 'columns': False, 'include_nulls': False}
unpivot: bool
3784    @property
3785    def unpivot(self) -> bool:
3786        return bool(self.args.get("unpivot"))
key = 'pivot'
class Window(Condition):
3789class Window(Condition):
3790    arg_types = {
3791        "this": True,
3792        "partition_by": False,
3793        "order": False,
3794        "spec": False,
3795        "alias": False,
3796        "over": False,
3797        "first": False,
3798    }
arg_types = {'this': True, 'partition_by': False, 'order': False, 'spec': False, 'alias': False, 'over': False, 'first': False}
key = 'window'
class WindowSpec(Expression):
3801class WindowSpec(Expression):
3802    arg_types = {
3803        "kind": False,
3804        "start": False,
3805        "start_side": False,
3806        "end": False,
3807        "end_side": False,
3808    }
arg_types = {'kind': False, 'start': False, 'start_side': False, 'end': False, 'end_side': False}
key = 'windowspec'
class PreWhere(Expression):
3811class PreWhere(Expression):
3812    pass
key = 'prewhere'
class Where(Expression):
3815class Where(Expression):
3816    pass
key = 'where'
class Star(Expression):
3819class Star(Expression):
3820    arg_types = {"except": False, "replace": False}
3821
3822    @property
3823    def name(self) -> str:
3824        return "*"
3825
3826    @property
3827    def output_name(self) -> str:
3828        return self.name
arg_types = {'except': False, 'replace': False}
name: str
3822    @property
3823    def name(self) -> str:
3824        return "*"
output_name: str
3826    @property
3827    def output_name(self) -> str:
3828        return self.name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'star'
class Parameter(Condition):
3831class Parameter(Condition):
3832    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'parameter'
class SessionParameter(Condition):
3835class SessionParameter(Condition):
3836    arg_types = {"this": True, "kind": False}
arg_types = {'this': True, 'kind': False}
key = 'sessionparameter'
class Placeholder(Condition):
3839class Placeholder(Condition):
3840    arg_types = {"this": False, "kind": False}
3841
3842    @property
3843    def name(self) -> str:
3844        return self.this or "?"
arg_types = {'this': False, 'kind': False}
name: str
3842    @property
3843    def name(self) -> str:
3844        return self.this or "?"
key = 'placeholder'
class Null(Condition):
3847class Null(Condition):
3848    arg_types: t.Dict[str, t.Any] = {}
3849
3850    @property
3851    def name(self) -> str:
3852        return "NULL"
arg_types: Dict[str, Any] = {}
name: str
3850    @property
3851    def name(self) -> str:
3852        return "NULL"
key = 'null'
class Boolean(Condition):
3855class Boolean(Condition):
3856    pass
key = 'boolean'
class DataTypeParam(Expression):
3859class DataTypeParam(Expression):
3860    arg_types = {"this": True, "expression": False}
3861
3862    @property
3863    def name(self) -> str:
3864        return self.this.name
arg_types = {'this': True, 'expression': False}
name: str
3862    @property
3863    def name(self) -> str:
3864        return self.this.name
key = 'datatypeparam'
class DataType(Expression):
3867class DataType(Expression):
3868    arg_types = {
3869        "this": True,
3870        "expressions": False,
3871        "nested": False,
3872        "values": False,
3873        "prefix": False,
3874        "kind": False,
3875    }
3876
3877    class Type(AutoName):
3878        ARRAY = auto()
3879        AGGREGATEFUNCTION = auto()
3880        SIMPLEAGGREGATEFUNCTION = auto()
3881        BIGDECIMAL = auto()
3882        BIGINT = auto()
3883        BIGSERIAL = auto()
3884        BINARY = auto()
3885        BIT = auto()
3886        BOOLEAN = auto()
3887        BPCHAR = auto()
3888        CHAR = auto()
3889        DATE = auto()
3890        DATE32 = auto()
3891        DATEMULTIRANGE = auto()
3892        DATERANGE = auto()
3893        DATETIME = auto()
3894        DATETIME64 = auto()
3895        DECIMAL = auto()
3896        DOUBLE = auto()
3897        ENUM = auto()
3898        ENUM8 = auto()
3899        ENUM16 = auto()
3900        FIXEDSTRING = auto()
3901        FLOAT = auto()
3902        GEOGRAPHY = auto()
3903        GEOMETRY = auto()
3904        HLLSKETCH = auto()
3905        HSTORE = auto()
3906        IMAGE = auto()
3907        INET = auto()
3908        INT = auto()
3909        INT128 = auto()
3910        INT256 = auto()
3911        INT4MULTIRANGE = auto()
3912        INT4RANGE = auto()
3913        INT8MULTIRANGE = auto()
3914        INT8RANGE = auto()
3915        INTERVAL = auto()
3916        IPADDRESS = auto()
3917        IPPREFIX = auto()
3918        IPV4 = auto()
3919        IPV6 = auto()
3920        JSON = auto()
3921        JSONB = auto()
3922        LONGBLOB = auto()
3923        LONGTEXT = auto()
3924        LOWCARDINALITY = auto()
3925        MAP = auto()
3926        MEDIUMBLOB = auto()
3927        MEDIUMINT = auto()
3928        MEDIUMTEXT = auto()
3929        MONEY = auto()
3930        NAME = auto()
3931        NCHAR = auto()
3932        NESTED = auto()
3933        NULL = auto()
3934        NULLABLE = auto()
3935        NUMMULTIRANGE = auto()
3936        NUMRANGE = auto()
3937        NVARCHAR = auto()
3938        OBJECT = auto()
3939        ROWVERSION = auto()
3940        SERIAL = auto()
3941        SET = auto()
3942        SMALLINT = auto()
3943        SMALLMONEY = auto()
3944        SMALLSERIAL = auto()
3945        STRUCT = auto()
3946        SUPER = auto()
3947        TEXT = auto()
3948        TINYBLOB = auto()
3949        TINYTEXT = auto()
3950        TIME = auto()
3951        TIMETZ = auto()
3952        TIMESTAMP = auto()
3953        TIMESTAMPNTZ = auto()
3954        TIMESTAMPLTZ = auto()
3955        TIMESTAMPTZ = auto()
3956        TIMESTAMP_S = auto()
3957        TIMESTAMP_MS = auto()
3958        TIMESTAMP_NS = auto()
3959        TINYINT = auto()
3960        TSMULTIRANGE = auto()
3961        TSRANGE = auto()
3962        TSTZMULTIRANGE = auto()
3963        TSTZRANGE = auto()
3964        UBIGINT = auto()
3965        UINT = auto()
3966        UINT128 = auto()
3967        UINT256 = auto()
3968        UMEDIUMINT = auto()
3969        UDECIMAL = auto()
3970        UNIQUEIDENTIFIER = auto()
3971        UNKNOWN = auto()  # Sentinel value, useful for type annotation
3972        USERDEFINED = "USER-DEFINED"
3973        USMALLINT = auto()
3974        UTINYINT = auto()
3975        UUID = auto()
3976        VARBINARY = auto()
3977        VARCHAR = auto()
3978        VARIANT = auto()
3979        XML = auto()
3980        YEAR = auto()
3981        TDIGEST = auto()
3982
3983    STRUCT_TYPES = {
3984        Type.NESTED,
3985        Type.OBJECT,
3986        Type.STRUCT,
3987    }
3988
3989    NESTED_TYPES = {
3990        *STRUCT_TYPES,
3991        Type.ARRAY,
3992        Type.MAP,
3993    }
3994
3995    TEXT_TYPES = {
3996        Type.CHAR,
3997        Type.NCHAR,
3998        Type.NVARCHAR,
3999        Type.TEXT,
4000        Type.VARCHAR,
4001        Type.NAME,
4002    }
4003
4004    SIGNED_INTEGER_TYPES = {
4005        Type.BIGINT,
4006        Type.INT,
4007        Type.INT128,
4008        Type.INT256,
4009        Type.MEDIUMINT,
4010        Type.SMALLINT,
4011        Type.TINYINT,
4012    }
4013
4014    UNSIGNED_INTEGER_TYPES = {
4015        Type.UBIGINT,
4016        Type.UINT,
4017        Type.UINT128,
4018        Type.UINT256,
4019        Type.UMEDIUMINT,
4020        Type.USMALLINT,
4021        Type.UTINYINT,
4022    }
4023
4024    INTEGER_TYPES = {
4025        *SIGNED_INTEGER_TYPES,
4026        *UNSIGNED_INTEGER_TYPES,
4027        Type.BIT,
4028    }
4029
4030    FLOAT_TYPES = {
4031        Type.DOUBLE,
4032        Type.FLOAT,
4033    }
4034
4035    REAL_TYPES = {
4036        *FLOAT_TYPES,
4037        Type.BIGDECIMAL,
4038        Type.DECIMAL,
4039        Type.MONEY,
4040        Type.SMALLMONEY,
4041        Type.UDECIMAL,
4042    }
4043
4044    NUMERIC_TYPES = {
4045        *INTEGER_TYPES,
4046        *REAL_TYPES,
4047    }
4048
4049    TEMPORAL_TYPES = {
4050        Type.DATE,
4051        Type.DATE32,
4052        Type.DATETIME,
4053        Type.DATETIME64,
4054        Type.TIME,
4055        Type.TIMESTAMP,
4056        Type.TIMESTAMPNTZ,
4057        Type.TIMESTAMPLTZ,
4058        Type.TIMESTAMPTZ,
4059        Type.TIMESTAMP_MS,
4060        Type.TIMESTAMP_NS,
4061        Type.TIMESTAMP_S,
4062        Type.TIMETZ,
4063    }
4064
4065    @classmethod
4066    def build(
4067        cls,
4068        dtype: DATA_TYPE,
4069        dialect: DialectType = None,
4070        udt: bool = False,
4071        copy: bool = True,
4072        **kwargs,
4073    ) -> DataType:
4074        """
4075        Constructs a DataType object.
4076
4077        Args:
4078            dtype: the data type of interest.
4079            dialect: the dialect to use for parsing `dtype`, in case it's a string.
4080            udt: when set to True, `dtype` will be used as-is if it can't be parsed into a
4081                DataType, thus creating a user-defined type.
4082            copy: whether to copy the data type.
4083            kwargs: additional arguments to pass in the constructor of DataType.
4084
4085        Returns:
4086            The constructed DataType object.
4087        """
4088        from sqlglot import parse_one
4089
4090        if isinstance(dtype, str):
4091            if dtype.upper() == "UNKNOWN":
4092                return DataType(this=DataType.Type.UNKNOWN, **kwargs)
4093
4094            try:
4095                data_type_exp = parse_one(
4096                    dtype, read=dialect, into=DataType, error_level=ErrorLevel.IGNORE
4097                )
4098            except ParseError:
4099                if udt:
4100                    return DataType(this=DataType.Type.USERDEFINED, kind=dtype, **kwargs)
4101                raise
4102        elif isinstance(dtype, DataType.Type):
4103            data_type_exp = DataType(this=dtype)
4104        elif isinstance(dtype, DataType):
4105            return maybe_copy(dtype, copy)
4106        else:
4107            raise ValueError(f"Invalid data type: {type(dtype)}. Expected str or DataType.Type")
4108
4109        return DataType(**{**data_type_exp.args, **kwargs})
4110
4111    def is_type(self, *dtypes: DATA_TYPE) -> bool:
4112        """
4113        Checks whether this DataType matches one of the provided data types. Nested types or precision
4114        will be compared using "structural equivalence" semantics, so e.g. array<int> != array<float>.
4115
4116        Args:
4117            dtypes: the data types to compare this DataType to.
4118
4119        Returns:
4120            True, if and only if there is a type in `dtypes` which is equal to this DataType.
4121        """
4122        for dtype in dtypes:
4123            other = DataType.build(dtype, copy=False, udt=True)
4124
4125            if (
4126                other.expressions
4127                or self.this == DataType.Type.USERDEFINED
4128                or other.this == DataType.Type.USERDEFINED
4129            ):
4130                matches = self == other
4131            else:
4132                matches = self.this == other.this
4133
4134            if matches:
4135                return True
4136        return False
arg_types = {'this': True, 'expressions': False, 'nested': False, 'values': False, 'prefix': False, 'kind': False}
STRUCT_TYPES = {<Type.NESTED: 'NESTED'>, <Type.OBJECT: 'OBJECT'>, <Type.STRUCT: 'STRUCT'>}
NESTED_TYPES = {<Type.NESTED: 'NESTED'>, <Type.ARRAY: 'ARRAY'>, <Type.STRUCT: 'STRUCT'>, <Type.OBJECT: 'OBJECT'>, <Type.MAP: 'MAP'>}
TEXT_TYPES = {<Type.NVARCHAR: 'NVARCHAR'>, <Type.CHAR: 'CHAR'>, <Type.TEXT: 'TEXT'>, <Type.VARCHAR: 'VARCHAR'>, <Type.NCHAR: 'NCHAR'>, <Type.NAME: 'NAME'>}
SIGNED_INTEGER_TYPES = {<Type.MEDIUMINT: 'MEDIUMINT'>, <Type.INT256: 'INT256'>, <Type.SMALLINT: 'SMALLINT'>, <Type.INT: 'INT'>, <Type.INT128: 'INT128'>, <Type.BIGINT: 'BIGINT'>, <Type.TINYINT: 'TINYINT'>}
UNSIGNED_INTEGER_TYPES = {<Type.UINT256: 'UINT256'>, <Type.UMEDIUMINT: 'UMEDIUMINT'>, <Type.UINT128: 'UINT128'>, <Type.USMALLINT: 'USMALLINT'>, <Type.UBIGINT: 'UBIGINT'>, <Type.UINT: 'UINT'>, <Type.UTINYINT: 'UTINYINT'>}
INTEGER_TYPES = {<Type.UINT256: 'UINT256'>, <Type.UMEDIUMINT: 'UMEDIUMINT'>, <Type.MEDIUMINT: 'MEDIUMINT'>, <Type.INT256: 'INT256'>, <Type.UINT128: 'UINT128'>, <Type.USMALLINT: 'USMALLINT'>, <Type.UBIGINT: 'UBIGINT'>, <Type.SMALLINT: 'SMALLINT'>, <Type.UINT: 'UINT'>, <Type.BIT: 'BIT'>, <Type.INT: 'INT'>, <Type.INT128: 'INT128'>, <Type.UTINYINT: 'UTINYINT'>, <Type.BIGINT: 'BIGINT'>, <Type.TINYINT: 'TINYINT'>}
FLOAT_TYPES = {<Type.DOUBLE: 'DOUBLE'>, <Type.FLOAT: 'FLOAT'>}
REAL_TYPES = {<Type.DECIMAL: 'DECIMAL'>, <Type.MONEY: 'MONEY'>, <Type.DOUBLE: 'DOUBLE'>, <Type.BIGDECIMAL: 'BIGDECIMAL'>, <Type.SMALLMONEY: 'SMALLMONEY'>, <Type.FLOAT: 'FLOAT'>, <Type.UDECIMAL: 'UDECIMAL'>}
NUMERIC_TYPES = {<Type.UINT256: 'UINT256'>, <Type.UMEDIUMINT: 'UMEDIUMINT'>, <Type.DECIMAL: 'DECIMAL'>, <Type.UINT128: 'UINT128'>, <Type.MONEY: 'MONEY'>, <Type.USMALLINT: 'USMALLINT'>, <Type.UBIGINT: 'UBIGINT'>, <Type.SMALLINT: 'SMALLINT'>, <Type.BIT: 'BIT'>, <Type.FLOAT: 'FLOAT'>, <Type.INT: 'INT'>, <Type.BIGINT: 'BIGINT'>, <Type.TINYINT: 'TINYINT'>, <Type.MEDIUMINT: 'MEDIUMINT'>, <Type.INT256: 'INT256'>, <Type.DOUBLE: 'DOUBLE'>, <Type.UINT: 'UINT'>, <Type.BIGDECIMAL: 'BIGDECIMAL'>, <Type.SMALLMONEY: 'SMALLMONEY'>, <Type.UDECIMAL: 'UDECIMAL'>, <Type.UTINYINT: 'UTINYINT'>, <Type.INT128: 'INT128'>}
TEMPORAL_TYPES = {<Type.DATETIME64: 'DATETIME64'>, <Type.DATE32: 'DATE32'>, <Type.TIMESTAMP: 'TIMESTAMP'>, <Type.TIMETZ: 'TIMETZ'>, <Type.TIMESTAMP_NS: 'TIMESTAMP_NS'>, <Type.TIMESTAMP_S: 'TIMESTAMP_S'>, <Type.TIMESTAMPTZ: 'TIMESTAMPTZ'>, <Type.TIME: 'TIME'>, <Type.TIMESTAMPLTZ: 'TIMESTAMPLTZ'>, <Type.TIMESTAMP_MS: 'TIMESTAMP_MS'>, <Type.TIMESTAMPNTZ: 'TIMESTAMPNTZ'>, <Type.DATE: 'DATE'>, <Type.DATETIME: 'DATETIME'>}
@classmethod
def build( cls, dtype: Union[str, DataType, DataType.Type], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, udt: bool = False, copy: bool = True, **kwargs) -> DataType:
4065    @classmethod
4066    def build(
4067        cls,
4068        dtype: DATA_TYPE,
4069        dialect: DialectType = None,
4070        udt: bool = False,
4071        copy: bool = True,
4072        **kwargs,
4073    ) -> DataType:
4074        """
4075        Constructs a DataType object.
4076
4077        Args:
4078            dtype: the data type of interest.
4079            dialect: the dialect to use for parsing `dtype`, in case it's a string.
4080            udt: when set to True, `dtype` will be used as-is if it can't be parsed into a
4081                DataType, thus creating a user-defined type.
4082            copy: whether to copy the data type.
4083            kwargs: additional arguments to pass in the constructor of DataType.
4084
4085        Returns:
4086            The constructed DataType object.
4087        """
4088        from sqlglot import parse_one
4089
4090        if isinstance(dtype, str):
4091            if dtype.upper() == "UNKNOWN":
4092                return DataType(this=DataType.Type.UNKNOWN, **kwargs)
4093
4094            try:
4095                data_type_exp = parse_one(
4096                    dtype, read=dialect, into=DataType, error_level=ErrorLevel.IGNORE
4097                )
4098            except ParseError:
4099                if udt:
4100                    return DataType(this=DataType.Type.USERDEFINED, kind=dtype, **kwargs)
4101                raise
4102        elif isinstance(dtype, DataType.Type):
4103            data_type_exp = DataType(this=dtype)
4104        elif isinstance(dtype, DataType):
4105            return maybe_copy(dtype, copy)
4106        else:
4107            raise ValueError(f"Invalid data type: {type(dtype)}. Expected str or DataType.Type")
4108
4109        return DataType(**{**data_type_exp.args, **kwargs})

Constructs a DataType object.

Arguments:
  • dtype: the data type of interest.
  • dialect: the dialect to use for parsing dtype, in case it's a string.
  • udt: when set to True, dtype will be used as-is if it can't be parsed into a DataType, thus creating a user-defined type.
  • copy: whether to copy the data type.
  • kwargs: additional arguments to pass in the constructor of DataType.
Returns:

The constructed DataType object.

def is_type( self, *dtypes: Union[str, DataType, DataType.Type]) -> bool:
4111    def is_type(self, *dtypes: DATA_TYPE) -> bool:
4112        """
4113        Checks whether this DataType matches one of the provided data types. Nested types or precision
4114        will be compared using "structural equivalence" semantics, so e.g. array<int> != array<float>.
4115
4116        Args:
4117            dtypes: the data types to compare this DataType to.
4118
4119        Returns:
4120            True, if and only if there is a type in `dtypes` which is equal to this DataType.
4121        """
4122        for dtype in dtypes:
4123            other = DataType.build(dtype, copy=False, udt=True)
4124
4125            if (
4126                other.expressions
4127                or self.this == DataType.Type.USERDEFINED
4128                or other.this == DataType.Type.USERDEFINED
4129            ):
4130                matches = self == other
4131            else:
4132                matches = self.this == other.this
4133
4134            if matches:
4135                return True
4136        return False

Checks whether this DataType matches one of the provided data types. Nested types or precision will be compared using "structural equivalence" semantics, so e.g. array != array.

Arguments:
  • dtypes: the data types to compare this DataType to.
Returns:

True, if and only if there is a type in dtypes which is equal to this DataType.

key = 'datatype'
class DataType.Type(sqlglot.helper.AutoName):
3877    class Type(AutoName):
3878        ARRAY = auto()
3879        AGGREGATEFUNCTION = auto()
3880        SIMPLEAGGREGATEFUNCTION = auto()
3881        BIGDECIMAL = auto()
3882        BIGINT = auto()
3883        BIGSERIAL = auto()
3884        BINARY = auto()
3885        BIT = auto()
3886        BOOLEAN = auto()
3887        BPCHAR = auto()
3888        CHAR = auto()
3889        DATE = auto()
3890        DATE32 = auto()
3891        DATEMULTIRANGE = auto()
3892        DATERANGE = auto()
3893        DATETIME = auto()
3894        DATETIME64 = auto()
3895        DECIMAL = auto()
3896        DOUBLE = auto()
3897        ENUM = auto()
3898        ENUM8 = auto()
3899        ENUM16 = auto()
3900        FIXEDSTRING = auto()
3901        FLOAT = auto()
3902        GEOGRAPHY = auto()
3903        GEOMETRY = auto()
3904        HLLSKETCH = auto()
3905        HSTORE = auto()
3906        IMAGE = auto()
3907        INET = auto()
3908        INT = auto()
3909        INT128 = auto()
3910        INT256 = auto()
3911        INT4MULTIRANGE = auto()
3912        INT4RANGE = auto()
3913        INT8MULTIRANGE = auto()
3914        INT8RANGE = auto()
3915        INTERVAL = auto()
3916        IPADDRESS = auto()
3917        IPPREFIX = auto()
3918        IPV4 = auto()
3919        IPV6 = auto()
3920        JSON = auto()
3921        JSONB = auto()
3922        LONGBLOB = auto()
3923        LONGTEXT = auto()
3924        LOWCARDINALITY = auto()
3925        MAP = auto()
3926        MEDIUMBLOB = auto()
3927        MEDIUMINT = auto()
3928        MEDIUMTEXT = auto()
3929        MONEY = auto()
3930        NAME = auto()
3931        NCHAR = auto()
3932        NESTED = auto()
3933        NULL = auto()
3934        NULLABLE = auto()
3935        NUMMULTIRANGE = auto()
3936        NUMRANGE = auto()
3937        NVARCHAR = auto()
3938        OBJECT = auto()
3939        ROWVERSION = auto()
3940        SERIAL = auto()
3941        SET = auto()
3942        SMALLINT = auto()
3943        SMALLMONEY = auto()
3944        SMALLSERIAL = auto()
3945        STRUCT = auto()
3946        SUPER = auto()
3947        TEXT = auto()
3948        TINYBLOB = auto()
3949        TINYTEXT = auto()
3950        TIME = auto()
3951        TIMETZ = auto()
3952        TIMESTAMP = auto()
3953        TIMESTAMPNTZ = auto()
3954        TIMESTAMPLTZ = auto()
3955        TIMESTAMPTZ = auto()
3956        TIMESTAMP_S = auto()
3957        TIMESTAMP_MS = auto()
3958        TIMESTAMP_NS = auto()
3959        TINYINT = auto()
3960        TSMULTIRANGE = auto()
3961        TSRANGE = auto()
3962        TSTZMULTIRANGE = auto()
3963        TSTZRANGE = auto()
3964        UBIGINT = auto()
3965        UINT = auto()
3966        UINT128 = auto()
3967        UINT256 = auto()
3968        UMEDIUMINT = auto()
3969        UDECIMAL = auto()
3970        UNIQUEIDENTIFIER = auto()
3971        UNKNOWN = auto()  # Sentinel value, useful for type annotation
3972        USERDEFINED = "USER-DEFINED"
3973        USMALLINT = auto()
3974        UTINYINT = auto()
3975        UUID = auto()
3976        VARBINARY = auto()
3977        VARCHAR = auto()
3978        VARIANT = auto()
3979        XML = auto()
3980        YEAR = auto()
3981        TDIGEST = auto()

An enumeration.

ARRAY = <Type.ARRAY: 'ARRAY'>
AGGREGATEFUNCTION = <Type.AGGREGATEFUNCTION: 'AGGREGATEFUNCTION'>
SIMPLEAGGREGATEFUNCTION = <Type.SIMPLEAGGREGATEFUNCTION: 'SIMPLEAGGREGATEFUNCTION'>
BIGDECIMAL = <Type.BIGDECIMAL: 'BIGDECIMAL'>
BIGINT = <Type.BIGINT: 'BIGINT'>
BIGSERIAL = <Type.BIGSERIAL: 'BIGSERIAL'>
BINARY = <Type.BINARY: 'BINARY'>
BIT = <Type.BIT: 'BIT'>
BOOLEAN = <Type.BOOLEAN: 'BOOLEAN'>
BPCHAR = <Type.BPCHAR: 'BPCHAR'>
CHAR = <Type.CHAR: 'CHAR'>
DATE = <Type.DATE: 'DATE'>
DATE32 = <Type.DATE32: 'DATE32'>
DATEMULTIRANGE = <Type.DATEMULTIRANGE: 'DATEMULTIRANGE'>
DATERANGE = <Type.DATERANGE: 'DATERANGE'>
DATETIME = <Type.DATETIME: 'DATETIME'>
DATETIME64 = <Type.DATETIME64: 'DATETIME64'>
DECIMAL = <Type.DECIMAL: 'DECIMAL'>
DOUBLE = <Type.DOUBLE: 'DOUBLE'>
ENUM = <Type.ENUM: 'ENUM'>
ENUM8 = <Type.ENUM8: 'ENUM8'>
ENUM16 = <Type.ENUM16: 'ENUM16'>
FIXEDSTRING = <Type.FIXEDSTRING: 'FIXEDSTRING'>
FLOAT = <Type.FLOAT: 'FLOAT'>
GEOGRAPHY = <Type.GEOGRAPHY: 'GEOGRAPHY'>
GEOMETRY = <Type.GEOMETRY: 'GEOMETRY'>
HLLSKETCH = <Type.HLLSKETCH: 'HLLSKETCH'>
HSTORE = <Type.HSTORE: 'HSTORE'>
IMAGE = <Type.IMAGE: 'IMAGE'>
INET = <Type.INET: 'INET'>
INT = <Type.INT: 'INT'>
INT128 = <Type.INT128: 'INT128'>
INT256 = <Type.INT256: 'INT256'>
INT4MULTIRANGE = <Type.INT4MULTIRANGE: 'INT4MULTIRANGE'>
INT4RANGE = <Type.INT4RANGE: 'INT4RANGE'>
INT8MULTIRANGE = <Type.INT8MULTIRANGE: 'INT8MULTIRANGE'>
INT8RANGE = <Type.INT8RANGE: 'INT8RANGE'>
INTERVAL = <Type.INTERVAL: 'INTERVAL'>
IPADDRESS = <Type.IPADDRESS: 'IPADDRESS'>
IPPREFIX = <Type.IPPREFIX: 'IPPREFIX'>
IPV4 = <Type.IPV4: 'IPV4'>
IPV6 = <Type.IPV6: 'IPV6'>
JSON = <Type.JSON: 'JSON'>
JSONB = <Type.JSONB: 'JSONB'>
LONGBLOB = <Type.LONGBLOB: 'LONGBLOB'>
LONGTEXT = <Type.LONGTEXT: 'LONGTEXT'>
LOWCARDINALITY = <Type.LOWCARDINALITY: 'LOWCARDINALITY'>
MAP = <Type.MAP: 'MAP'>
MEDIUMBLOB = <Type.MEDIUMBLOB: 'MEDIUMBLOB'>
MEDIUMINT = <Type.MEDIUMINT: 'MEDIUMINT'>
MEDIUMTEXT = <Type.MEDIUMTEXT: 'MEDIUMTEXT'>
MONEY = <Type.MONEY: 'MONEY'>
NAME = <Type.NAME: 'NAME'>
NCHAR = <Type.NCHAR: 'NCHAR'>
NESTED = <Type.NESTED: 'NESTED'>
NULL = <Type.NULL: 'NULL'>
NULLABLE = <Type.NULLABLE: 'NULLABLE'>
NUMMULTIRANGE = <Type.NUMMULTIRANGE: 'NUMMULTIRANGE'>
NUMRANGE = <Type.NUMRANGE: 'NUMRANGE'>
NVARCHAR = <Type.NVARCHAR: 'NVARCHAR'>
OBJECT = <Type.OBJECT: 'OBJECT'>
ROWVERSION = <Type.ROWVERSION: 'ROWVERSION'>
SERIAL = <Type.SERIAL: 'SERIAL'>
SET = <Type.SET: 'SET'>
SMALLINT = <Type.SMALLINT: 'SMALLINT'>
SMALLMONEY = <Type.SMALLMONEY: 'SMALLMONEY'>
SMALLSERIAL = <Type.SMALLSERIAL: 'SMALLSERIAL'>
STRUCT = <Type.STRUCT: 'STRUCT'>
SUPER = <Type.SUPER: 'SUPER'>
TEXT = <Type.TEXT: 'TEXT'>
TINYBLOB = <Type.TINYBLOB: 'TINYBLOB'>
TINYTEXT = <Type.TINYTEXT: 'TINYTEXT'>
TIME = <Type.TIME: 'TIME'>
TIMETZ = <Type.TIMETZ: 'TIMETZ'>
TIMESTAMP = <Type.TIMESTAMP: 'TIMESTAMP'>
TIMESTAMPNTZ = <Type.TIMESTAMPNTZ: 'TIMESTAMPNTZ'>
TIMESTAMPLTZ = <Type.TIMESTAMPLTZ: 'TIMESTAMPLTZ'>
TIMESTAMPTZ = <Type.TIMESTAMPTZ: 'TIMESTAMPTZ'>
TIMESTAMP_S = <Type.TIMESTAMP_S: 'TIMESTAMP_S'>
TIMESTAMP_MS = <Type.TIMESTAMP_MS: 'TIMESTAMP_MS'>
TIMESTAMP_NS = <Type.TIMESTAMP_NS: 'TIMESTAMP_NS'>
TINYINT = <Type.TINYINT: 'TINYINT'>
TSMULTIRANGE = <Type.TSMULTIRANGE: 'TSMULTIRANGE'>
TSRANGE = <Type.TSRANGE: 'TSRANGE'>
TSTZMULTIRANGE = <Type.TSTZMULTIRANGE: 'TSTZMULTIRANGE'>
TSTZRANGE = <Type.TSTZRANGE: 'TSTZRANGE'>
UBIGINT = <Type.UBIGINT: 'UBIGINT'>
UINT = <Type.UINT: 'UINT'>
UINT128 = <Type.UINT128: 'UINT128'>
UINT256 = <Type.UINT256: 'UINT256'>
UMEDIUMINT = <Type.UMEDIUMINT: 'UMEDIUMINT'>
UDECIMAL = <Type.UDECIMAL: 'UDECIMAL'>
UNIQUEIDENTIFIER = <Type.UNIQUEIDENTIFIER: 'UNIQUEIDENTIFIER'>
UNKNOWN = <Type.UNKNOWN: 'UNKNOWN'>
USERDEFINED = <Type.USERDEFINED: 'USER-DEFINED'>
USMALLINT = <Type.USMALLINT: 'USMALLINT'>
UTINYINT = <Type.UTINYINT: 'UTINYINT'>
UUID = <Type.UUID: 'UUID'>
VARBINARY = <Type.VARBINARY: 'VARBINARY'>
VARCHAR = <Type.VARCHAR: 'VARCHAR'>
VARIANT = <Type.VARIANT: 'VARIANT'>
XML = <Type.XML: 'XML'>
YEAR = <Type.YEAR: 'YEAR'>
TDIGEST = <Type.TDIGEST: 'TDIGEST'>
Inherited Members
enum.Enum
name
value
DATA_TYPE = typing.Union[str, DataType, DataType.Type]
class PseudoType(DataType):
4143class PseudoType(DataType):
4144    arg_types = {"this": True}
arg_types = {'this': True}
key = 'pseudotype'
class ObjectIdentifier(DataType):
4148class ObjectIdentifier(DataType):
4149    arg_types = {"this": True}
arg_types = {'this': True}
key = 'objectidentifier'
class SubqueryPredicate(Predicate):
4153class SubqueryPredicate(Predicate):
4154    pass
key = 'subquerypredicate'
class All(SubqueryPredicate):
4157class All(SubqueryPredicate):
4158    pass
key = 'all'
class Any(SubqueryPredicate):
4161class Any(SubqueryPredicate):
4162    pass
key = 'any'
class Exists(SubqueryPredicate):
4165class Exists(SubqueryPredicate):
4166    pass
key = 'exists'
class Command(Expression):
4171class Command(Expression):
4172    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'command'
class Transaction(Expression):
4175class Transaction(Expression):
4176    arg_types = {"this": False, "modes": False, "mark": False}
arg_types = {'this': False, 'modes': False, 'mark': False}
key = 'transaction'
class Commit(Expression):
4179class Commit(Expression):
4180    arg_types = {"chain": False, "this": False, "durability": False}
arg_types = {'chain': False, 'this': False, 'durability': False}
key = 'commit'
class Rollback(Expression):
4183class Rollback(Expression):
4184    arg_types = {"savepoint": False, "this": False}
arg_types = {'savepoint': False, 'this': False}
key = 'rollback'
class AlterTable(Expression):
4187class AlterTable(Expression):
4188    arg_types = {
4189        "this": True,
4190        "actions": True,
4191        "exists": False,
4192        "only": False,
4193        "options": False,
4194        "cluster": False,
4195    }
arg_types = {'this': True, 'actions': True, 'exists': False, 'only': False, 'options': False, 'cluster': False}
key = 'altertable'
class AddConstraint(Expression):
4198class AddConstraint(Expression):
4199    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'addconstraint'
class DropPartition(Expression):
4202class DropPartition(Expression):
4203    arg_types = {"expressions": True, "exists": False}
arg_types = {'expressions': True, 'exists': False}
key = 'droppartition'
class ReplacePartition(Expression):
4207class ReplacePartition(Expression):
4208    arg_types = {"expression": True, "source": True}
arg_types = {'expression': True, 'source': True}
key = 'replacepartition'
class Binary(Condition):
4212class Binary(Condition):
4213    arg_types = {"this": True, "expression": True}
4214
4215    @property
4216    def left(self) -> Expression:
4217        return self.this
4218
4219    @property
4220    def right(self) -> Expression:
4221        return self.expression
arg_types = {'this': True, 'expression': True}
left: Expression
4215    @property
4216    def left(self) -> Expression:
4217        return self.this
right: Expression
4219    @property
4220    def right(self) -> Expression:
4221        return self.expression
key = 'binary'
class Add(Binary):
4224class Add(Binary):
4225    pass
key = 'add'
class Connector(Binary):
4228class Connector(Binary):
4229    pass
key = 'connector'
class And(Connector):
4232class And(Connector):
4233    pass
key = 'and'
class Or(Connector):
4236class Or(Connector):
4237    pass
key = 'or'
class BitwiseAnd(Binary):
4240class BitwiseAnd(Binary):
4241    pass
key = 'bitwiseand'
class BitwiseLeftShift(Binary):
4244class BitwiseLeftShift(Binary):
4245    pass
key = 'bitwiseleftshift'
class BitwiseOr(Binary):
4248class BitwiseOr(Binary):
4249    pass
key = 'bitwiseor'
class BitwiseRightShift(Binary):
4252class BitwiseRightShift(Binary):
4253    pass
key = 'bitwiserightshift'
class BitwiseXor(Binary):
4256class BitwiseXor(Binary):
4257    pass
key = 'bitwisexor'
class Div(Binary):
4260class Div(Binary):
4261    arg_types = {"this": True, "expression": True, "typed": False, "safe": False}
arg_types = {'this': True, 'expression': True, 'typed': False, 'safe': False}
key = 'div'
class Overlaps(Binary):
4264class Overlaps(Binary):
4265    pass
key = 'overlaps'
class Dot(Binary):
4268class Dot(Binary):
4269    @property
4270    def is_star(self) -> bool:
4271        return self.expression.is_star
4272
4273    @property
4274    def name(self) -> str:
4275        return self.expression.name
4276
4277    @property
4278    def output_name(self) -> str:
4279        return self.name
4280
4281    @classmethod
4282    def build(self, expressions: t.Sequence[Expression]) -> Dot:
4283        """Build a Dot object with a sequence of expressions."""
4284        if len(expressions) < 2:
4285            raise ValueError("Dot requires >= 2 expressions.")
4286
4287        return t.cast(Dot, reduce(lambda x, y: Dot(this=x, expression=y), expressions))
4288
4289    @property
4290    def parts(self) -> t.List[Expression]:
4291        """Return the parts of a table / column in order catalog, db, table."""
4292        this, *parts = self.flatten()
4293
4294        parts.reverse()
4295
4296        for arg in COLUMN_PARTS:
4297            part = this.args.get(arg)
4298
4299            if isinstance(part, Expression):
4300                parts.append(part)
4301
4302        parts.reverse()
4303        return parts
is_star: bool
4269    @property
4270    def is_star(self) -> bool:
4271        return self.expression.is_star

Checks whether an expression is a star.

name: str
4273    @property
4274    def name(self) -> str:
4275        return self.expression.name
output_name: str
4277    @property
4278    def output_name(self) -> str:
4279        return self.name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
@classmethod
def build( self, expressions: Sequence[Expression]) -> Dot:
4281    @classmethod
4282    def build(self, expressions: t.Sequence[Expression]) -> Dot:
4283        """Build a Dot object with a sequence of expressions."""
4284        if len(expressions) < 2:
4285            raise ValueError("Dot requires >= 2 expressions.")
4286
4287        return t.cast(Dot, reduce(lambda x, y: Dot(this=x, expression=y), expressions))

Build a Dot object with a sequence of expressions.

parts: List[Expression]
4289    @property
4290    def parts(self) -> t.List[Expression]:
4291        """Return the parts of a table / column in order catalog, db, table."""
4292        this, *parts = self.flatten()
4293
4294        parts.reverse()
4295
4296        for arg in COLUMN_PARTS:
4297            part = this.args.get(arg)
4298
4299            if isinstance(part, Expression):
4300                parts.append(part)
4301
4302        parts.reverse()
4303        return parts

Return the parts of a table / column in order catalog, db, table.

key = 'dot'
class DPipe(Binary):
4306class DPipe(Binary):
4307    arg_types = {"this": True, "expression": True, "safe": False}
arg_types = {'this': True, 'expression': True, 'safe': False}
key = 'dpipe'
class EQ(Binary, Predicate):
4310class EQ(Binary, Predicate):
4311    pass
key = 'eq'
class NullSafeEQ(Binary, Predicate):
4314class NullSafeEQ(Binary, Predicate):
4315    pass
key = 'nullsafeeq'
class NullSafeNEQ(Binary, Predicate):
4318class NullSafeNEQ(Binary, Predicate):
4319    pass
key = 'nullsafeneq'
class PropertyEQ(Binary):
4323class PropertyEQ(Binary):
4324    pass
key = 'propertyeq'
class Distance(Binary):
4327class Distance(Binary):
4328    pass
key = 'distance'
class Escape(Binary):
4331class Escape(Binary):
4332    pass
key = 'escape'
class Glob(Binary, Predicate):
4335class Glob(Binary, Predicate):
4336    pass
key = 'glob'
class GT(Binary, Predicate):
4339class GT(Binary, Predicate):
4340    pass
key = 'gt'
class GTE(Binary, Predicate):
4343class GTE(Binary, Predicate):
4344    pass
key = 'gte'
class ILike(Binary, Predicate):
4347class ILike(Binary, Predicate):
4348    pass
key = 'ilike'
class ILikeAny(Binary, Predicate):
4351class ILikeAny(Binary, Predicate):
4352    pass
key = 'ilikeany'
class IntDiv(Binary):
4355class IntDiv(Binary):
4356    pass
key = 'intdiv'
class Is(Binary, Predicate):
4359class Is(Binary, Predicate):
4360    pass
key = 'is'
class Kwarg(Binary):
4363class Kwarg(Binary):
4364    """Kwarg in special functions like func(kwarg => y)."""

Kwarg in special functions like func(kwarg => y).

key = 'kwarg'
class Like(Binary, Predicate):
4367class Like(Binary, Predicate):
4368    pass
key = 'like'
class LikeAny(Binary, Predicate):
4371class LikeAny(Binary, Predicate):
4372    pass
key = 'likeany'
class LT(Binary, Predicate):
4375class LT(Binary, Predicate):
4376    pass
key = 'lt'
class LTE(Binary, Predicate):
4379class LTE(Binary, Predicate):
4380    pass
key = 'lte'
class Mod(Binary):
4383class Mod(Binary):
4384    pass
key = 'mod'
class Mul(Binary):
4387class Mul(Binary):
4388    pass
key = 'mul'
class NEQ(Binary, Predicate):
4391class NEQ(Binary, Predicate):
4392    pass
key = 'neq'
class Operator(Binary):
4396class Operator(Binary):
4397    arg_types = {"this": True, "operator": True, "expression": True}
arg_types = {'this': True, 'operator': True, 'expression': True}
key = 'operator'
class SimilarTo(Binary, Predicate):
4400class SimilarTo(Binary, Predicate):
4401    pass
key = 'similarto'
class Slice(Binary):
4404class Slice(Binary):
4405    arg_types = {"this": False, "expression": False}
arg_types = {'this': False, 'expression': False}
key = 'slice'
class Sub(Binary):
4408class Sub(Binary):
4409    pass
key = 'sub'
class Unary(Condition):
4414class Unary(Condition):
4415    pass
key = 'unary'
class BitwiseNot(Unary):
4418class BitwiseNot(Unary):
4419    pass
key = 'bitwisenot'
class Not(Unary):
4422class Not(Unary):
4423    pass
key = 'not'
class Paren(Unary):
4426class Paren(Unary):
4427    @property
4428    def output_name(self) -> str:
4429        return self.this.name
output_name: str
4427    @property
4428    def output_name(self) -> str:
4429        return self.this.name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'paren'
class Neg(Unary):
4432class Neg(Unary):
4433    pass
key = 'neg'
class Alias(Expression):
4436class Alias(Expression):
4437    arg_types = {"this": True, "alias": False}
4438
4439    @property
4440    def output_name(self) -> str:
4441        return self.alias
arg_types = {'this': True, 'alias': False}
output_name: str
4439    @property
4440    def output_name(self) -> str:
4441        return self.alias

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'alias'
class PivotAlias(Alias):
4446class PivotAlias(Alias):
4447    pass
key = 'pivotalias'
class Aliases(Expression):
4450class Aliases(Expression):
4451    arg_types = {"this": True, "expressions": True}
4452
4453    @property
4454    def aliases(self):
4455        return self.expressions
arg_types = {'this': True, 'expressions': True}
aliases
4453    @property
4454    def aliases(self):
4455        return self.expressions
key = 'aliases'
class AtIndex(Expression):
4459class AtIndex(Expression):
4460    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'atindex'
class AtTimeZone(Expression):
4463class AtTimeZone(Expression):
4464    arg_types = {"this": True, "zone": True}
arg_types = {'this': True, 'zone': True}
key = 'attimezone'
class FromTimeZone(Expression):
4467class FromTimeZone(Expression):
4468    arg_types = {"this": True, "zone": True}
arg_types = {'this': True, 'zone': True}
key = 'fromtimezone'
class Between(Predicate):
4471class Between(Predicate):
4472    arg_types = {"this": True, "low": True, "high": True}
arg_types = {'this': True, 'low': True, 'high': True}
key = 'between'
class Bracket(Condition):
4475class Bracket(Condition):
4476    # https://cloud.google.com/bigquery/docs/reference/standard-sql/operators#array_subscript_operator
4477    arg_types = {
4478        "this": True,
4479        "expressions": True,
4480        "offset": False,
4481        "safe": False,
4482        "returns_list_for_maps": False,
4483    }
4484
4485    @property
4486    def output_name(self) -> str:
4487        if len(self.expressions) == 1:
4488            return self.expressions[0].output_name
4489
4490        return super().output_name
arg_types = {'this': True, 'expressions': True, 'offset': False, 'safe': False, 'returns_list_for_maps': False}
output_name: str
4485    @property
4486    def output_name(self) -> str:
4487        if len(self.expressions) == 1:
4488            return self.expressions[0].output_name
4489
4490        return super().output_name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'bracket'
class Distinct(Expression):
4493class Distinct(Expression):
4494    arg_types = {"expressions": False, "on": False}
arg_types = {'expressions': False, 'on': False}
key = 'distinct'
class In(Predicate):
4497class In(Predicate):
4498    arg_types = {
4499        "this": True,
4500        "expressions": False,
4501        "query": False,
4502        "unnest": False,
4503        "field": False,
4504        "is_global": False,
4505    }
arg_types = {'this': True, 'expressions': False, 'query': False, 'unnest': False, 'field': False, 'is_global': False}
key = 'in'
class ForIn(Expression):
4509class ForIn(Expression):
4510    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'forin'
class TimeUnit(Expression):
4513class TimeUnit(Expression):
4514    """Automatically converts unit arg into a var."""
4515
4516    arg_types = {"unit": False}
4517
4518    UNABBREVIATED_UNIT_NAME = {
4519        "D": "DAY",
4520        "H": "HOUR",
4521        "M": "MINUTE",
4522        "MS": "MILLISECOND",
4523        "NS": "NANOSECOND",
4524        "Q": "QUARTER",
4525        "S": "SECOND",
4526        "US": "MICROSECOND",
4527        "W": "WEEK",
4528        "Y": "YEAR",
4529    }
4530
4531    VAR_LIKE = (Column, Literal, Var)
4532
4533    def __init__(self, **args):
4534        unit = args.get("unit")
4535        if isinstance(unit, self.VAR_LIKE):
4536            args["unit"] = Var(
4537                this=(self.UNABBREVIATED_UNIT_NAME.get(unit.name) or unit.name).upper()
4538            )
4539        elif isinstance(unit, Week):
4540            unit.set("this", Var(this=unit.this.name.upper()))
4541
4542        super().__init__(**args)
4543
4544    @property
4545    def unit(self) -> t.Optional[Var | IntervalSpan]:
4546        return self.args.get("unit")

Automatically converts unit arg into a var.

TimeUnit(**args)
4533    def __init__(self, **args):
4534        unit = args.get("unit")
4535        if isinstance(unit, self.VAR_LIKE):
4536            args["unit"] = Var(
4537                this=(self.UNABBREVIATED_UNIT_NAME.get(unit.name) or unit.name).upper()
4538            )
4539        elif isinstance(unit, Week):
4540            unit.set("this", Var(this=unit.this.name.upper()))
4541
4542        super().__init__(**args)
arg_types = {'unit': False}
UNABBREVIATED_UNIT_NAME = {'D': 'DAY', 'H': 'HOUR', 'M': 'MINUTE', 'MS': 'MILLISECOND', 'NS': 'NANOSECOND', 'Q': 'QUARTER', 'S': 'SECOND', 'US': 'MICROSECOND', 'W': 'WEEK', 'Y': 'YEAR'}
VAR_LIKE = (<class 'Column'>, <class 'Literal'>, <class 'Var'>)
unit: Union[Var, IntervalSpan, NoneType]
4544    @property
4545    def unit(self) -> t.Optional[Var | IntervalSpan]:
4546        return self.args.get("unit")
key = 'timeunit'
class IntervalOp(TimeUnit):
4549class IntervalOp(TimeUnit):
4550    arg_types = {"unit": True, "expression": True}
4551
4552    def interval(self):
4553        return Interval(
4554            this=self.expression.copy(),
4555            unit=self.unit.copy(),
4556        )
arg_types = {'unit': True, 'expression': True}
def interval(self):
4552    def interval(self):
4553        return Interval(
4554            this=self.expression.copy(),
4555            unit=self.unit.copy(),
4556        )
key = 'intervalop'
class IntervalSpan(DataType):
4562class IntervalSpan(DataType):
4563    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'intervalspan'
class Interval(TimeUnit):
4566class Interval(TimeUnit):
4567    arg_types = {"this": False, "unit": False}
arg_types = {'this': False, 'unit': False}
key = 'interval'
class IgnoreNulls(Expression):
4570class IgnoreNulls(Expression):
4571    pass
key = 'ignorenulls'
class RespectNulls(Expression):
4574class RespectNulls(Expression):
4575    pass
key = 'respectnulls'
class HavingMax(Expression):
4579class HavingMax(Expression):
4580    arg_types = {"this": True, "expression": True, "max": True}
arg_types = {'this': True, 'expression': True, 'max': True}
key = 'havingmax'
class Func(Condition):
4584class Func(Condition):
4585    """
4586    The base class for all function expressions.
4587
4588    Attributes:
4589        is_var_len_args (bool): if set to True the last argument defined in arg_types will be
4590            treated as a variable length argument and the argument's value will be stored as a list.
4591        _sql_names (list): the SQL name (1st item in the list) and aliases (subsequent items) for this
4592            function expression. These values are used to map this node to a name during parsing as
4593            well as to provide the function's name during SQL string generation. By default the SQL
4594            name is set to the expression's class name transformed to snake case.
4595    """
4596
4597    is_var_len_args = False
4598
4599    @classmethod
4600    def from_arg_list(cls, args):
4601        if cls.is_var_len_args:
4602            all_arg_keys = list(cls.arg_types)
4603            # If this function supports variable length argument treat the last argument as such.
4604            non_var_len_arg_keys = all_arg_keys[:-1] if cls.is_var_len_args else all_arg_keys
4605            num_non_var = len(non_var_len_arg_keys)
4606
4607            args_dict = {arg_key: arg for arg, arg_key in zip(args, non_var_len_arg_keys)}
4608            args_dict[all_arg_keys[-1]] = args[num_non_var:]
4609        else:
4610            args_dict = {arg_key: arg for arg, arg_key in zip(args, cls.arg_types)}
4611
4612        return cls(**args_dict)
4613
4614    @classmethod
4615    def sql_names(cls):
4616        if cls is Func:
4617            raise NotImplementedError(
4618                "SQL name is only supported by concrete function implementations"
4619            )
4620        if "_sql_names" not in cls.__dict__:
4621            cls._sql_names = [camel_to_snake_case(cls.__name__)]
4622        return cls._sql_names
4623
4624    @classmethod
4625    def sql_name(cls):
4626        return cls.sql_names()[0]
4627
4628    @classmethod
4629    def default_parser_mappings(cls):
4630        return {name: cls.from_arg_list for name in cls.sql_names()}

The base class for all function expressions.

Attributes:
  • is_var_len_args (bool): if set to True the last argument defined in arg_types will be treated as a variable length argument and the argument's value will be stored as a list.
  • _sql_names (list): the SQL name (1st item in the list) and aliases (subsequent items) for this function expression. These values are used to map this node to a name during parsing as well as to provide the function's name during SQL string generation. By default the SQL name is set to the expression's class name transformed to snake case.
is_var_len_args = False
@classmethod
def from_arg_list(cls, args):
4599    @classmethod
4600    def from_arg_list(cls, args):
4601        if cls.is_var_len_args:
4602            all_arg_keys = list(cls.arg_types)
4603            # If this function supports variable length argument treat the last argument as such.
4604            non_var_len_arg_keys = all_arg_keys[:-1] if cls.is_var_len_args else all_arg_keys
4605            num_non_var = len(non_var_len_arg_keys)
4606
4607            args_dict = {arg_key: arg for arg, arg_key in zip(args, non_var_len_arg_keys)}
4608            args_dict[all_arg_keys[-1]] = args[num_non_var:]
4609        else:
4610            args_dict = {arg_key: arg for arg, arg_key in zip(args, cls.arg_types)}
4611
4612        return cls(**args_dict)
@classmethod
def sql_names(cls):
4614    @classmethod
4615    def sql_names(cls):
4616        if cls is Func:
4617            raise NotImplementedError(
4618                "SQL name is only supported by concrete function implementations"
4619            )
4620        if "_sql_names" not in cls.__dict__:
4621            cls._sql_names = [camel_to_snake_case(cls.__name__)]
4622        return cls._sql_names
@classmethod
def sql_name(cls):
4624    @classmethod
4625    def sql_name(cls):
4626        return cls.sql_names()[0]
@classmethod
def default_parser_mappings(cls):
4628    @classmethod
4629    def default_parser_mappings(cls):
4630        return {name: cls.from_arg_list for name in cls.sql_names()}
key = 'func'
class AggFunc(Func):
4633class AggFunc(Func):
4634    pass
key = 'aggfunc'
class ParameterizedAgg(AggFunc):
4637class ParameterizedAgg(AggFunc):
4638    arg_types = {"this": True, "expressions": True, "params": True}
arg_types = {'this': True, 'expressions': True, 'params': True}
key = 'parameterizedagg'
class Abs(Func):
4641class Abs(Func):
4642    pass
key = 'abs'
class ArgMax(AggFunc):
4645class ArgMax(AggFunc):
4646    arg_types = {"this": True, "expression": True, "count": False}
4647    _sql_names = ["ARG_MAX", "ARGMAX", "MAX_BY"]
arg_types = {'this': True, 'expression': True, 'count': False}
key = 'argmax'
class ArgMin(AggFunc):
4650class ArgMin(AggFunc):
4651    arg_types = {"this": True, "expression": True, "count": False}
4652    _sql_names = ["ARG_MIN", "ARGMIN", "MIN_BY"]
arg_types = {'this': True, 'expression': True, 'count': False}
key = 'argmin'
class ApproxTopK(AggFunc):
4655class ApproxTopK(AggFunc):
4656    arg_types = {"this": True, "expression": False, "counters": False}
arg_types = {'this': True, 'expression': False, 'counters': False}
key = 'approxtopk'
class Flatten(Func):
4659class Flatten(Func):
4660    pass
key = 'flatten'
class Transform(Func):
4664class Transform(Func):
4665    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'transform'
class Anonymous(Func):
4668class Anonymous(Func):
4669    arg_types = {"this": True, "expressions": False}
4670    is_var_len_args = True
4671
4672    @property
4673    def name(self) -> str:
4674        return self.this if isinstance(self.this, str) else self.this.name
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
name: str
4672    @property
4673    def name(self) -> str:
4674        return self.this if isinstance(self.this, str) else self.this.name
key = 'anonymous'
class AnonymousAggFunc(AggFunc):
4677class AnonymousAggFunc(AggFunc):
4678    arg_types = {"this": True, "expressions": False}
4679    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'anonymousaggfunc'
class CombinedAggFunc(AnonymousAggFunc):
4683class CombinedAggFunc(AnonymousAggFunc):
4684    arg_types = {"this": True, "expressions": False, "parts": True}
arg_types = {'this': True, 'expressions': False, 'parts': True}
key = 'combinedaggfunc'
class CombinedParameterizedAgg(ParameterizedAgg):
4687class CombinedParameterizedAgg(ParameterizedAgg):
4688    arg_types = {"this": True, "expressions": True, "params": True, "parts": True}
arg_types = {'this': True, 'expressions': True, 'params': True, 'parts': True}
key = 'combinedparameterizedagg'
class Hll(AggFunc):
4693class Hll(AggFunc):
4694    arg_types = {"this": True, "expressions": False}
4695    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'hll'
class ApproxDistinct(AggFunc):
4698class ApproxDistinct(AggFunc):
4699    arg_types = {"this": True, "accuracy": False}
4700    _sql_names = ["APPROX_DISTINCT", "APPROX_COUNT_DISTINCT"]
arg_types = {'this': True, 'accuracy': False}
key = 'approxdistinct'
class Array(Func):
4703class Array(Func):
4704    arg_types = {"expressions": False}
4705    is_var_len_args = True
arg_types = {'expressions': False}
is_var_len_args = True
key = 'array'
class ToArray(Func):
4709class ToArray(Func):
4710    pass
key = 'toarray'
class ToChar(Func):
4715class ToChar(Func):
4716    arg_types = {"this": True, "format": False, "nlsparam": False}
arg_types = {'this': True, 'format': False, 'nlsparam': False}
key = 'tochar'
class ToNumber(Func):
4721class ToNumber(Func):
4722    arg_types = {
4723        "this": True,
4724        "format": False,
4725        "nlsparam": False,
4726        "precision": False,
4727        "scale": False,
4728    }
arg_types = {'this': True, 'format': False, 'nlsparam': False, 'precision': False, 'scale': False}
key = 'tonumber'
class Convert(Func):
4732class Convert(Func):
4733    arg_types = {"this": True, "expression": True, "style": False}
arg_types = {'this': True, 'expression': True, 'style': False}
key = 'convert'
class GenerateSeries(Func):
4736class GenerateSeries(Func):
4737    arg_types = {"start": True, "end": True, "step": False, "is_end_exclusive": False}
arg_types = {'start': True, 'end': True, 'step': False, 'is_end_exclusive': False}
key = 'generateseries'
class ArrayAgg(AggFunc):
4740class ArrayAgg(AggFunc):
4741    pass
key = 'arrayagg'
class ArrayUniqueAgg(AggFunc):
4744class ArrayUniqueAgg(AggFunc):
4745    pass
key = 'arrayuniqueagg'
class ArrayAll(Func):
4748class ArrayAll(Func):
4749    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'arrayall'
class ArrayAny(Func):
4753class ArrayAny(Func):
4754    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'arrayany'
class ArrayConcat(Func):
4757class ArrayConcat(Func):
4758    _sql_names = ["ARRAY_CONCAT", "ARRAY_CAT"]
4759    arg_types = {"this": True, "expressions": False}
4760    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'arrayconcat'
class ArrayContains(Binary, Func):
4763class ArrayContains(Binary, Func):
4764    pass
key = 'arraycontains'
class ArrayContained(Binary):
4767class ArrayContained(Binary):
4768    pass
key = 'arraycontained'
class ArrayFilter(Func):
4771class ArrayFilter(Func):
4772    arg_types = {"this": True, "expression": True}
4773    _sql_names = ["FILTER", "ARRAY_FILTER"]
arg_types = {'this': True, 'expression': True}
key = 'arrayfilter'
class ArrayToString(Func):
4776class ArrayToString(Func):
4777    arg_types = {"this": True, "expression": True, "null": False}
4778    _sql_names = ["ARRAY_TO_STRING", "ARRAY_JOIN"]
arg_types = {'this': True, 'expression': True, 'null': False}
key = 'arraytostring'
class ArrayOverlaps(Binary, Func):
4781class ArrayOverlaps(Binary, Func):
4782    pass
key = 'arrayoverlaps'
class ArraySize(Func):
4785class ArraySize(Func):
4786    arg_types = {"this": True, "expression": False}
4787    _sql_names = ["ARRAY_SIZE", "ARRAY_LENGTH"]
arg_types = {'this': True, 'expression': False}
key = 'arraysize'
class ArraySort(Func):
4790class ArraySort(Func):
4791    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'arraysort'
class ArraySum(Func):
4794class ArraySum(Func):
4795    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'arraysum'
class ArrayUnionAgg(AggFunc):
4798class ArrayUnionAgg(AggFunc):
4799    pass
key = 'arrayunionagg'
class Avg(AggFunc):
4802class Avg(AggFunc):
4803    pass
key = 'avg'
class AnyValue(AggFunc):
4806class AnyValue(AggFunc):
4807    pass
key = 'anyvalue'
class Lag(AggFunc):
4810class Lag(AggFunc):
4811    arg_types = {"this": True, "offset": False, "default": False}
arg_types = {'this': True, 'offset': False, 'default': False}
key = 'lag'
class Lead(AggFunc):
4814class Lead(AggFunc):
4815    arg_types = {"this": True, "offset": False, "default": False}
arg_types = {'this': True, 'offset': False, 'default': False}
key = 'lead'
class First(AggFunc):
4820class First(AggFunc):
4821    pass
key = 'first'
class Last(AggFunc):
4824class Last(AggFunc):
4825    pass
key = 'last'
class FirstValue(AggFunc):
4828class FirstValue(AggFunc):
4829    pass
key = 'firstvalue'
class LastValue(AggFunc):
4832class LastValue(AggFunc):
4833    pass
key = 'lastvalue'
class NthValue(AggFunc):
4836class NthValue(AggFunc):
4837    arg_types = {"this": True, "offset": True}
arg_types = {'this': True, 'offset': True}
key = 'nthvalue'
class Case(Func):
4840class Case(Func):
4841    arg_types = {"this": False, "ifs": True, "default": False}
4842
4843    def when(self, condition: ExpOrStr, then: ExpOrStr, copy: bool = True, **opts) -> Case:
4844        instance = maybe_copy(self, copy)
4845        instance.append(
4846            "ifs",
4847            If(
4848                this=maybe_parse(condition, copy=copy, **opts),
4849                true=maybe_parse(then, copy=copy, **opts),
4850            ),
4851        )
4852        return instance
4853
4854    def else_(self, condition: ExpOrStr, copy: bool = True, **opts) -> Case:
4855        instance = maybe_copy(self, copy)
4856        instance.set("default", maybe_parse(condition, copy=copy, **opts))
4857        return instance
arg_types = {'this': False, 'ifs': True, 'default': False}
def when( self, condition: Union[str, Expression], then: Union[str, Expression], copy: bool = True, **opts) -> Case:
4843    def when(self, condition: ExpOrStr, then: ExpOrStr, copy: bool = True, **opts) -> Case:
4844        instance = maybe_copy(self, copy)
4845        instance.append(
4846            "ifs",
4847            If(
4848                this=maybe_parse(condition, copy=copy, **opts),
4849                true=maybe_parse(then, copy=copy, **opts),
4850            ),
4851        )
4852        return instance
def else_( self, condition: Union[str, Expression], copy: bool = True, **opts) -> Case:
4854    def else_(self, condition: ExpOrStr, copy: bool = True, **opts) -> Case:
4855        instance = maybe_copy(self, copy)
4856        instance.set("default", maybe_parse(condition, copy=copy, **opts))
4857        return instance
key = 'case'
class Cast(Func):
4860class Cast(Func):
4861    arg_types = {
4862        "this": True,
4863        "to": True,
4864        "format": False,
4865        "safe": False,
4866        "action": False,
4867    }
4868
4869    @property
4870    def name(self) -> str:
4871        return self.this.name
4872
4873    @property
4874    def to(self) -> DataType:
4875        return self.args["to"]
4876
4877    @property
4878    def output_name(self) -> str:
4879        return self.name
4880
4881    def is_type(self, *dtypes: DATA_TYPE) -> bool:
4882        """
4883        Checks whether this Cast's DataType matches one of the provided data types. Nested types
4884        like arrays or structs will be compared using "structural equivalence" semantics, so e.g.
4885        array<int> != array<float>.
4886
4887        Args:
4888            dtypes: the data types to compare this Cast's DataType to.
4889
4890        Returns:
4891            True, if and only if there is a type in `dtypes` which is equal to this Cast's DataType.
4892        """
4893        return self.to.is_type(*dtypes)
arg_types = {'this': True, 'to': True, 'format': False, 'safe': False, 'action': False}
name: str
4869    @property
4870    def name(self) -> str:
4871        return self.this.name
to: DataType
4873    @property
4874    def to(self) -> DataType:
4875        return self.args["to"]
output_name: str
4877    @property
4878    def output_name(self) -> str:
4879        return self.name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
def is_type( self, *dtypes: Union[str, DataType, DataType.Type]) -> bool:
4881    def is_type(self, *dtypes: DATA_TYPE) -> bool:
4882        """
4883        Checks whether this Cast's DataType matches one of the provided data types. Nested types
4884        like arrays or structs will be compared using "structural equivalence" semantics, so e.g.
4885        array<int> != array<float>.
4886
4887        Args:
4888            dtypes: the data types to compare this Cast's DataType to.
4889
4890        Returns:
4891            True, if and only if there is a type in `dtypes` which is equal to this Cast's DataType.
4892        """
4893        return self.to.is_type(*dtypes)

Checks whether this Cast's DataType matches one of the provided data types. Nested types like arrays or structs will be compared using "structural equivalence" semantics, so e.g. array != array.

Arguments:
  • dtypes: the data types to compare this Cast's DataType to.
Returns:

True, if and only if there is a type in dtypes which is equal to this Cast's DataType.

key = 'cast'
class TryCast(Cast):
4896class TryCast(Cast):
4897    pass
key = 'trycast'
class Try(Func):
4900class Try(Func):
4901    pass
key = 'try'
class CastToStrType(Func):
4904class CastToStrType(Func):
4905    arg_types = {"this": True, "to": True}
arg_types = {'this': True, 'to': True}
key = 'casttostrtype'
class Collate(Binary, Func):
4908class Collate(Binary, Func):
4909    pass
key = 'collate'
class Ceil(Func):
4912class Ceil(Func):
4913    arg_types = {"this": True, "decimals": False}
4914    _sql_names = ["CEIL", "CEILING"]
arg_types = {'this': True, 'decimals': False}
key = 'ceil'
class Coalesce(Func):
4917class Coalesce(Func):
4918    arg_types = {"this": True, "expressions": False}
4919    is_var_len_args = True
4920    _sql_names = ["COALESCE", "IFNULL", "NVL"]
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'coalesce'
class Chr(Func):
4923class Chr(Func):
4924    arg_types = {"this": True, "charset": False, "expressions": False}
4925    is_var_len_args = True
4926    _sql_names = ["CHR", "CHAR"]
arg_types = {'this': True, 'charset': False, 'expressions': False}
is_var_len_args = True
key = 'chr'
class Concat(Func):
4929class Concat(Func):
4930    arg_types = {"expressions": True, "safe": False, "coalesce": False}
4931    is_var_len_args = True
arg_types = {'expressions': True, 'safe': False, 'coalesce': False}
is_var_len_args = True
key = 'concat'
class ConcatWs(Concat):
4934class ConcatWs(Concat):
4935    _sql_names = ["CONCAT_WS"]
key = 'concatws'
class ConnectByRoot(Func):
4939class ConnectByRoot(Func):
4940    pass
key = 'connectbyroot'
class Count(AggFunc):
4943class Count(AggFunc):
4944    arg_types = {"this": False, "expressions": False}
4945    is_var_len_args = True
arg_types = {'this': False, 'expressions': False}
is_var_len_args = True
key = 'count'
class CountIf(AggFunc):
4948class CountIf(AggFunc):
4949    _sql_names = ["COUNT_IF", "COUNTIF"]
key = 'countif'
class Cbrt(Func):
4953class Cbrt(Func):
4954    pass
key = 'cbrt'
class CurrentDate(Func):
4957class CurrentDate(Func):
4958    arg_types = {"this": False}
arg_types = {'this': False}
key = 'currentdate'
class CurrentDatetime(Func):
4961class CurrentDatetime(Func):
4962    arg_types = {"this": False}
arg_types = {'this': False}
key = 'currentdatetime'
class CurrentTime(Func):
4965class CurrentTime(Func):
4966    arg_types = {"this": False}
arg_types = {'this': False}
key = 'currenttime'
class CurrentTimestamp(Func):
4969class CurrentTimestamp(Func):
4970    arg_types = {"this": False, "transaction": False}
arg_types = {'this': False, 'transaction': False}
key = 'currenttimestamp'
class CurrentUser(Func):
4973class CurrentUser(Func):
4974    arg_types = {"this": False}
arg_types = {'this': False}
key = 'currentuser'
class DateAdd(Func, IntervalOp):
4977class DateAdd(Func, IntervalOp):
4978    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'dateadd'
class DateSub(Func, IntervalOp):
4981class DateSub(Func, IntervalOp):
4982    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'datesub'
class DateDiff(Func, TimeUnit):
4985class DateDiff(Func, TimeUnit):
4986    _sql_names = ["DATEDIFF", "DATE_DIFF"]
4987    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'datediff'
class DateTrunc(Func):
4990class DateTrunc(Func):
4991    arg_types = {"unit": True, "this": True, "zone": False}
4992
4993    def __init__(self, **args):
4994        unit = args.get("unit")
4995        if isinstance(unit, TimeUnit.VAR_LIKE):
4996            args["unit"] = Literal.string(
4997                (TimeUnit.UNABBREVIATED_UNIT_NAME.get(unit.name) or unit.name).upper()
4998            )
4999        elif isinstance(unit, Week):
5000            unit.set("this", Literal.string(unit.this.name.upper()))
5001
5002        super().__init__(**args)
5003
5004    @property
5005    def unit(self) -> Expression:
5006        return self.args["unit"]
DateTrunc(**args)
4993    def __init__(self, **args):
4994        unit = args.get("unit")
4995        if isinstance(unit, TimeUnit.VAR_LIKE):
4996            args["unit"] = Literal.string(
4997                (TimeUnit.UNABBREVIATED_UNIT_NAME.get(unit.name) or unit.name).upper()
4998            )
4999        elif isinstance(unit, Week):
5000            unit.set("this", Literal.string(unit.this.name.upper()))
5001
5002        super().__init__(**args)
arg_types = {'unit': True, 'this': True, 'zone': False}
unit: Expression
5004    @property
5005    def unit(self) -> Expression:
5006        return self.args["unit"]
key = 'datetrunc'
class DatetimeAdd(Func, IntervalOp):
5009class DatetimeAdd(Func, IntervalOp):
5010    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'datetimeadd'
class DatetimeSub(Func, IntervalOp):
5013class DatetimeSub(Func, IntervalOp):
5014    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'datetimesub'
class DatetimeDiff(Func, TimeUnit):
5017class DatetimeDiff(Func, TimeUnit):
5018    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'datetimediff'
class DatetimeTrunc(Func, TimeUnit):
5021class DatetimeTrunc(Func, TimeUnit):
5022    arg_types = {"this": True, "unit": True, "zone": False}
arg_types = {'this': True, 'unit': True, 'zone': False}
key = 'datetimetrunc'
class DayOfWeek(Func):
5025class DayOfWeek(Func):
5026    _sql_names = ["DAY_OF_WEEK", "DAYOFWEEK"]
key = 'dayofweek'
class DayOfMonth(Func):
5029class DayOfMonth(Func):
5030    _sql_names = ["DAY_OF_MONTH", "DAYOFMONTH"]
key = 'dayofmonth'
class DayOfYear(Func):
5033class DayOfYear(Func):
5034    _sql_names = ["DAY_OF_YEAR", "DAYOFYEAR"]
key = 'dayofyear'
class ToDays(Func):
5037class ToDays(Func):
5038    pass
key = 'todays'
class WeekOfYear(Func):
5041class WeekOfYear(Func):
5042    _sql_names = ["WEEK_OF_YEAR", "WEEKOFYEAR"]
key = 'weekofyear'
class MonthsBetween(Func):
5045class MonthsBetween(Func):
5046    arg_types = {"this": True, "expression": True, "roundoff": False}
arg_types = {'this': True, 'expression': True, 'roundoff': False}
key = 'monthsbetween'
class LastDay(Func, TimeUnit):
5049class LastDay(Func, TimeUnit):
5050    _sql_names = ["LAST_DAY", "LAST_DAY_OF_MONTH"]
5051    arg_types = {"this": True, "unit": False}
arg_types = {'this': True, 'unit': False}
key = 'lastday'
class Extract(Func):
5054class Extract(Func):
5055    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'extract'
class Timestamp(Func):
5058class Timestamp(Func):
5059    arg_types = {"this": False, "expression": False, "with_tz": False}
arg_types = {'this': False, 'expression': False, 'with_tz': False}
key = 'timestamp'
class TimestampAdd(Func, TimeUnit):
5062class TimestampAdd(Func, TimeUnit):
5063    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'timestampadd'
class TimestampSub(Func, TimeUnit):
5066class TimestampSub(Func, TimeUnit):
5067    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'timestampsub'
class TimestampDiff(Func, TimeUnit):
5070class TimestampDiff(Func, TimeUnit):
5071    _sql_names = ["TIMESTAMPDIFF", "TIMESTAMP_DIFF"]
5072    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'timestampdiff'
class TimestampTrunc(Func, TimeUnit):
5075class TimestampTrunc(Func, TimeUnit):
5076    arg_types = {"this": True, "unit": True, "zone": False}
arg_types = {'this': True, 'unit': True, 'zone': False}
key = 'timestamptrunc'
class TimeAdd(Func, TimeUnit):
5079class TimeAdd(Func, TimeUnit):
5080    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'timeadd'
class TimeSub(Func, TimeUnit):
5083class TimeSub(Func, TimeUnit):
5084    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'timesub'
class TimeDiff(Func, TimeUnit):
5087class TimeDiff(Func, TimeUnit):
5088    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'timediff'
class TimeTrunc(Func, TimeUnit):
5091class TimeTrunc(Func, TimeUnit):
5092    arg_types = {"this": True, "unit": True, "zone": False}
arg_types = {'this': True, 'unit': True, 'zone': False}
key = 'timetrunc'
class DateFromParts(Func):
5095class DateFromParts(Func):
5096    _sql_names = ["DATE_FROM_PARTS", "DATEFROMPARTS"]
5097    arg_types = {"year": True, "month": True, "day": True}
arg_types = {'year': True, 'month': True, 'day': True}
key = 'datefromparts'
class TimeFromParts(Func):
5100class TimeFromParts(Func):
5101    _sql_names = ["TIME_FROM_PARTS", "TIMEFROMPARTS"]
5102    arg_types = {
5103        "hour": True,
5104        "min": True,
5105        "sec": True,
5106        "nano": False,
5107        "fractions": False,
5108        "precision": False,
5109    }
arg_types = {'hour': True, 'min': True, 'sec': True, 'nano': False, 'fractions': False, 'precision': False}
key = 'timefromparts'
class DateStrToDate(Func):
5112class DateStrToDate(Func):
5113    pass
key = 'datestrtodate'
class DateToDateStr(Func):
5116class DateToDateStr(Func):
5117    pass
key = 'datetodatestr'
class DateToDi(Func):
5120class DateToDi(Func):
5121    pass
key = 'datetodi'
class Date(Func):
5125class Date(Func):
5126    arg_types = {"this": False, "zone": False, "expressions": False}
5127    is_var_len_args = True
arg_types = {'this': False, 'zone': False, 'expressions': False}
is_var_len_args = True
key = 'date'
class Day(Func):
5130class Day(Func):
5131    pass
key = 'day'
class Decode(Func):
5134class Decode(Func):
5135    arg_types = {"this": True, "charset": True, "replace": False}
arg_types = {'this': True, 'charset': True, 'replace': False}
key = 'decode'
class DiToDate(Func):
5138class DiToDate(Func):
5139    pass
key = 'ditodate'
class Encode(Func):
5142class Encode(Func):
5143    arg_types = {"this": True, "charset": True}
arg_types = {'this': True, 'charset': True}
key = 'encode'
class Exp(Func):
5146class Exp(Func):
5147    pass
key = 'exp'
class Explode(Func):
5151class Explode(Func):
5152    arg_types = {"this": True, "expressions": False}
5153    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'explode'
class ExplodeOuter(Explode):
5156class ExplodeOuter(Explode):
5157    pass
key = 'explodeouter'
class Posexplode(Explode):
5160class Posexplode(Explode):
5161    pass
key = 'posexplode'
class PosexplodeOuter(Posexplode, ExplodeOuter):
5164class PosexplodeOuter(Posexplode, ExplodeOuter):
5165    pass
key = 'posexplodeouter'
class Floor(Func):
5168class Floor(Func):
5169    arg_types = {"this": True, "decimals": False}
arg_types = {'this': True, 'decimals': False}
key = 'floor'
class FromBase64(Func):
5172class FromBase64(Func):
5173    pass
key = 'frombase64'
class ToBase64(Func):
5176class ToBase64(Func):
5177    pass
key = 'tobase64'
class GenerateDateArray(Func):
5180class GenerateDateArray(Func):
5181    arg_types = {"start": True, "end": True, "interval": False}
arg_types = {'start': True, 'end': True, 'interval': False}
key = 'generatedatearray'
class Greatest(Func):
5184class Greatest(Func):
5185    arg_types = {"this": True, "expressions": False}
5186    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'greatest'
class GroupConcat(AggFunc):
5189class GroupConcat(AggFunc):
5190    arg_types = {"this": True, "separator": False}
arg_types = {'this': True, 'separator': False}
key = 'groupconcat'
class Hex(Func):
5193class Hex(Func):
5194    pass
key = 'hex'
class Xor(Connector, Func):
5197class Xor(Connector, Func):
5198    arg_types = {"this": False, "expression": False, "expressions": False}
arg_types = {'this': False, 'expression': False, 'expressions': False}
key = 'xor'
class If(Func):
5201class If(Func):
5202    arg_types = {"this": True, "true": True, "false": False}
5203    _sql_names = ["IF", "IIF"]
arg_types = {'this': True, 'true': True, 'false': False}
key = 'if'
class Nullif(Func):
5206class Nullif(Func):
5207    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'nullif'
class Initcap(Func):
5210class Initcap(Func):
5211    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'initcap'
class IsNan(Func):
5214class IsNan(Func):
5215    _sql_names = ["IS_NAN", "ISNAN"]
key = 'isnan'
class IsInf(Func):
5218class IsInf(Func):
5219    _sql_names = ["IS_INF", "ISINF"]
key = 'isinf'
class JSONPath(Expression):
5222class JSONPath(Expression):
5223    arg_types = {"expressions": True}
5224
5225    @property
5226    def output_name(self) -> str:
5227        last_segment = self.expressions[-1].this
5228        return last_segment if isinstance(last_segment, str) else ""
arg_types = {'expressions': True}
output_name: str
5225    @property
5226    def output_name(self) -> str:
5227        last_segment = self.expressions[-1].this
5228        return last_segment if isinstance(last_segment, str) else ""

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'jsonpath'
class JSONPathPart(Expression):
5231class JSONPathPart(Expression):
5232    arg_types = {}
arg_types = {}
key = 'jsonpathpart'
class JSONPathFilter(JSONPathPart):
5235class JSONPathFilter(JSONPathPart):
5236    arg_types = {"this": True}
arg_types = {'this': True}
key = 'jsonpathfilter'
class JSONPathKey(JSONPathPart):
5239class JSONPathKey(JSONPathPart):
5240    arg_types = {"this": True}
arg_types = {'this': True}
key = 'jsonpathkey'
class JSONPathRecursive(JSONPathPart):
5243class JSONPathRecursive(JSONPathPart):
5244    arg_types = {"this": False}
arg_types = {'this': False}
key = 'jsonpathrecursive'
class JSONPathRoot(JSONPathPart):
5247class JSONPathRoot(JSONPathPart):
5248    pass
key = 'jsonpathroot'
class JSONPathScript(JSONPathPart):
5251class JSONPathScript(JSONPathPart):
5252    arg_types = {"this": True}
arg_types = {'this': True}
key = 'jsonpathscript'
class JSONPathSlice(JSONPathPart):
5255class JSONPathSlice(JSONPathPart):
5256    arg_types = {"start": False, "end": False, "step": False}
arg_types = {'start': False, 'end': False, 'step': False}
key = 'jsonpathslice'
class JSONPathSelector(JSONPathPart):
5259class JSONPathSelector(JSONPathPart):
5260    arg_types = {"this": True}
arg_types = {'this': True}
key = 'jsonpathselector'
class JSONPathSubscript(JSONPathPart):
5263class JSONPathSubscript(JSONPathPart):
5264    arg_types = {"this": True}
arg_types = {'this': True}
key = 'jsonpathsubscript'
class JSONPathUnion(JSONPathPart):
5267class JSONPathUnion(JSONPathPart):
5268    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'jsonpathunion'
class JSONPathWildcard(JSONPathPart):
5271class JSONPathWildcard(JSONPathPart):
5272    pass
key = 'jsonpathwildcard'
class FormatJson(Expression):
5275class FormatJson(Expression):
5276    pass
key = 'formatjson'
class JSONKeyValue(Expression):
5279class JSONKeyValue(Expression):
5280    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'jsonkeyvalue'
class JSONObject(Func):
5283class JSONObject(Func):
5284    arg_types = {
5285        "expressions": False,
5286        "null_handling": False,
5287        "unique_keys": False,
5288        "return_type": False,
5289        "encoding": False,
5290    }
arg_types = {'expressions': False, 'null_handling': False, 'unique_keys': False, 'return_type': False, 'encoding': False}
key = 'jsonobject'
class JSONObjectAgg(AggFunc):
5293class JSONObjectAgg(AggFunc):
5294    arg_types = {
5295        "expressions": False,
5296        "null_handling": False,
5297        "unique_keys": False,
5298        "return_type": False,
5299        "encoding": False,
5300    }
arg_types = {'expressions': False, 'null_handling': False, 'unique_keys': False, 'return_type': False, 'encoding': False}
key = 'jsonobjectagg'
class JSONArray(Func):
5304class JSONArray(Func):
5305    arg_types = {
5306        "expressions": True,
5307        "null_handling": False,
5308        "return_type": False,
5309        "strict": False,
5310    }
arg_types = {'expressions': True, 'null_handling': False, 'return_type': False, 'strict': False}
key = 'jsonarray'
class JSONArrayAgg(Func):
5314class JSONArrayAgg(Func):
5315    arg_types = {
5316        "this": True,
5317        "order": False,
5318        "null_handling": False,
5319        "return_type": False,
5320        "strict": False,
5321    }
arg_types = {'this': True, 'order': False, 'null_handling': False, 'return_type': False, 'strict': False}
key = 'jsonarrayagg'
class JSONColumnDef(Expression):
5326class JSONColumnDef(Expression):
5327    arg_types = {"this": False, "kind": False, "path": False, "nested_schema": False}
arg_types = {'this': False, 'kind': False, 'path': False, 'nested_schema': False}
key = 'jsoncolumndef'
class JSONSchema(Expression):
5330class JSONSchema(Expression):
5331    arg_types = {"expressions": True}
arg_types = {'expressions': True}
key = 'jsonschema'
class JSONTable(Func):
5335class JSONTable(Func):
5336    arg_types = {
5337        "this": True,
5338        "schema": True,
5339        "path": False,
5340        "error_handling": False,
5341        "empty_handling": False,
5342    }
arg_types = {'this': True, 'schema': True, 'path': False, 'error_handling': False, 'empty_handling': False}
key = 'jsontable'
class OpenJSONColumnDef(Expression):
5345class OpenJSONColumnDef(Expression):
5346    arg_types = {"this": True, "kind": True, "path": False, "as_json": False}
arg_types = {'this': True, 'kind': True, 'path': False, 'as_json': False}
key = 'openjsoncolumndef'
class OpenJSON(Func):
5349class OpenJSON(Func):
5350    arg_types = {"this": True, "path": False, "expressions": False}
arg_types = {'this': True, 'path': False, 'expressions': False}
key = 'openjson'
class JSONBContains(Binary):
5353class JSONBContains(Binary):
5354    _sql_names = ["JSONB_CONTAINS"]
key = 'jsonbcontains'
class JSONExtract(Binary, Func):
5357class JSONExtract(Binary, Func):
5358    arg_types = {"this": True, "expression": True, "only_json_types": False, "expressions": False}
5359    _sql_names = ["JSON_EXTRACT"]
5360    is_var_len_args = True
5361
5362    @property
5363    def output_name(self) -> str:
5364        return self.expression.output_name if not self.expressions else ""
arg_types = {'this': True, 'expression': True, 'only_json_types': False, 'expressions': False}
is_var_len_args = True
output_name: str
5362    @property
5363    def output_name(self) -> str:
5364        return self.expression.output_name if not self.expressions else ""

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'jsonextract'
class JSONExtractScalar(Binary, Func):
5367class JSONExtractScalar(Binary, Func):
5368    arg_types = {"this": True, "expression": True, "only_json_types": False, "expressions": False}
5369    _sql_names = ["JSON_EXTRACT_SCALAR"]
5370    is_var_len_args = True
5371
5372    @property
5373    def output_name(self) -> str:
5374        return self.expression.output_name
arg_types = {'this': True, 'expression': True, 'only_json_types': False, 'expressions': False}
is_var_len_args = True
output_name: str
5372    @property
5373    def output_name(self) -> str:
5374        return self.expression.output_name

Name of the output column if this expression is a selection.

If the Expression has no output name, an empty string is returned.

Example:
>>> from sqlglot import parse_one
>>> parse_one("SELECT a")sqlglot.expressions[0].output_name
'a'
>>> parse_one("SELECT b AS c")sqlglot.expressions[0].output_name
'c'
>>> parse_one("SELECT 1 + 2")sqlglot.expressions[0].output_name
''
key = 'jsonextractscalar'
class JSONBExtract(Binary, Func):
5377class JSONBExtract(Binary, Func):
5378    _sql_names = ["JSONB_EXTRACT"]
key = 'jsonbextract'
class JSONBExtractScalar(Binary, Func):
5381class JSONBExtractScalar(Binary, Func):
5382    _sql_names = ["JSONB_EXTRACT_SCALAR"]
key = 'jsonbextractscalar'
class JSONFormat(Func):
5385class JSONFormat(Func):
5386    arg_types = {"this": False, "options": False}
5387    _sql_names = ["JSON_FORMAT"]
arg_types = {'this': False, 'options': False}
key = 'jsonformat'
class JSONArrayContains(Binary, Predicate, Func):
5391class JSONArrayContains(Binary, Predicate, Func):
5392    _sql_names = ["JSON_ARRAY_CONTAINS"]
key = 'jsonarraycontains'
class ParseJSON(Func):
5395class ParseJSON(Func):
5396    # BigQuery, Snowflake have PARSE_JSON, Presto has JSON_PARSE
5397    _sql_names = ["PARSE_JSON", "JSON_PARSE"]
5398    arg_types = {"this": True, "expressions": False}
5399    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'parsejson'
class Least(Func):
5402class Least(Func):
5403    arg_types = {"this": True, "expressions": False}
5404    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'least'
class Left(Func):
5407class Left(Func):
5408    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'left'
class Length(Func):
5415class Length(Func):
5416    _sql_names = ["LENGTH", "LEN"]
key = 'length'
class Levenshtein(Func):
5419class Levenshtein(Func):
5420    arg_types = {
5421        "this": True,
5422        "expression": False,
5423        "ins_cost": False,
5424        "del_cost": False,
5425        "sub_cost": False,
5426    }
arg_types = {'this': True, 'expression': False, 'ins_cost': False, 'del_cost': False, 'sub_cost': False}
key = 'levenshtein'
class Ln(Func):
5429class Ln(Func):
5430    pass
key = 'ln'
class Log(Func):
5433class Log(Func):
5434    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'log'
class LogicalOr(AggFunc):
5437class LogicalOr(AggFunc):
5438    _sql_names = ["LOGICAL_OR", "BOOL_OR", "BOOLOR_AGG"]
key = 'logicalor'
class LogicalAnd(AggFunc):
5441class LogicalAnd(AggFunc):
5442    _sql_names = ["LOGICAL_AND", "BOOL_AND", "BOOLAND_AGG"]
key = 'logicaland'
class Lower(Func):
5445class Lower(Func):
5446    _sql_names = ["LOWER", "LCASE"]
key = 'lower'
class Map(Func):
5449class Map(Func):
5450    arg_types = {"keys": False, "values": False}
5451
5452    @property
5453    def keys(self) -> t.List[Expression]:
5454        keys = self.args.get("keys")
5455        return keys.expressions if keys else []
5456
5457    @property
5458    def values(self) -> t.List[Expression]:
5459        values = self.args.get("values")
5460        return values.expressions if values else []
arg_types = {'keys': False, 'values': False}
keys: List[Expression]
5452    @property
5453    def keys(self) -> t.List[Expression]:
5454        keys = self.args.get("keys")
5455        return keys.expressions if keys else []
values: List[Expression]
5457    @property
5458    def values(self) -> t.List[Expression]:
5459        values = self.args.get("values")
5460        return values.expressions if values else []
key = 'map'
class ToMap(Func):
5464class ToMap(Func):
5465    pass
key = 'tomap'
class MapFromEntries(Func):
5468class MapFromEntries(Func):
5469    pass
key = 'mapfromentries'
class StarMap(Func):
5472class StarMap(Func):
5473    pass
key = 'starmap'
class VarMap(Func):
5476class VarMap(Func):
5477    arg_types = {"keys": True, "values": True}
5478    is_var_len_args = True
5479
5480    @property
5481    def keys(self) -> t.List[Expression]:
5482        return self.args["keys"].expressions
5483
5484    @property
5485    def values(self) -> t.List[Expression]:
5486        return self.args["values"].expressions
arg_types = {'keys': True, 'values': True}
is_var_len_args = True
keys: List[Expression]
5480    @property
5481    def keys(self) -> t.List[Expression]:
5482        return self.args["keys"].expressions
values: List[Expression]
5484    @property
5485    def values(self) -> t.List[Expression]:
5486        return self.args["values"].expressions
key = 'varmap'
class MatchAgainst(Func):
5490class MatchAgainst(Func):
5491    arg_types = {"this": True, "expressions": True, "modifier": False}
arg_types = {'this': True, 'expressions': True, 'modifier': False}
key = 'matchagainst'
class Max(AggFunc):
5494class Max(AggFunc):
5495    arg_types = {"this": True, "expressions": False}
5496    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'max'
class MD5(Func):
5499class MD5(Func):
5500    _sql_names = ["MD5"]
key = 'md5'
class MD5Digest(Func):
5504class MD5Digest(Func):
5505    _sql_names = ["MD5_DIGEST"]
key = 'md5digest'
class Min(AggFunc):
5508class Min(AggFunc):
5509    arg_types = {"this": True, "expressions": False}
5510    is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
is_var_len_args = True
key = 'min'
class Month(Func):
5513class Month(Func):
5514    pass
key = 'month'
class AddMonths(Func):
5517class AddMonths(Func):
5518    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'addmonths'
class Nvl2(Func):
5521class Nvl2(Func):
5522    arg_types = {"this": True, "true": True, "false": False}
arg_types = {'this': True, 'true': True, 'false': False}
key = 'nvl2'
class Predict(Func):
5526class Predict(Func):
5527    arg_types = {"this": True, "expression": True, "params_struct": False}
arg_types = {'this': True, 'expression': True, 'params_struct': False}
key = 'predict'
class Pow(Binary, Func):
5530class Pow(Binary, Func):
5531    _sql_names = ["POWER", "POW"]
key = 'pow'
class PercentileCont(AggFunc):
5534class PercentileCont(AggFunc):
5535    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'percentilecont'
class PercentileDisc(AggFunc):
5538class PercentileDisc(AggFunc):
5539    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'percentiledisc'
class Quantile(AggFunc):
5542class Quantile(AggFunc):
5543    arg_types = {"this": True, "quantile": True}
arg_types = {'this': True, 'quantile': True}
key = 'quantile'
class ApproxQuantile(Quantile):
5546class ApproxQuantile(Quantile):
5547    arg_types = {"this": True, "quantile": True, "accuracy": False, "weight": False}
arg_types = {'this': True, 'quantile': True, 'accuracy': False, 'weight': False}
key = 'approxquantile'
class Quarter(Func):
5550class Quarter(Func):
5551    pass
key = 'quarter'
class Rand(Func):
5554class Rand(Func):
5555    _sql_names = ["RAND", "RANDOM"]
5556    arg_types = {"this": False}
arg_types = {'this': False}
key = 'rand'
class Randn(Func):
5559class Randn(Func):
5560    arg_types = {"this": False}
arg_types = {'this': False}
key = 'randn'
class RangeN(Func):
5563class RangeN(Func):
5564    arg_types = {"this": True, "expressions": True, "each": False}
arg_types = {'this': True, 'expressions': True, 'each': False}
key = 'rangen'
class ReadCSV(Func):
5567class ReadCSV(Func):
5568    _sql_names = ["READ_CSV"]
5569    is_var_len_args = True
5570    arg_types = {"this": True, "expressions": False}
is_var_len_args = True
arg_types = {'this': True, 'expressions': False}
key = 'readcsv'
class Reduce(Func):
5573class Reduce(Func):
5574    arg_types = {"this": True, "initial": True, "merge": True, "finish": False}
arg_types = {'this': True, 'initial': True, 'merge': True, 'finish': False}
key = 'reduce'
class RegexpExtract(Func):
5577class RegexpExtract(Func):
5578    arg_types = {
5579        "this": True,
5580        "expression": True,
5581        "position": False,
5582        "occurrence": False,
5583        "parameters": False,
5584        "group": False,
5585    }
arg_types = {'this': True, 'expression': True, 'position': False, 'occurrence': False, 'parameters': False, 'group': False}
key = 'regexpextract'
class RegexpReplace(Func):
5588class RegexpReplace(Func):
5589    arg_types = {
5590        "this": True,
5591        "expression": True,
5592        "replacement": False,
5593        "position": False,
5594        "occurrence": False,
5595        "modifiers": False,
5596    }
arg_types = {'this': True, 'expression': True, 'replacement': False, 'position': False, 'occurrence': False, 'modifiers': False}
key = 'regexpreplace'
class RegexpLike(Binary, Func):
5599class RegexpLike(Binary, Func):
5600    arg_types = {"this": True, "expression": True, "flag": False}
arg_types = {'this': True, 'expression': True, 'flag': False}
key = 'regexplike'
class RegexpILike(Binary, Func):
5603class RegexpILike(Binary, Func):
5604    arg_types = {"this": True, "expression": True, "flag": False}
arg_types = {'this': True, 'expression': True, 'flag': False}
key = 'regexpilike'
class RegexpSplit(Func):
5609class RegexpSplit(Func):
5610    arg_types = {"this": True, "expression": True, "limit": False}
arg_types = {'this': True, 'expression': True, 'limit': False}
key = 'regexpsplit'
class Repeat(Func):
5613class Repeat(Func):
5614    arg_types = {"this": True, "times": True}
arg_types = {'this': True, 'times': True}
key = 'repeat'
class Round(Func):
5619class Round(Func):
5620    arg_types = {"this": True, "decimals": False, "truncate": False}
arg_types = {'this': True, 'decimals': False, 'truncate': False}
key = 'round'
class RowNumber(Func):
5623class RowNumber(Func):
5624    arg_types: t.Dict[str, t.Any] = {}
arg_types: Dict[str, Any] = {}
key = 'rownumber'
class SafeDivide(Func):
5627class SafeDivide(Func):
5628    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'safedivide'
class SHA(Func):
5631class SHA(Func):
5632    _sql_names = ["SHA", "SHA1"]
key = 'sha'
class SHA2(Func):
5635class SHA2(Func):
5636    _sql_names = ["SHA2"]
5637    arg_types = {"this": True, "length": False}
arg_types = {'this': True, 'length': False}
key = 'sha2'
class Sign(Func):
5640class Sign(Func):
5641    _sql_names = ["SIGN", "SIGNUM"]
key = 'sign'
class SortArray(Func):
5644class SortArray(Func):
5645    arg_types = {"this": True, "asc": False}
arg_types = {'this': True, 'asc': False}
key = 'sortarray'
class Split(Func):
5648class Split(Func):
5649    arg_types = {"this": True, "expression": True, "limit": False}
arg_types = {'this': True, 'expression': True, 'limit': False}
key = 'split'
class Substring(Func):
5654class Substring(Func):
5655    arg_types = {"this": True, "start": False, "length": False}
arg_types = {'this': True, 'start': False, 'length': False}
key = 'substring'
class StandardHash(Func):
5658class StandardHash(Func):
5659    arg_types = {"this": True, "expression": False}
arg_types = {'this': True, 'expression': False}
key = 'standardhash'
class StartsWith(Func):
5662class StartsWith(Func):
5663    _sql_names = ["STARTS_WITH", "STARTSWITH"]
5664    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'startswith'
class StrPosition(Func):
5667class StrPosition(Func):
5668    arg_types = {
5669        "this": True,
5670        "substr": True,
5671        "position": False,
5672        "instance": False,
5673    }
arg_types = {'this': True, 'substr': True, 'position': False, 'instance': False}
key = 'strposition'
class StrToDate(Func):
5676class StrToDate(Func):
5677    arg_types = {"this": True, "format": True}
arg_types = {'this': True, 'format': True}
key = 'strtodate'
class StrToTime(Func):
5680class StrToTime(Func):
5681    arg_types = {"this": True, "format": True, "zone": False}
arg_types = {'this': True, 'format': True, 'zone': False}
key = 'strtotime'
class StrToUnix(Func):
5686class StrToUnix(Func):
5687    arg_types = {"this": False, "format": False}
arg_types = {'this': False, 'format': False}
key = 'strtounix'
class StrToMap(Func):
5692class StrToMap(Func):
5693    arg_types = {
5694        "this": True,
5695        "pair_delim": False,
5696        "key_value_delim": False,
5697        "duplicate_resolution_callback": False,
5698    }
arg_types = {'this': True, 'pair_delim': False, 'key_value_delim': False, 'duplicate_resolution_callback': False}
key = 'strtomap'
class NumberToStr(Func):
5701class NumberToStr(Func):
5702    arg_types = {"this": True, "format": True, "culture": False}
arg_types = {'this': True, 'format': True, 'culture': False}
key = 'numbertostr'
class FromBase(Func):
5705class FromBase(Func):
5706    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'frombase'
class Struct(Func):
5709class Struct(Func):
5710    arg_types = {"expressions": False}
5711    is_var_len_args = True
arg_types = {'expressions': False}
is_var_len_args = True
key = 'struct'
class StructExtract(Func):
5714class StructExtract(Func):
5715    arg_types = {"this": True, "expression": True}
arg_types = {'this': True, 'expression': True}
key = 'structextract'
class Stuff(Func):
5720class Stuff(Func):
5721    _sql_names = ["STUFF", "INSERT"]
5722    arg_types = {"this": True, "start": True, "length": True, "expression": True}
arg_types = {'this': True, 'start': True, 'length': True, 'expression': True}
key = 'stuff'
class Sum(AggFunc):
5725class Sum(AggFunc):
5726    pass
key = 'sum'
class Sqrt(Func):
5729class Sqrt(Func):
5730    pass
key = 'sqrt'
class Stddev(AggFunc):
5733class Stddev(AggFunc):
5734    pass
key = 'stddev'
class StddevPop(AggFunc):
5737class StddevPop(AggFunc):
5738    pass
key = 'stddevpop'
class StddevSamp(AggFunc):
5741class StddevSamp(AggFunc):
5742    pass
key = 'stddevsamp'
class TimeToStr(Func):
5745class TimeToStr(Func):
5746    arg_types = {"this": True, "format": True, "culture": False, "timezone": False}
arg_types = {'this': True, 'format': True, 'culture': False, 'timezone': False}
key = 'timetostr'
class TimeToTimeStr(Func):
5749class TimeToTimeStr(Func):
5750    pass
key = 'timetotimestr'
class TimeToUnix(Func):
5753class TimeToUnix(Func):
5754    pass
key = 'timetounix'
class TimeStrToDate(Func):
5757class TimeStrToDate(Func):
5758    pass
key = 'timestrtodate'
class TimeStrToTime(Func):
5761class TimeStrToTime(Func):
5762    pass
key = 'timestrtotime'
class TimeStrToUnix(Func):
5765class TimeStrToUnix(Func):
5766    pass
key = 'timestrtounix'
class Trim(Func):
5769class Trim(Func):
5770    arg_types = {
5771        "this": True,
5772        "expression": False,
5773        "position": False,
5774        "collation": False,
5775    }
arg_types = {'this': True, 'expression': False, 'position': False, 'collation': False}
key = 'trim'
class TsOrDsAdd(Func, TimeUnit):
5778class TsOrDsAdd(Func, TimeUnit):
5779    # return_type is used to correctly cast the arguments of this expression when transpiling it
5780    arg_types = {"this": True, "expression": True, "unit": False, "return_type": False}
5781
5782    @property
5783    def return_type(self) -> DataType:
5784        return DataType.build(self.args.get("return_type") or DataType.Type.DATE)
arg_types = {'this': True, 'expression': True, 'unit': False, 'return_type': False}
return_type: DataType
5782    @property
5783    def return_type(self) -> DataType:
5784        return DataType.build(self.args.get("return_type") or DataType.Type.DATE)
key = 'tsordsadd'
class TsOrDsDiff(Func, TimeUnit):
5787class TsOrDsDiff(Func, TimeUnit):
5788    arg_types = {"this": True, "expression": True, "unit": False}
arg_types = {'this': True, 'expression': True, 'unit': False}
key = 'tsordsdiff'
class TsOrDsToDateStr(Func):
5791class TsOrDsToDateStr(Func):
5792    pass
key = 'tsordstodatestr'
class TsOrDsToDate(Func):
5795class TsOrDsToDate(Func):
5796    arg_types = {"this": True, "format": False, "safe": False}
arg_types = {'this': True, 'format': False, 'safe': False}
key = 'tsordstodate'
class TsOrDsToTime(Func):
5799class TsOrDsToTime(Func):
5800    pass
key = 'tsordstotime'
class TsOrDsToTimestamp(Func):
5803class TsOrDsToTimestamp(Func):
5804    pass
key = 'tsordstotimestamp'
class TsOrDiToDi(Func):
5807class TsOrDiToDi(Func):
5808    pass
key = 'tsorditodi'
class Unhex(Func):
5811class Unhex(Func):
5812    pass
key = 'unhex'
class UnixDate(Func):
5816class UnixDate(Func):
5817    pass
key = 'unixdate'
class UnixToStr(Func):
5820class UnixToStr(Func):
5821    arg_types = {"this": True, "format": False}
arg_types = {'this': True, 'format': False}
key = 'unixtostr'
class UnixToTime(Func):
5826class UnixToTime(Func):
5827    arg_types = {
5828        "this": True,
5829        "scale": False,
5830        "zone": False,
5831        "hours": False,
5832        "minutes": False,
5833        "format": False,
5834    }
5835
5836    SECONDS = Literal.number(0)
5837    DECIS = Literal.number(1)
5838    CENTIS = Literal.number(2)
5839    MILLIS = Literal.number(3)
5840    DECIMILLIS = Literal.number(4)
5841    CENTIMILLIS = Literal.number(5)
5842    MICROS = Literal.number(6)
5843    DECIMICROS = Literal.number(7)
5844    CENTIMICROS = Literal.number(8)
5845    NANOS = Literal.number(9)
arg_types = {'this': True, 'scale': False, 'zone': False, 'hours': False, 'minutes': False, 'format': False}
SECONDS = Literal(this=0, is_string=False)
DECIS = Literal(this=1, is_string=False)
CENTIS = Literal(this=2, is_string=False)
MILLIS = Literal(this=3, is_string=False)
DECIMILLIS = Literal(this=4, is_string=False)
CENTIMILLIS = Literal(this=5, is_string=False)
MICROS = Literal(this=6, is_string=False)
DECIMICROS = Literal(this=7, is_string=False)
CENTIMICROS = Literal(this=8, is_string=False)
NANOS = Literal(this=9, is_string=False)
key = 'unixtotime'
class UnixToTimeStr(Func):
5848class UnixToTimeStr(Func):
5849    pass
key = 'unixtotimestr'
class TimestampFromParts(Func):
5852class TimestampFromParts(Func):
5853    _sql_names = ["TIMESTAMP_FROM_PARTS", "TIMESTAMPFROMPARTS"]
5854    arg_types = {
5855        "year": True,
5856        "month": True,
5857        "day": True,
5858        "hour": True,
5859        "min": True,
5860        "sec": True,
5861        "nano": False,
5862        "zone": False,
5863        "milli": False,
5864    }
arg_types = {'year': True, 'month': True, 'day': True, 'hour': True, 'min': True, 'sec': True, 'nano': False, 'zone': False, 'milli': False}
key = 'timestampfromparts'
class Upper(Func):
5867class Upper(Func):
5868    _sql_names = ["UPPER", "UCASE"]
key = 'upper'
class Corr(Binary, AggFunc):
5871class Corr(Binary, AggFunc):
5872    pass
key = 'corr'
class Variance(AggFunc):
5875class Variance(AggFunc):
5876    _sql_names = ["VARIANCE", "VARIANCE_SAMP", "VAR_SAMP"]
key = 'variance'
class VariancePop(AggFunc):
5879class VariancePop(AggFunc):
5880    _sql_names = ["VARIANCE_POP", "VAR_POP"]
key = 'variancepop'
class CovarSamp(Binary, AggFunc):
5883class CovarSamp(Binary, AggFunc):
5884    pass
key = 'covarsamp'
class CovarPop(Binary, AggFunc):
5887class CovarPop(Binary, AggFunc):
5888    pass
key = 'covarpop'
class Week(Func):
5891class Week(Func):
5892    arg_types = {"this": True, "mode": False}
arg_types = {'this': True, 'mode': False}
key = 'week'
class XMLTable(Func):
5895class XMLTable(Func):
5896    arg_types = {"this": True, "passing": False, "columns": False, "by_ref": False}
arg_types = {'this': True, 'passing': False, 'columns': False, 'by_ref': False}
key = 'xmltable'
class Year(Func):
5899class Year(Func):
5900    pass
key = 'year'
class Use(Expression):
5903class Use(Expression):
5904    arg_types = {"this": True, "kind": False}
arg_types = {'this': True, 'kind': False}
key = 'use'
class Merge(Expression):
5907class Merge(Expression):
5908    arg_types = {
5909        "this": True,
5910        "using": True,
5911        "on": True,
5912        "expressions": True,
5913        "with": False,
5914    }
arg_types = {'this': True, 'using': True, 'on': True, 'expressions': True, 'with': False}
key = 'merge'
class When(Func):
5917class When(Func):
5918    arg_types = {"matched": True, "source": False, "condition": False, "then": True}
arg_types = {'matched': True, 'source': False, 'condition': False, 'then': True}
key = 'when'
class NextValueFor(Func):
5923class NextValueFor(Func):
5924    arg_types = {"this": True, "order": False}
arg_types = {'this': True, 'order': False}
key = 'nextvaluefor'
class Semicolon(Expression):
5929class Semicolon(Expression):
5930    arg_types = {}
arg_types = {}
key = 'semicolon'
ALL_FUNCTIONS = [<class 'Abs'>, <class 'AddMonths'>, <class 'AnonymousAggFunc'>, <class 'AnyValue'>, <class 'ApproxDistinct'>, <class 'ApproxQuantile'>, <class 'ApproxTopK'>, <class 'ArgMax'>, <class 'ArgMin'>, <class 'Array'>, <class 'ArrayAgg'>, <class 'ArrayAll'>, <class 'ArrayAny'>, <class 'ArrayConcat'>, <class 'ArrayContains'>, <class 'ArrayFilter'>, <class 'ArrayOverlaps'>, <class 'ArraySize'>, <class 'ArraySort'>, <class 'ArraySum'>, <class 'ArrayToString'>, <class 'ArrayUnionAgg'>, <class 'ArrayUniqueAgg'>, <class 'Avg'>, <class 'Case'>, <class 'Cast'>, <class 'CastToStrType'>, <class 'Cbrt'>, <class 'Ceil'>, <class 'Chr'>, <class 'Coalesce'>, <class 'Collate'>, <class 'CombinedAggFunc'>, <class 'CombinedParameterizedAgg'>, <class 'Concat'>, <class 'ConcatWs'>, <class 'ConnectByRoot'>, <class 'Convert'>, <class 'Corr'>, <class 'Count'>, <class 'CountIf'>, <class 'CovarPop'>, <class 'CovarSamp'>, <class 'CurrentDate'>, <class 'CurrentDatetime'>, <class 'CurrentTime'>, <class 'CurrentTimestamp'>, <class 'CurrentUser'>, <class 'Date'>, <class 'DateAdd'>, <class 'DateDiff'>, <class 'DateFromParts'>, <class 'DateStrToDate'>, <class 'DateSub'>, <class 'DateToDateStr'>, <class 'DateToDi'>, <class 'DateTrunc'>, <class 'DatetimeAdd'>, <class 'DatetimeDiff'>, <class 'DatetimeSub'>, <class 'DatetimeTrunc'>, <class 'Day'>, <class 'DayOfMonth'>, <class 'DayOfWeek'>, <class 'DayOfYear'>, <class 'Decode'>, <class 'DiToDate'>, <class 'Encode'>, <class 'Exp'>, <class 'Explode'>, <class 'ExplodeOuter'>, <class 'Extract'>, <class 'First'>, <class 'FirstValue'>, <class 'Flatten'>, <class 'Floor'>, <class 'FromBase'>, <class 'FromBase64'>, <class 'GenerateDateArray'>, <class 'GenerateSeries'>, <class 'Greatest'>, <class 'GroupConcat'>, <class 'Hex'>, <class 'Hll'>, <class 'If'>, <class 'Initcap'>, <class 'IsInf'>, <class 'IsNan'>, <class 'JSONArray'>, <class 'JSONArrayAgg'>, <class 'JSONArrayContains'>, <class 'JSONBExtract'>, <class 'JSONBExtractScalar'>, <class 'JSONExtract'>, <class 'JSONExtractScalar'>, <class 'JSONFormat'>, <class 'JSONObject'>, <class 'JSONObjectAgg'>, <class 'JSONTable'>, <class 'Lag'>, <class 'Last'>, <class 'LastDay'>, <class 'LastValue'>, <class 'Lead'>, <class 'Least'>, <class 'Left'>, <class 'Length'>, <class 'Levenshtein'>, <class 'Ln'>, <class 'Log'>, <class 'LogicalAnd'>, <class 'LogicalOr'>, <class 'Lower'>, <class 'MD5'>, <class 'MD5Digest'>, <class 'Map'>, <class 'MapFromEntries'>, <class 'MatchAgainst'>, <class 'Max'>, <class 'Min'>, <class 'Month'>, <class 'MonthsBetween'>, <class 'NextValueFor'>, <class 'NthValue'>, <class 'Nullif'>, <class 'NumberToStr'>, <class 'Nvl2'>, <class 'OpenJSON'>, <class 'ParameterizedAgg'>, <class 'ParseJSON'>, <class 'PercentileCont'>, <class 'PercentileDisc'>, <class 'Posexplode'>, <class 'PosexplodeOuter'>, <class 'Pow'>, <class 'Predict'>, <class 'Quantile'>, <class 'Quarter'>, <class 'Rand'>, <class 'Randn'>, <class 'RangeN'>, <class 'ReadCSV'>, <class 'Reduce'>, <class 'RegexpExtract'>, <class 'RegexpILike'>, <class 'RegexpLike'>, <class 'RegexpReplace'>, <class 'RegexpSplit'>, <class 'Repeat'>, <class 'Right'>, <class 'Round'>, <class 'RowNumber'>, <class 'SHA'>, <class 'SHA2'>, <class 'SafeDivide'>, <class 'Sign'>, <class 'SortArray'>, <class 'Split'>, <class 'Sqrt'>, <class 'StandardHash'>, <class 'StarMap'>, <class 'StartsWith'>, <class 'Stddev'>, <class 'StddevPop'>, <class 'StddevSamp'>, <class 'StrPosition'>, <class 'StrToDate'>, <class 'StrToMap'>, <class 'StrToTime'>, <class 'StrToUnix'>, <class 'Struct'>, <class 'StructExtract'>, <class 'Stuff'>, <class 'Substring'>, <class 'Sum'>, <class 'TimeAdd'>, <class 'TimeDiff'>, <class 'TimeFromParts'>, <class 'TimeStrToDate'>, <class 'TimeStrToTime'>, <class 'TimeStrToUnix'>, <class 'TimeSub'>, <class 'TimeToStr'>, <class 'TimeToTimeStr'>, <class 'TimeToUnix'>, <class 'TimeTrunc'>, <class 'Timestamp'>, <class 'TimestampAdd'>, <class 'TimestampDiff'>, <class 'TimestampFromParts'>, <class 'TimestampSub'>, <class 'TimestampTrunc'>, <class 'ToArray'>, <class 'ToBase64'>, <class 'ToChar'>, <class 'ToDays'>, <class 'ToMap'>, <class 'ToNumber'>, <class 'Transform'>, <class 'Trim'>, <class 'Try'>, <class 'TryCast'>, <class 'TsOrDiToDi'>, <class 'TsOrDsAdd'>, <class 'TsOrDsDiff'>, <class 'TsOrDsToDate'>, <class 'TsOrDsToDateStr'>, <class 'TsOrDsToTime'>, <class 'TsOrDsToTimestamp'>, <class 'Unhex'>, <class 'UnixDate'>, <class 'UnixToStr'>, <class 'UnixToTime'>, <class 'UnixToTimeStr'>, <class 'Upper'>, <class 'VarMap'>, <class 'Variance'>, <class 'VariancePop'>, <class 'Week'>, <class 'WeekOfYear'>, <class 'When'>, <class 'XMLTable'>, <class 'Xor'>, <class 'Year'>]
FUNCTION_BY_NAME = {'ABS': <class 'Abs'>, 'ADD_MONTHS': <class 'AddMonths'>, 'ANONYMOUS_AGG_FUNC': <class 'AnonymousAggFunc'>, 'ANY_VALUE': <class 'AnyValue'>, 'APPROX_DISTINCT': <class 'ApproxDistinct'>, 'APPROX_COUNT_DISTINCT': <class 'ApproxDistinct'>, 'APPROX_QUANTILE': <class 'ApproxQuantile'>, 'APPROX_TOP_K': <class 'ApproxTopK'>, 'ARG_MAX': <class 'ArgMax'>, 'ARGMAX': <class 'ArgMax'>, 'MAX_BY': <class 'ArgMax'>, 'ARG_MIN': <class 'ArgMin'>, 'ARGMIN': <class 'ArgMin'>, 'MIN_BY': <class 'ArgMin'>, 'ARRAY': <class 'Array'>, 'ARRAY_AGG': <class 'ArrayAgg'>, 'ARRAY_ALL': <class 'ArrayAll'>, 'ARRAY_ANY': <class 'ArrayAny'>, 'ARRAY_CONCAT': <class 'ArrayConcat'>, 'ARRAY_CAT': <class 'ArrayConcat'>, 'ARRAY_CONTAINS': <class 'ArrayContains'>, 'FILTER': <class 'ArrayFilter'>, 'ARRAY_FILTER': <class 'ArrayFilter'>, 'ARRAY_OVERLAPS': <class 'ArrayOverlaps'>, 'ARRAY_SIZE': <class 'ArraySize'>, 'ARRAY_LENGTH': <class 'ArraySize'>, 'ARRAY_SORT': <class 'ArraySort'>, 'ARRAY_SUM': <class 'ArraySum'>, 'ARRAY_TO_STRING': <class 'ArrayToString'>, 'ARRAY_JOIN': <class 'ArrayToString'>, 'ARRAY_UNION_AGG': <class 'ArrayUnionAgg'>, 'ARRAY_UNIQUE_AGG': <class 'ArrayUniqueAgg'>, 'AVG': <class 'Avg'>, 'CASE': <class 'Case'>, 'CAST': <class 'Cast'>, 'CAST_TO_STR_TYPE': <class 'CastToStrType'>, 'CBRT': <class 'Cbrt'>, 'CEIL': <class 'Ceil'>, 'CEILING': <class 'Ceil'>, 'CHR': <class 'Chr'>, 'CHAR': <class 'Chr'>, 'COALESCE': <class 'Coalesce'>, 'IFNULL': <class 'Coalesce'>, 'NVL': <class 'Coalesce'>, 'COLLATE': <class 'Collate'>, 'COMBINED_AGG_FUNC': <class 'CombinedAggFunc'>, 'COMBINED_PARAMETERIZED_AGG': <class 'CombinedParameterizedAgg'>, 'CONCAT': <class 'Concat'>, 'CONCAT_WS': <class 'ConcatWs'>, 'CONNECT_BY_ROOT': <class 'ConnectByRoot'>, 'CONVERT': <class 'Convert'>, 'CORR': <class 'Corr'>, 'COUNT': <class 'Count'>, 'COUNT_IF': <class 'CountIf'>, 'COUNTIF': <class 'CountIf'>, 'COVAR_POP': <class 'CovarPop'>, 'COVAR_SAMP': <class 'CovarSamp'>, 'CURRENT_DATE': <class 'CurrentDate'>, 'CURRENT_DATETIME': <class 'CurrentDatetime'>, 'CURRENT_TIME': <class 'CurrentTime'>, 'CURRENT_TIMESTAMP': <class 'CurrentTimestamp'>, 'CURRENT_USER': <class 'CurrentUser'>, 'DATE': <class 'Date'>, 'DATE_ADD': <class 'DateAdd'>, 'DATEDIFF': <class 'DateDiff'>, 'DATE_DIFF': <class 'DateDiff'>, 'DATE_FROM_PARTS': <class 'DateFromParts'>, 'DATEFROMPARTS': <class 'DateFromParts'>, 'DATE_STR_TO_DATE': <class 'DateStrToDate'>, 'DATE_SUB': <class 'DateSub'>, 'DATE_TO_DATE_STR': <class 'DateToDateStr'>, 'DATE_TO_DI': <class 'DateToDi'>, 'DATE_TRUNC': <class 'DateTrunc'>, 'DATETIME_ADD': <class 'DatetimeAdd'>, 'DATETIME_DIFF': <class 'DatetimeDiff'>, 'DATETIME_SUB': <class 'DatetimeSub'>, 'DATETIME_TRUNC': <class 'DatetimeTrunc'>, 'DAY': <class 'Day'>, 'DAY_OF_MONTH': <class 'DayOfMonth'>, 'DAYOFMONTH': <class 'DayOfMonth'>, 'DAY_OF_WEEK': <class 'DayOfWeek'>, 'DAYOFWEEK': <class 'DayOfWeek'>, 'DAY_OF_YEAR': <class 'DayOfYear'>, 'DAYOFYEAR': <class 'DayOfYear'>, 'DECODE': <class 'Decode'>, 'DI_TO_DATE': <class 'DiToDate'>, 'ENCODE': <class 'Encode'>, 'EXP': <class 'Exp'>, 'EXPLODE': <class 'Explode'>, 'EXPLODE_OUTER': <class 'ExplodeOuter'>, 'EXTRACT': <class 'Extract'>, 'FIRST': <class 'First'>, 'FIRST_VALUE': <class 'FirstValue'>, 'FLATTEN': <class 'Flatten'>, 'FLOOR': <class 'Floor'>, 'FROM_BASE': <class 'FromBase'>, 'FROM_BASE64': <class 'FromBase64'>, 'GENERATE_DATE_ARRAY': <class 'GenerateDateArray'>, 'GENERATE_SERIES': <class 'GenerateSeries'>, 'GREATEST': <class 'Greatest'>, 'GROUP_CONCAT': <class 'GroupConcat'>, 'HEX': <class 'Hex'>, 'HLL': <class 'Hll'>, 'IF': <class 'If'>, 'IIF': <class 'If'>, 'INITCAP': <class 'Initcap'>, 'IS_INF': <class 'IsInf'>, 'ISINF': <class 'IsInf'>, 'IS_NAN': <class 'IsNan'>, 'ISNAN': <class 'IsNan'>, 'J_S_O_N_ARRAY': <class 'JSONArray'>, 'J_S_O_N_ARRAY_AGG': <class 'JSONArrayAgg'>, 'JSON_ARRAY_CONTAINS': <class 'JSONArrayContains'>, 'JSONB_EXTRACT': <class 'JSONBExtract'>, 'JSONB_EXTRACT_SCALAR': <class 'JSONBExtractScalar'>, 'JSON_EXTRACT': <class 'JSONExtract'>, 'JSON_EXTRACT_SCALAR': <class 'JSONExtractScalar'>, 'JSON_FORMAT': <class 'JSONFormat'>, 'J_S_O_N_OBJECT': <class 'JSONObject'>, 'J_S_O_N_OBJECT_AGG': <class 'JSONObjectAgg'>, 'J_S_O_N_TABLE': <class 'JSONTable'>, 'LAG': <class 'Lag'>, 'LAST': <class 'Last'>, 'LAST_DAY': <class 'LastDay'>, 'LAST_DAY_OF_MONTH': <class 'LastDay'>, 'LAST_VALUE': <class 'LastValue'>, 'LEAD': <class 'Lead'>, 'LEAST': <class 'Least'>, 'LEFT': <class 'Left'>, 'LENGTH': <class 'Length'>, 'LEN': <class 'Length'>, 'LEVENSHTEIN': <class 'Levenshtein'>, 'LN': <class 'Ln'>, 'LOG': <class 'Log'>, 'LOGICAL_AND': <class 'LogicalAnd'>, 'BOOL_AND': <class 'LogicalAnd'>, 'BOOLAND_AGG': <class 'LogicalAnd'>, 'LOGICAL_OR': <class 'LogicalOr'>, 'BOOL_OR': <class 'LogicalOr'>, 'BOOLOR_AGG': <class 'LogicalOr'>, 'LOWER': <class 'Lower'>, 'LCASE': <class 'Lower'>, 'MD5': <class 'MD5'>, 'MD5_DIGEST': <class 'MD5Digest'>, 'MAP': <class 'Map'>, 'MAP_FROM_ENTRIES': <class 'MapFromEntries'>, 'MATCH_AGAINST': <class 'MatchAgainst'>, 'MAX': <class 'Max'>, 'MIN': <class 'Min'>, 'MONTH': <class 'Month'>, 'MONTHS_BETWEEN': <class 'MonthsBetween'>, 'NEXT_VALUE_FOR': <class 'NextValueFor'>, 'NTH_VALUE': <class 'NthValue'>, 'NULLIF': <class 'Nullif'>, 'NUMBER_TO_STR': <class 'NumberToStr'>, 'NVL2': <class 'Nvl2'>, 'OPEN_J_S_O_N': <class 'OpenJSON'>, 'PARAMETERIZED_AGG': <class 'ParameterizedAgg'>, 'PARSE_JSON': <class 'ParseJSON'>, 'JSON_PARSE': <class 'ParseJSON'>, 'PERCENTILE_CONT': <class 'PercentileCont'>, 'PERCENTILE_DISC': <class 'PercentileDisc'>, 'POSEXPLODE': <class 'Posexplode'>, 'POSEXPLODE_OUTER': <class 'PosexplodeOuter'>, 'POWER': <class 'Pow'>, 'POW': <class 'Pow'>, 'PREDICT': <class 'Predict'>, 'QUANTILE': <class 'Quantile'>, 'QUARTER': <class 'Quarter'>, 'RAND': <class 'Rand'>, 'RANDOM': <class 'Rand'>, 'RANDN': <class 'Randn'>, 'RANGE_N': <class 'RangeN'>, 'READ_CSV': <class 'ReadCSV'>, 'REDUCE': <class 'Reduce'>, 'REGEXP_EXTRACT': <class 'RegexpExtract'>, 'REGEXP_I_LIKE': <class 'RegexpILike'>, 'REGEXP_LIKE': <class 'RegexpLike'>, 'REGEXP_REPLACE': <class 'RegexpReplace'>, 'REGEXP_SPLIT': <class 'RegexpSplit'>, 'REPEAT': <class 'Repeat'>, 'RIGHT': <class 'Right'>, 'ROUND': <class 'Round'>, 'ROW_NUMBER': <class 'RowNumber'>, 'SHA': <class 'SHA'>, 'SHA1': <class 'SHA'>, 'SHA2': <class 'SHA2'>, 'SAFE_DIVIDE': <class 'SafeDivide'>, 'SIGN': <class 'Sign'>, 'SIGNUM': <class 'Sign'>, 'SORT_ARRAY': <class 'SortArray'>, 'SPLIT': <class 'Split'>, 'SQRT': <class 'Sqrt'>, 'STANDARD_HASH': <class 'StandardHash'>, 'STAR_MAP': <class 'StarMap'>, 'STARTS_WITH': <class 'StartsWith'>, 'STARTSWITH': <class 'StartsWith'>, 'STDDEV': <class 'Stddev'>, 'STDDEV_POP': <class 'StddevPop'>, 'STDDEV_SAMP': <class 'StddevSamp'>, 'STR_POSITION': <class 'StrPosition'>, 'STR_TO_DATE': <class 'StrToDate'>, 'STR_TO_MAP': <class 'StrToMap'>, 'STR_TO_TIME': <class 'StrToTime'>, 'STR_TO_UNIX': <class 'StrToUnix'>, 'STRUCT': <class 'Struct'>, 'STRUCT_EXTRACT': <class 'StructExtract'>, 'STUFF': <class 'Stuff'>, 'INSERT': <class 'Stuff'>, 'SUBSTRING': <class 'Substring'>, 'SUM': <class 'Sum'>, 'TIME_ADD': <class 'TimeAdd'>, 'TIME_DIFF': <class 'TimeDiff'>, 'TIME_FROM_PARTS': <class 'TimeFromParts'>, 'TIMEFROMPARTS': <class 'TimeFromParts'>, 'TIME_STR_TO_DATE': <class 'TimeStrToDate'>, 'TIME_STR_TO_TIME': <class 'TimeStrToTime'>, 'TIME_STR_TO_UNIX': <class 'TimeStrToUnix'>, 'TIME_SUB': <class 'TimeSub'>, 'TIME_TO_STR': <class 'TimeToStr'>, 'TIME_TO_TIME_STR': <class 'TimeToTimeStr'>, 'TIME_TO_UNIX': <class 'TimeToUnix'>, 'TIME_TRUNC': <class 'TimeTrunc'>, 'TIMESTAMP': <class 'Timestamp'>, 'TIMESTAMP_ADD': <class 'TimestampAdd'>, 'TIMESTAMPDIFF': <class 'TimestampDiff'>, 'TIMESTAMP_DIFF': <class 'TimestampDiff'>, 'TIMESTAMP_FROM_PARTS': <class 'TimestampFromParts'>, 'TIMESTAMPFROMPARTS': <class 'TimestampFromParts'>, 'TIMESTAMP_SUB': <class 'TimestampSub'>, 'TIMESTAMP_TRUNC': <class 'TimestampTrunc'>, 'TO_ARRAY': <class 'ToArray'>, 'TO_BASE64': <class 'ToBase64'>, 'TO_CHAR': <class 'ToChar'>, 'TO_DAYS': <class 'ToDays'>, 'TO_MAP': <class 'ToMap'>, 'TO_NUMBER': <class 'ToNumber'>, 'TRANSFORM': <class 'Transform'>, 'TRIM': <class 'Trim'>, 'TRY': <class 'Try'>, 'TRY_CAST': <class 'TryCast'>, 'TS_OR_DI_TO_DI': <class 'TsOrDiToDi'>, 'TS_OR_DS_ADD': <class 'TsOrDsAdd'>, 'TS_OR_DS_DIFF': <class 'TsOrDsDiff'>, 'TS_OR_DS_TO_DATE': <class 'TsOrDsToDate'>, 'TS_OR_DS_TO_DATE_STR': <class 'TsOrDsToDateStr'>, 'TS_OR_DS_TO_TIME': <class 'TsOrDsToTime'>, 'TS_OR_DS_TO_TIMESTAMP': <class 'TsOrDsToTimestamp'>, 'UNHEX': <class 'Unhex'>, 'UNIX_DATE': <class 'UnixDate'>, 'UNIX_TO_STR': <class 'UnixToStr'>, 'UNIX_TO_TIME': <class 'UnixToTime'>, 'UNIX_TO_TIME_STR': <class 'UnixToTimeStr'>, 'UPPER': <class 'Upper'>, 'UCASE': <class 'Upper'>, 'VAR_MAP': <class 'VarMap'>, 'VARIANCE': <class 'Variance'>, 'VARIANCE_SAMP': <class 'Variance'>, 'VAR_SAMP': <class 'Variance'>, 'VARIANCE_POP': <class 'VariancePop'>, 'VAR_POP': <class 'VariancePop'>, 'WEEK': <class 'Week'>, 'WEEK_OF_YEAR': <class 'WeekOfYear'>, 'WEEKOFYEAR': <class 'WeekOfYear'>, 'WHEN': <class 'When'>, 'X_M_L_TABLE': <class 'XMLTable'>, 'XOR': <class 'Xor'>, 'YEAR': <class 'Year'>}
JSON_PATH_PARTS = [<class 'JSONPathFilter'>, <class 'JSONPathKey'>, <class 'JSONPathRecursive'>, <class 'JSONPathRoot'>, <class 'JSONPathScript'>, <class 'JSONPathSelector'>, <class 'JSONPathSlice'>, <class 'JSONPathSubscript'>, <class 'JSONPathUnion'>, <class 'JSONPathWildcard'>]
PERCENTILES = (<class 'PercentileCont'>, <class 'PercentileDisc'>)
def maybe_parse( sql_or_expression: Union[str, Expression], *, into: Union[str, Type[Expression], Collection[Union[str, Type[Expression]]], NoneType] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, prefix: Optional[str] = None, copy: bool = False, **opts) -> Expression:
5970def maybe_parse(
5971    sql_or_expression: ExpOrStr,
5972    *,
5973    into: t.Optional[IntoType] = None,
5974    dialect: DialectType = None,
5975    prefix: t.Optional[str] = None,
5976    copy: bool = False,
5977    **opts,
5978) -> Expression:
5979    """Gracefully handle a possible string or expression.
5980
5981    Example:
5982        >>> maybe_parse("1")
5983        Literal(this=1, is_string=False)
5984        >>> maybe_parse(to_identifier("x"))
5985        Identifier(this=x, quoted=False)
5986
5987    Args:
5988        sql_or_expression: the SQL code string or an expression
5989        into: the SQLGlot Expression to parse into
5990        dialect: the dialect used to parse the input expressions (in the case that an
5991            input expression is a SQL string).
5992        prefix: a string to prefix the sql with before it gets parsed
5993            (automatically includes a space)
5994        copy: whether to copy the expression.
5995        **opts: other options to use to parse the input expressions (again, in the case
5996            that an input expression is a SQL string).
5997
5998    Returns:
5999        Expression: the parsed or given expression.
6000    """
6001    if isinstance(sql_or_expression, Expression):
6002        if copy:
6003            return sql_or_expression.copy()
6004        return sql_or_expression
6005
6006    if sql_or_expression is None:
6007        raise ParseError("SQL cannot be None")
6008
6009    import sqlglot
6010
6011    sql = str(sql_or_expression)
6012    if prefix:
6013        sql = f"{prefix} {sql}"
6014
6015    return sqlglot.parse_one(sql, read=dialect, into=into, **opts)

Gracefully handle a possible string or expression.

Example:
>>> maybe_parse("1")
Literal(this=1, is_string=False)
>>> maybe_parse(to_identifier("x"))
Identifier(this=x, quoted=False)
Arguments:
  • sql_or_expression: the SQL code string or an expression
  • into: the SQLGlot Expression to parse into
  • dialect: the dialect used to parse the input expressions (in the case that an input expression is a SQL string).
  • prefix: a string to prefix the sql with before it gets parsed (automatically includes a space)
  • copy: whether to copy the expression.
  • **opts: other options to use to parse the input expressions (again, in the case that an input expression is a SQL string).
Returns:

Expression: the parsed or given expression.

def maybe_copy(instance, copy=True):
6026def maybe_copy(instance, copy=True):
6027    return instance.copy() if copy and instance else instance
def union( left: Union[str, Expression], right: Union[str, Expression], distinct: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Union:
6241def union(
6242    left: ExpOrStr,
6243    right: ExpOrStr,
6244    distinct: bool = True,
6245    dialect: DialectType = None,
6246    copy: bool = True,
6247    **opts,
6248) -> Union:
6249    """
6250    Initializes a syntax tree from one UNION expression.
6251
6252    Example:
6253        >>> union("SELECT * FROM foo", "SELECT * FROM bla").sql()
6254        'SELECT * FROM foo UNION SELECT * FROM bla'
6255
6256    Args:
6257        left: the SQL code string corresponding to the left-hand side.
6258            If an `Expression` instance is passed, it will be used as-is.
6259        right: the SQL code string corresponding to the right-hand side.
6260            If an `Expression` instance is passed, it will be used as-is.
6261        distinct: set the DISTINCT flag if and only if this is true.
6262        dialect: the dialect used to parse the input expression.
6263        copy: whether to copy the expression.
6264        opts: other options to use to parse the input expressions.
6265
6266    Returns:
6267        The new Union instance.
6268    """
6269    left = maybe_parse(sql_or_expression=left, dialect=dialect, copy=copy, **opts)
6270    right = maybe_parse(sql_or_expression=right, dialect=dialect, copy=copy, **opts)
6271
6272    return Union(this=left, expression=right, distinct=distinct)

Initializes a syntax tree from one UNION expression.

Example:
>>> union("SELECT * FROM foo", "SELECT * FROM bla").sql()
'SELECT * FROM foo UNION SELECT * FROM bla'
Arguments:
  • left: the SQL code string corresponding to the left-hand side. If an Expression instance is passed, it will be used as-is.
  • right: the SQL code string corresponding to the right-hand side. If an Expression instance is passed, it will be used as-is.
  • distinct: set the DISTINCT flag if and only if this is true.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy the expression.
  • opts: other options to use to parse the input expressions.
Returns:

The new Union instance.

def intersect( left: Union[str, Expression], right: Union[str, Expression], distinct: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Intersect:
6275def intersect(
6276    left: ExpOrStr,
6277    right: ExpOrStr,
6278    distinct: bool = True,
6279    dialect: DialectType = None,
6280    copy: bool = True,
6281    **opts,
6282) -> Intersect:
6283    """
6284    Initializes a syntax tree from one INTERSECT expression.
6285
6286    Example:
6287        >>> intersect("SELECT * FROM foo", "SELECT * FROM bla").sql()
6288        'SELECT * FROM foo INTERSECT SELECT * FROM bla'
6289
6290    Args:
6291        left: the SQL code string corresponding to the left-hand side.
6292            If an `Expression` instance is passed, it will be used as-is.
6293        right: the SQL code string corresponding to the right-hand side.
6294            If an `Expression` instance is passed, it will be used as-is.
6295        distinct: set the DISTINCT flag if and only if this is true.
6296        dialect: the dialect used to parse the input expression.
6297        copy: whether to copy the expression.
6298        opts: other options to use to parse the input expressions.
6299
6300    Returns:
6301        The new Intersect instance.
6302    """
6303    left = maybe_parse(sql_or_expression=left, dialect=dialect, copy=copy, **opts)
6304    right = maybe_parse(sql_or_expression=right, dialect=dialect, copy=copy, **opts)
6305
6306    return Intersect(this=left, expression=right, distinct=distinct)

Initializes a syntax tree from one INTERSECT expression.

Example:
>>> intersect("SELECT * FROM foo", "SELECT * FROM bla").sql()
'SELECT * FROM foo INTERSECT SELECT * FROM bla'
Arguments:
  • left: the SQL code string corresponding to the left-hand side. If an Expression instance is passed, it will be used as-is.
  • right: the SQL code string corresponding to the right-hand side. If an Expression instance is passed, it will be used as-is.
  • distinct: set the DISTINCT flag if and only if this is true.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy the expression.
  • opts: other options to use to parse the input expressions.
Returns:

The new Intersect instance.

def except_( left: Union[str, Expression], right: Union[str, Expression], distinct: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Except:
6309def except_(
6310    left: ExpOrStr,
6311    right: ExpOrStr,
6312    distinct: bool = True,
6313    dialect: DialectType = None,
6314    copy: bool = True,
6315    **opts,
6316) -> Except:
6317    """
6318    Initializes a syntax tree from one EXCEPT expression.
6319
6320    Example:
6321        >>> except_("SELECT * FROM foo", "SELECT * FROM bla").sql()
6322        'SELECT * FROM foo EXCEPT SELECT * FROM bla'
6323
6324    Args:
6325        left: the SQL code string corresponding to the left-hand side.
6326            If an `Expression` instance is passed, it will be used as-is.
6327        right: the SQL code string corresponding to the right-hand side.
6328            If an `Expression` instance is passed, it will be used as-is.
6329        distinct: set the DISTINCT flag if and only if this is true.
6330        dialect: the dialect used to parse the input expression.
6331        copy: whether to copy the expression.
6332        opts: other options to use to parse the input expressions.
6333
6334    Returns:
6335        The new Except instance.
6336    """
6337    left = maybe_parse(sql_or_expression=left, dialect=dialect, copy=copy, **opts)
6338    right = maybe_parse(sql_or_expression=right, dialect=dialect, copy=copy, **opts)
6339
6340    return Except(this=left, expression=right, distinct=distinct)

Initializes a syntax tree from one EXCEPT expression.

Example:
>>> except_("SELECT * FROM foo", "SELECT * FROM bla").sql()
'SELECT * FROM foo EXCEPT SELECT * FROM bla'
Arguments:
  • left: the SQL code string corresponding to the left-hand side. If an Expression instance is passed, it will be used as-is.
  • right: the SQL code string corresponding to the right-hand side. If an Expression instance is passed, it will be used as-is.
  • distinct: set the DISTINCT flag if and only if this is true.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy the expression.
  • opts: other options to use to parse the input expressions.
Returns:

The new Except instance.

def select( *expressions: Union[str, Expression], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> Select:
6343def select(*expressions: ExpOrStr, dialect: DialectType = None, **opts) -> Select:
6344    """
6345    Initializes a syntax tree from one or multiple SELECT expressions.
6346
6347    Example:
6348        >>> select("col1", "col2").from_("tbl").sql()
6349        'SELECT col1, col2 FROM tbl'
6350
6351    Args:
6352        *expressions: the SQL code string to parse as the expressions of a
6353            SELECT statement. If an Expression instance is passed, this is used as-is.
6354        dialect: the dialect used to parse the input expressions (in the case that an
6355            input expression is a SQL string).
6356        **opts: other options to use to parse the input expressions (again, in the case
6357            that an input expression is a SQL string).
6358
6359    Returns:
6360        Select: the syntax tree for the SELECT statement.
6361    """
6362    return Select().select(*expressions, dialect=dialect, **opts)

Initializes a syntax tree from one or multiple SELECT expressions.

Example:
>>> select("col1", "col2").from_("tbl").sql()
'SELECT col1, col2 FROM tbl'
Arguments:
  • *expressions: the SQL code string to parse as the expressions of a SELECT statement. If an Expression instance is passed, this is used as-is.
  • dialect: the dialect used to parse the input expressions (in the case that an input expression is a SQL string).
  • **opts: other options to use to parse the input expressions (again, in the case that an input expression is a SQL string).
Returns:

Select: the syntax tree for the SELECT statement.

def from_( expression: Union[str, Expression], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> Select:
6365def from_(expression: ExpOrStr, dialect: DialectType = None, **opts) -> Select:
6366    """
6367    Initializes a syntax tree from a FROM expression.
6368
6369    Example:
6370        >>> from_("tbl").select("col1", "col2").sql()
6371        'SELECT col1, col2 FROM tbl'
6372
6373    Args:
6374        *expression: the SQL code string to parse as the FROM expressions of a
6375            SELECT statement. If an Expression instance is passed, this is used as-is.
6376        dialect: the dialect used to parse the input expression (in the case that the
6377            input expression is a SQL string).
6378        **opts: other options to use to parse the input expressions (again, in the case
6379            that the input expression is a SQL string).
6380
6381    Returns:
6382        Select: the syntax tree for the SELECT statement.
6383    """
6384    return Select().from_(expression, dialect=dialect, **opts)

Initializes a syntax tree from a FROM expression.

Example:
>>> from_("tbl").select("col1", "col2").sql()
'SELECT col1, col2 FROM tbl'
Arguments:
  • *expression: the SQL code string to parse as the FROM expressions of a SELECT statement. If an Expression instance is passed, this is used as-is.
  • dialect: the dialect used to parse the input expression (in the case that the input expression is a SQL string).
  • **opts: other options to use to parse the input expressions (again, in the case that the input expression is a SQL string).
Returns:

Select: the syntax tree for the SELECT statement.

def update( table: str | Table, properties: dict, where: Union[str, Expression, NoneType] = None, from_: Union[str, Expression, NoneType] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> Update:
6387def update(
6388    table: str | Table,
6389    properties: dict,
6390    where: t.Optional[ExpOrStr] = None,
6391    from_: t.Optional[ExpOrStr] = None,
6392    dialect: DialectType = None,
6393    **opts,
6394) -> Update:
6395    """
6396    Creates an update statement.
6397
6398    Example:
6399        >>> update("my_table", {"x": 1, "y": "2", "z": None}, from_="baz", where="id > 1").sql()
6400        "UPDATE my_table SET x = 1, y = '2', z = NULL FROM baz WHERE id > 1"
6401
6402    Args:
6403        *properties: dictionary of properties to set which are
6404            auto converted to sql objects eg None -> NULL
6405        where: sql conditional parsed into a WHERE statement
6406        from_: sql statement parsed into a FROM statement
6407        dialect: the dialect used to parse the input expressions.
6408        **opts: other options to use to parse the input expressions.
6409
6410    Returns:
6411        Update: the syntax tree for the UPDATE statement.
6412    """
6413    update_expr = Update(this=maybe_parse(table, into=Table, dialect=dialect))
6414    update_expr.set(
6415        "expressions",
6416        [
6417            EQ(this=maybe_parse(k, dialect=dialect, **opts), expression=convert(v))
6418            for k, v in properties.items()
6419        ],
6420    )
6421    if from_:
6422        update_expr.set(
6423            "from",
6424            maybe_parse(from_, into=From, dialect=dialect, prefix="FROM", **opts),
6425        )
6426    if isinstance(where, Condition):
6427        where = Where(this=where)
6428    if where:
6429        update_expr.set(
6430            "where",
6431            maybe_parse(where, into=Where, dialect=dialect, prefix="WHERE", **opts),
6432        )
6433    return update_expr

Creates an update statement.

Example:
>>> update("my_table", {"x": 1, "y": "2", "z": None}, from_="baz", where="id > 1").sql()
"UPDATE my_table SET x = 1, y = '2', z = NULL FROM baz WHERE id > 1"
Arguments:
  • *properties: dictionary of properties to set which are auto converted to sql objects eg None -> NULL
  • where: sql conditional parsed into a WHERE statement
  • from_: sql statement parsed into a FROM statement
  • dialect: the dialect used to parse the input expressions.
  • **opts: other options to use to parse the input expressions.
Returns:

Update: the syntax tree for the UPDATE statement.

def delete( table: Union[str, Expression], where: Union[str, Expression, NoneType] = None, returning: Union[str, Expression, NoneType] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> Delete:
6436def delete(
6437    table: ExpOrStr,
6438    where: t.Optional[ExpOrStr] = None,
6439    returning: t.Optional[ExpOrStr] = None,
6440    dialect: DialectType = None,
6441    **opts,
6442) -> Delete:
6443    """
6444    Builds a delete statement.
6445
6446    Example:
6447        >>> delete("my_table", where="id > 1").sql()
6448        'DELETE FROM my_table WHERE id > 1'
6449
6450    Args:
6451        where: sql conditional parsed into a WHERE statement
6452        returning: sql conditional parsed into a RETURNING statement
6453        dialect: the dialect used to parse the input expressions.
6454        **opts: other options to use to parse the input expressions.
6455
6456    Returns:
6457        Delete: the syntax tree for the DELETE statement.
6458    """
6459    delete_expr = Delete().delete(table, dialect=dialect, copy=False, **opts)
6460    if where:
6461        delete_expr = delete_expr.where(where, dialect=dialect, copy=False, **opts)
6462    if returning:
6463        delete_expr = t.cast(
6464            Delete, delete_expr.returning(returning, dialect=dialect, copy=False, **opts)
6465        )
6466    return delete_expr

Builds a delete statement.

Example:
>>> delete("my_table", where="id > 1").sql()
'DELETE FROM my_table WHERE id > 1'
Arguments:
  • where: sql conditional parsed into a WHERE statement
  • returning: sql conditional parsed into a RETURNING statement
  • dialect: the dialect used to parse the input expressions.
  • **opts: other options to use to parse the input expressions.
Returns:

Delete: the syntax tree for the DELETE statement.

def insert( expression: Union[str, Expression], into: Union[str, Expression], columns: Optional[Sequence[str | Identifier]] = None, overwrite: Optional[bool] = None, returning: Union[str, Expression, NoneType] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Insert:
6469def insert(
6470    expression: ExpOrStr,
6471    into: ExpOrStr,
6472    columns: t.Optional[t.Sequence[str | Identifier]] = None,
6473    overwrite: t.Optional[bool] = None,
6474    returning: t.Optional[ExpOrStr] = None,
6475    dialect: DialectType = None,
6476    copy: bool = True,
6477    **opts,
6478) -> Insert:
6479    """
6480    Builds an INSERT statement.
6481
6482    Example:
6483        >>> insert("VALUES (1, 2, 3)", "tbl").sql()
6484        'INSERT INTO tbl VALUES (1, 2, 3)'
6485
6486    Args:
6487        expression: the sql string or expression of the INSERT statement
6488        into: the tbl to insert data to.
6489        columns: optionally the table's column names.
6490        overwrite: whether to INSERT OVERWRITE or not.
6491        returning: sql conditional parsed into a RETURNING statement
6492        dialect: the dialect used to parse the input expressions.
6493        copy: whether to copy the expression.
6494        **opts: other options to use to parse the input expressions.
6495
6496    Returns:
6497        Insert: the syntax tree for the INSERT statement.
6498    """
6499    expr = maybe_parse(expression, dialect=dialect, copy=copy, **opts)
6500    this: Table | Schema = maybe_parse(into, into=Table, dialect=dialect, copy=copy, **opts)
6501
6502    if columns:
6503        this = Schema(this=this, expressions=[to_identifier(c, copy=copy) for c in columns])
6504
6505    insert = Insert(this=this, expression=expr, overwrite=overwrite)
6506
6507    if returning:
6508        insert = t.cast(Insert, insert.returning(returning, dialect=dialect, copy=False, **opts))
6509
6510    return insert

Builds an INSERT statement.

Example:
>>> insert("VALUES (1, 2, 3)", "tbl").sql()
'INSERT INTO tbl VALUES (1, 2, 3)'
Arguments:
  • expression: the sql string or expression of the INSERT statement
  • into: the tbl to insert data to.
  • columns: optionally the table's column names.
  • overwrite: whether to INSERT OVERWRITE or not.
  • returning: sql conditional parsed into a RETURNING statement
  • dialect: the dialect used to parse the input expressions.
  • copy: whether to copy the expression.
  • **opts: other options to use to parse the input expressions.
Returns:

Insert: the syntax tree for the INSERT statement.

def condition( expression: Union[str, Expression], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Condition:
6513def condition(
6514    expression: ExpOrStr, dialect: DialectType = None, copy: bool = True, **opts
6515) -> Condition:
6516    """
6517    Initialize a logical condition expression.
6518
6519    Example:
6520        >>> condition("x=1").sql()
6521        'x = 1'
6522
6523        This is helpful for composing larger logical syntax trees:
6524        >>> where = condition("x=1")
6525        >>> where = where.and_("y=1")
6526        >>> Select().from_("tbl").select("*").where(where).sql()
6527        'SELECT * FROM tbl WHERE x = 1 AND y = 1'
6528
6529    Args:
6530        *expression: the SQL code string to parse.
6531            If an Expression instance is passed, this is used as-is.
6532        dialect: the dialect used to parse the input expression (in the case that the
6533            input expression is a SQL string).
6534        copy: Whether to copy `expression` (only applies to expressions).
6535        **opts: other options to use to parse the input expressions (again, in the case
6536            that the input expression is a SQL string).
6537
6538    Returns:
6539        The new Condition instance
6540    """
6541    return maybe_parse(
6542        expression,
6543        into=Condition,
6544        dialect=dialect,
6545        copy=copy,
6546        **opts,
6547    )

Initialize a logical condition expression.

Example:
>>> condition("x=1").sql()
'x = 1'

This is helpful for composing larger logical syntax trees:

>>> where = condition("x=1")
>>> where = where.and_("y=1")
>>> Select().from_("tbl").select("*").where(where).sql()
'SELECT * FROM tbl WHERE x = 1 AND y = 1'
Arguments:
  • *expression: the SQL code string to parse. If an Expression instance is passed, this is used as-is.
  • dialect: the dialect used to parse the input expression (in the case that the input expression is a SQL string).
  • copy: Whether to copy expression (only applies to expressions).
  • **opts: other options to use to parse the input expressions (again, in the case that the input expression is a SQL string).
Returns:

The new Condition instance

def and_( *expressions: Union[str, Expression, NoneType], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Condition:
6550def and_(
6551    *expressions: t.Optional[ExpOrStr], dialect: DialectType = None, copy: bool = True, **opts
6552) -> Condition:
6553    """
6554    Combine multiple conditions with an AND logical operator.
6555
6556    Example:
6557        >>> and_("x=1", and_("y=1", "z=1")).sql()
6558        'x = 1 AND (y = 1 AND z = 1)'
6559
6560    Args:
6561        *expressions: the SQL code strings to parse.
6562            If an Expression instance is passed, this is used as-is.
6563        dialect: the dialect used to parse the input expression.
6564        copy: whether to copy `expressions` (only applies to Expressions).
6565        **opts: other options to use to parse the input expressions.
6566
6567    Returns:
6568        The new condition
6569    """
6570    return t.cast(Condition, _combine(expressions, And, dialect, copy=copy, **opts))

Combine multiple conditions with an AND logical operator.

Example:
>>> and_("x=1", and_("y=1", "z=1")).sql()
'x = 1 AND (y = 1 AND z = 1)'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, this is used as-is.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy expressions (only applies to Expressions).
  • **opts: other options to use to parse the input expressions.
Returns:

The new condition

def or_( *expressions: Union[str, Expression, NoneType], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Condition:
6573def or_(
6574    *expressions: t.Optional[ExpOrStr], dialect: DialectType = None, copy: bool = True, **opts
6575) -> Condition:
6576    """
6577    Combine multiple conditions with an OR logical operator.
6578
6579    Example:
6580        >>> or_("x=1", or_("y=1", "z=1")).sql()
6581        'x = 1 OR (y = 1 OR z = 1)'
6582
6583    Args:
6584        *expressions: the SQL code strings to parse.
6585            If an Expression instance is passed, this is used as-is.
6586        dialect: the dialect used to parse the input expression.
6587        copy: whether to copy `expressions` (only applies to Expressions).
6588        **opts: other options to use to parse the input expressions.
6589
6590    Returns:
6591        The new condition
6592    """
6593    return t.cast(Condition, _combine(expressions, Or, dialect, copy=copy, **opts))

Combine multiple conditions with an OR logical operator.

Example:
>>> or_("x=1", or_("y=1", "z=1")).sql()
'x = 1 OR (y = 1 OR z = 1)'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, this is used as-is.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy expressions (only applies to Expressions).
  • **opts: other options to use to parse the input expressions.
Returns:

The new condition

def xor( *expressions: Union[str, Expression, NoneType], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Condition:
6596def xor(
6597    *expressions: t.Optional[ExpOrStr], dialect: DialectType = None, copy: bool = True, **opts
6598) -> Condition:
6599    """
6600    Combine multiple conditions with an XOR logical operator.
6601
6602    Example:
6603        >>> xor("x=1", xor("y=1", "z=1")).sql()
6604        'x = 1 XOR (y = 1 XOR z = 1)'
6605
6606    Args:
6607        *expressions: the SQL code strings to parse.
6608            If an Expression instance is passed, this is used as-is.
6609        dialect: the dialect used to parse the input expression.
6610        copy: whether to copy `expressions` (only applies to Expressions).
6611        **opts: other options to use to parse the input expressions.
6612
6613    Returns:
6614        The new condition
6615    """
6616    return t.cast(Condition, _combine(expressions, Xor, dialect, copy=copy, **opts))

Combine multiple conditions with an XOR logical operator.

Example:
>>> xor("x=1", xor("y=1", "z=1")).sql()
'x = 1 XOR (y = 1 XOR z = 1)'
Arguments:
  • *expressions: the SQL code strings to parse. If an Expression instance is passed, this is used as-is.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy expressions (only applies to Expressions).
  • **opts: other options to use to parse the input expressions.
Returns:

The new condition

def not_( expression: Union[str, Expression], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts) -> Not:
6619def not_(expression: ExpOrStr, dialect: DialectType = None, copy: bool = True, **opts) -> Not:
6620    """
6621    Wrap a condition with a NOT operator.
6622
6623    Example:
6624        >>> not_("this_suit='black'").sql()
6625        "NOT this_suit = 'black'"
6626
6627    Args:
6628        expression: the SQL code string to parse.
6629            If an Expression instance is passed, this is used as-is.
6630        dialect: the dialect used to parse the input expression.
6631        copy: whether to copy the expression or not.
6632        **opts: other options to use to parse the input expressions.
6633
6634    Returns:
6635        The new condition.
6636    """
6637    this = condition(
6638        expression,
6639        dialect=dialect,
6640        copy=copy,
6641        **opts,
6642    )
6643    return Not(this=_wrap(this, Connector))

Wrap a condition with a NOT operator.

Example:
>>> not_("this_suit='black'").sql()
"NOT this_suit = 'black'"
Arguments:
  • expression: the SQL code string to parse. If an Expression instance is passed, this is used as-is.
  • dialect: the dialect used to parse the input expression.
  • copy: whether to copy the expression or not.
  • **opts: other options to use to parse the input expressions.
Returns:

The new condition.

def paren( expression: Union[str, Expression], copy: bool = True) -> Paren:
6646def paren(expression: ExpOrStr, copy: bool = True) -> Paren:
6647    """
6648    Wrap an expression in parentheses.
6649
6650    Example:
6651        >>> paren("5 + 3").sql()
6652        '(5 + 3)'
6653
6654    Args:
6655        expression: the SQL code string to parse.
6656            If an Expression instance is passed, this is used as-is.
6657        copy: whether to copy the expression or not.
6658
6659    Returns:
6660        The wrapped expression.
6661    """
6662    return Paren(this=maybe_parse(expression, copy=copy))

Wrap an expression in parentheses.

Example:
>>> paren("5 + 3").sql()
'(5 + 3)'
Arguments:
  • expression: the SQL code string to parse. If an Expression instance is passed, this is used as-is.
  • copy: whether to copy the expression or not.
Returns:

The wrapped expression.

SAFE_IDENTIFIER_RE: Pattern[str] = re.compile('^[_a-zA-Z][\\w]*$')
def to_identifier(name, quoted=None, copy=True):
6678def to_identifier(name, quoted=None, copy=True):
6679    """Builds an identifier.
6680
6681    Args:
6682        name: The name to turn into an identifier.
6683        quoted: Whether to force quote the identifier.
6684        copy: Whether to copy name if it's an Identifier.
6685
6686    Returns:
6687        The identifier ast node.
6688    """
6689
6690    if name is None:
6691        return None
6692
6693    if isinstance(name, Identifier):
6694        identifier = maybe_copy(name, copy)
6695    elif isinstance(name, str):
6696        identifier = Identifier(
6697            this=name,
6698            quoted=not SAFE_IDENTIFIER_RE.match(name) if quoted is None else quoted,
6699        )
6700    else:
6701        raise ValueError(f"Name needs to be a string or an Identifier, got: {name.__class__}")
6702    return identifier

Builds an identifier.

Arguments:
  • name: The name to turn into an identifier.
  • quoted: Whether to force quote the identifier.
  • copy: Whether to copy name if it's an Identifier.
Returns:

The identifier ast node.

def parse_identifier( name: str | Identifier, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None) -> Identifier:
6705def parse_identifier(name: str | Identifier, dialect: DialectType = None) -> Identifier:
6706    """
6707    Parses a given string into an identifier.
6708
6709    Args:
6710        name: The name to parse into an identifier.
6711        dialect: The dialect to parse against.
6712
6713    Returns:
6714        The identifier ast node.
6715    """
6716    try:
6717        expression = maybe_parse(name, dialect=dialect, into=Identifier)
6718    except ParseError:
6719        expression = to_identifier(name)
6720
6721    return expression

Parses a given string into an identifier.

Arguments:
  • name: The name to parse into an identifier.
  • dialect: The dialect to parse against.
Returns:

The identifier ast node.

INTERVAL_STRING_RE = re.compile('\\s*([0-9]+)\\s*([a-zA-Z]+)\\s*')
def to_interval( interval: str | Literal) -> Interval:
6727def to_interval(interval: str | Literal) -> Interval:
6728    """Builds an interval expression from a string like '1 day' or '5 months'."""
6729    if isinstance(interval, Literal):
6730        if not interval.is_string:
6731            raise ValueError("Invalid interval string.")
6732
6733        interval = interval.this
6734
6735    interval_parts = INTERVAL_STRING_RE.match(interval)  # type: ignore
6736
6737    if not interval_parts:
6738        raise ValueError("Invalid interval string.")
6739
6740    return Interval(
6741        this=Literal.string(interval_parts.group(1)),
6742        unit=Var(this=interval_parts.group(2).upper()),
6743    )

Builds an interval expression from a string like '1 day' or '5 months'.

def to_table( sql_path: str | Table, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **kwargs) -> Table:
6746def to_table(
6747    sql_path: str | Table, dialect: DialectType = None, copy: bool = True, **kwargs
6748) -> Table:
6749    """
6750    Create a table expression from a `[catalog].[schema].[table]` sql path. Catalog and schema are optional.
6751    If a table is passed in then that table is returned.
6752
6753    Args:
6754        sql_path: a `[catalog].[schema].[table]` string.
6755        dialect: the source dialect according to which the table name will be parsed.
6756        copy: Whether to copy a table if it is passed in.
6757        kwargs: the kwargs to instantiate the resulting `Table` expression with.
6758
6759    Returns:
6760        A table expression.
6761    """
6762    if isinstance(sql_path, Table):
6763        return maybe_copy(sql_path, copy=copy)
6764
6765    table = maybe_parse(sql_path, into=Table, dialect=dialect)
6766
6767    for k, v in kwargs.items():
6768        table.set(k, v)
6769
6770    return table

Create a table expression from a [catalog].[schema].[table] sql path. Catalog and schema are optional. If a table is passed in then that table is returned.

Arguments:
  • sql_path: a [catalog].[schema].[table] string.
  • dialect: the source dialect according to which the table name will be parsed.
  • copy: Whether to copy a table if it is passed in.
  • kwargs: the kwargs to instantiate the resulting Table expression with.
Returns:

A table expression.

def to_column( sql_path: str | Column, quoted: Optional[bool] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **kwargs) -> Column:
6773def to_column(
6774    sql_path: str | Column,
6775    quoted: t.Optional[bool] = None,
6776    dialect: DialectType = None,
6777    copy: bool = True,
6778    **kwargs,
6779) -> Column:
6780    """
6781    Create a column from a `[table].[column]` sql path. Table is optional.
6782    If a column is passed in then that column is returned.
6783
6784    Args:
6785        sql_path: a `[table].[column]` string.
6786        quoted: Whether or not to force quote identifiers.
6787        dialect: the source dialect according to which the column name will be parsed.
6788        copy: Whether to copy a column if it is passed in.
6789        kwargs: the kwargs to instantiate the resulting `Column` expression with.
6790
6791    Returns:
6792        A column expression.
6793    """
6794    if isinstance(sql_path, Column):
6795        return maybe_copy(sql_path, copy=copy)
6796
6797    try:
6798        col = maybe_parse(sql_path, into=Column, dialect=dialect)
6799    except ParseError:
6800        return column(*reversed(sql_path.split(".")), quoted=quoted, **kwargs)
6801
6802    for k, v in kwargs.items():
6803        col.set(k, v)
6804
6805    if quoted:
6806        for i in col.find_all(Identifier):
6807            i.set("quoted", True)
6808
6809    return col

Create a column from a [table].[column] sql path. Table is optional. If a column is passed in then that column is returned.

Arguments:
  • sql_path: a [table].[column] string.
  • quoted: Whether or not to force quote identifiers.
  • dialect: the source dialect according to which the column name will be parsed.
  • copy: Whether to copy a column if it is passed in.
  • kwargs: the kwargs to instantiate the resulting Column expression with.
Returns:

A column expression.

def alias_( expression: Union[str, Expression], alias: Union[Identifier, str, NoneType], table: Union[bool, Sequence[str | Identifier]] = False, quoted: Optional[bool] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True, **opts):
6812def alias_(
6813    expression: ExpOrStr,
6814    alias: t.Optional[str | Identifier],
6815    table: bool | t.Sequence[str | Identifier] = False,
6816    quoted: t.Optional[bool] = None,
6817    dialect: DialectType = None,
6818    copy: bool = True,
6819    **opts,
6820):
6821    """Create an Alias expression.
6822
6823    Example:
6824        >>> alias_('foo', 'bar').sql()
6825        'foo AS bar'
6826
6827        >>> alias_('(select 1, 2)', 'bar', table=['a', 'b']).sql()
6828        '(SELECT 1, 2) AS bar(a, b)'
6829
6830    Args:
6831        expression: the SQL code strings to parse.
6832            If an Expression instance is passed, this is used as-is.
6833        alias: the alias name to use. If the name has
6834            special characters it is quoted.
6835        table: Whether to create a table alias, can also be a list of columns.
6836        quoted: whether to quote the alias
6837        dialect: the dialect used to parse the input expression.
6838        copy: Whether to copy the expression.
6839        **opts: other options to use to parse the input expressions.
6840
6841    Returns:
6842        Alias: the aliased expression
6843    """
6844    exp = maybe_parse(expression, dialect=dialect, copy=copy, **opts)
6845    alias = to_identifier(alias, quoted=quoted)
6846
6847    if table:
6848        table_alias = TableAlias(this=alias)
6849        exp.set("alias", table_alias)
6850
6851        if not isinstance(table, bool):
6852            for column in table:
6853                table_alias.append("columns", to_identifier(column, quoted=quoted))
6854
6855        return exp
6856
6857    # We don't set the "alias" arg for Window expressions, because that would add an IDENTIFIER node in
6858    # the AST, representing a "named_window" [1] construct (eg. bigquery). What we want is an ALIAS node
6859    # for the complete Window expression.
6860    #
6861    # [1]: https://cloud.google.com/bigquery/docs/reference/standard-sql/window-function-calls
6862
6863    if "alias" in exp.arg_types and not isinstance(exp, Window):
6864        exp.set("alias", alias)
6865        return exp
6866    return Alias(this=exp, alias=alias)

Create an Alias expression.

Example:
>>> alias_('foo', 'bar').sql()
'foo AS bar'
>>> alias_('(select 1, 2)', 'bar', table=['a', 'b']).sql()
'(SELECT 1, 2) AS bar(a, b)'
Arguments:
  • expression: the SQL code strings to parse. If an Expression instance is passed, this is used as-is.
  • alias: the alias name to use. If the name has special characters it is quoted.
  • table: Whether to create a table alias, can also be a list of columns.
  • quoted: whether to quote the alias
  • dialect: the dialect used to parse the input expression.
  • copy: Whether to copy the expression.
  • **opts: other options to use to parse the input expressions.
Returns:

Alias: the aliased expression

def subquery( expression: Union[str, Expression], alias: Union[Identifier, str, NoneType] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **opts) -> Select:
6869def subquery(
6870    expression: ExpOrStr,
6871    alias: t.Optional[Identifier | str] = None,
6872    dialect: DialectType = None,
6873    **opts,
6874) -> Select:
6875    """
6876    Build a subquery expression that's selected from.
6877
6878    Example:
6879        >>> subquery('select x from tbl', 'bar').select('x').sql()
6880        'SELECT x FROM (SELECT x FROM tbl) AS bar'
6881
6882    Args:
6883        expression: the SQL code strings to parse.
6884            If an Expression instance is passed, this is used as-is.
6885        alias: the alias name to use.
6886        dialect: the dialect used to parse the input expression.
6887        **opts: other options to use to parse the input expressions.
6888
6889    Returns:
6890        A new Select instance with the subquery expression included.
6891    """
6892
6893    expression = maybe_parse(expression, dialect=dialect, **opts).subquery(alias, **opts)
6894    return Select().from_(expression, dialect=dialect, **opts)

Build a subquery expression that's selected from.

Example:
>>> subquery('select x from tbl', 'bar').select('x').sql()
'SELECT x FROM (SELECT x FROM tbl) AS bar'
Arguments:
  • expression: the SQL code strings to parse. If an Expression instance is passed, this is used as-is.
  • alias: the alias name to use.
  • dialect: the dialect used to parse the input expression.
  • **opts: other options to use to parse the input expressions.
Returns:

A new Select instance with the subquery expression included.

def column( col, table=None, db=None, catalog=None, *, fields=None, quoted=None, copy=True):
6925def column(
6926    col,
6927    table=None,
6928    db=None,
6929    catalog=None,
6930    *,
6931    fields=None,
6932    quoted=None,
6933    copy=True,
6934):
6935    """
6936    Build a Column.
6937
6938    Args:
6939        col: Column name.
6940        table: Table name.
6941        db: Database name.
6942        catalog: Catalog name.
6943        fields: Additional fields using dots.
6944        quoted: Whether to force quotes on the column's identifiers.
6945        copy: Whether to copy identifiers if passed in.
6946
6947    Returns:
6948        The new Column instance.
6949    """
6950    this = Column(
6951        this=to_identifier(col, quoted=quoted, copy=copy),
6952        table=to_identifier(table, quoted=quoted, copy=copy),
6953        db=to_identifier(db, quoted=quoted, copy=copy),
6954        catalog=to_identifier(catalog, quoted=quoted, copy=copy),
6955    )
6956
6957    if fields:
6958        this = Dot.build(
6959            (this, *(to_identifier(field, quoted=quoted, copy=copy) for field in fields))
6960        )
6961    return this

Build a Column.

Arguments:
  • col: Column name.
  • table: Table name.
  • db: Database name.
  • catalog: Catalog name.
  • fields: Additional fields using dots.
  • quoted: Whether to force quotes on the column's identifiers.
  • copy: Whether to copy identifiers if passed in.
Returns:

The new Column instance.

def cast( expression: Union[str, Expression], to: Union[str, DataType, DataType.Type], copy: bool = True, **opts) -> Cast:
6964def cast(expression: ExpOrStr, to: DATA_TYPE, copy: bool = True, **opts) -> Cast:
6965    """Cast an expression to a data type.
6966
6967    Example:
6968        >>> cast('x + 1', 'int').sql()
6969        'CAST(x + 1 AS INT)'
6970
6971    Args:
6972        expression: The expression to cast.
6973        to: The datatype to cast to.
6974        copy: Whether to copy the supplied expressions.
6975
6976    Returns:
6977        The new Cast instance.
6978    """
6979    expr = maybe_parse(expression, copy=copy, **opts)
6980    data_type = DataType.build(to, copy=copy, **opts)
6981
6982    if expr.is_type(data_type):
6983        return expr
6984
6985    expr = Cast(this=expr, to=data_type)
6986    expr.type = data_type
6987
6988    return expr

Cast an expression to a data type.

Example:
>>> cast('x + 1', 'int').sql()
'CAST(x + 1 AS INT)'
Arguments:
  • expression: The expression to cast.
  • to: The datatype to cast to.
  • copy: Whether to copy the supplied expressions.
Returns:

The new Cast instance.

def table_( table: Identifier | str, db: Union[Identifier, str, NoneType] = None, catalog: Union[Identifier, str, NoneType] = None, quoted: Optional[bool] = None, alias: Union[Identifier, str, NoneType] = None) -> Table:
6991def table_(
6992    table: Identifier | str,
6993    db: t.Optional[Identifier | str] = None,
6994    catalog: t.Optional[Identifier | str] = None,
6995    quoted: t.Optional[bool] = None,
6996    alias: t.Optional[Identifier | str] = None,
6997) -> Table:
6998    """Build a Table.
6999
7000    Args:
7001        table: Table name.
7002        db: Database name.
7003        catalog: Catalog name.
7004        quote: Whether to force quotes on the table's identifiers.
7005        alias: Table's alias.
7006
7007    Returns:
7008        The new Table instance.
7009    """
7010    return Table(
7011        this=to_identifier(table, quoted=quoted) if table else None,
7012        db=to_identifier(db, quoted=quoted) if db else None,
7013        catalog=to_identifier(catalog, quoted=quoted) if catalog else None,
7014        alias=TableAlias(this=to_identifier(alias)) if alias else None,
7015    )

Build a Table.

Arguments:
  • table: Table name.
  • db: Database name.
  • catalog: Catalog name.
  • quote: Whether to force quotes on the table's identifiers.
  • alias: Table's alias.
Returns:

The new Table instance.

def values( values: Iterable[Tuple[Any, ...]], alias: Optional[str] = None, columns: Union[Iterable[str], Dict[str, DataType], NoneType] = None) -> Values:
7018def values(
7019    values: t.Iterable[t.Tuple[t.Any, ...]],
7020    alias: t.Optional[str] = None,
7021    columns: t.Optional[t.Iterable[str] | t.Dict[str, DataType]] = None,
7022) -> Values:
7023    """Build VALUES statement.
7024
7025    Example:
7026        >>> values([(1, '2')]).sql()
7027        "VALUES (1, '2')"
7028
7029    Args:
7030        values: values statements that will be converted to SQL
7031        alias: optional alias
7032        columns: Optional list of ordered column names or ordered dictionary of column names to types.
7033         If either are provided then an alias is also required.
7034
7035    Returns:
7036        Values: the Values expression object
7037    """
7038    if columns and not alias:
7039        raise ValueError("Alias is required when providing columns")
7040
7041    return Values(
7042        expressions=[convert(tup) for tup in values],
7043        alias=(
7044            TableAlias(this=to_identifier(alias), columns=[to_identifier(x) for x in columns])
7045            if columns
7046            else (TableAlias(this=to_identifier(alias)) if alias else None)
7047        ),
7048    )

Build VALUES statement.

Example:
>>> values([(1, '2')]).sql()
"VALUES (1, '2')"
Arguments:
  • values: values statements that will be converted to SQL
  • alias: optional alias
  • columns: Optional list of ordered column names or ordered dictionary of column names to types. If either are provided then an alias is also required.
Returns:

Values: the Values expression object

def var( name: Union[str, Expression, NoneType]) -> Var:
7051def var(name: t.Optional[ExpOrStr]) -> Var:
7052    """Build a SQL variable.
7053
7054    Example:
7055        >>> repr(var('x'))
7056        'Var(this=x)'
7057
7058        >>> repr(var(column('x', table='y')))
7059        'Var(this=x)'
7060
7061    Args:
7062        name: The name of the var or an expression who's name will become the var.
7063
7064    Returns:
7065        The new variable node.
7066    """
7067    if not name:
7068        raise ValueError("Cannot convert empty name into var.")
7069
7070    if isinstance(name, Expression):
7071        name = name.name
7072    return Var(this=name)

Build a SQL variable.

Example:
>>> repr(var('x'))
'Var(this=x)'
>>> repr(var(column('x', table='y')))
'Var(this=x)'
Arguments:
  • name: The name of the var or an expression who's name will become the var.
Returns:

The new variable node.

def rename_table( old_name: str | Table, new_name: str | Table, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None) -> AlterTable:
7075def rename_table(
7076    old_name: str | Table,
7077    new_name: str | Table,
7078    dialect: DialectType = None,
7079) -> AlterTable:
7080    """Build ALTER TABLE... RENAME... expression
7081
7082    Args:
7083        old_name: The old name of the table
7084        new_name: The new name of the table
7085        dialect: The dialect to parse the table.
7086
7087    Returns:
7088        Alter table expression
7089    """
7090    old_table = to_table(old_name, dialect=dialect)
7091    new_table = to_table(new_name, dialect=dialect)
7092    return AlterTable(
7093        this=old_table,
7094        actions=[
7095            RenameTable(this=new_table),
7096        ],
7097    )

Build ALTER TABLE... RENAME... expression

Arguments:
  • old_name: The old name of the table
  • new_name: The new name of the table
  • dialect: The dialect to parse the table.
Returns:

Alter table expression

def rename_column( table_name: str | Table, old_column_name: str | Column, new_column_name: str | Column, exists: Optional[bool] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None) -> AlterTable:
7100def rename_column(
7101    table_name: str | Table,
7102    old_column_name: str | Column,
7103    new_column_name: str | Column,
7104    exists: t.Optional[bool] = None,
7105    dialect: DialectType = None,
7106) -> AlterTable:
7107    """Build ALTER TABLE... RENAME COLUMN... expression
7108
7109    Args:
7110        table_name: Name of the table
7111        old_column: The old name of the column
7112        new_column: The new name of the column
7113        exists: Whether to add the `IF EXISTS` clause
7114        dialect: The dialect to parse the table/column.
7115
7116    Returns:
7117        Alter table expression
7118    """
7119    table = to_table(table_name, dialect=dialect)
7120    old_column = to_column(old_column_name, dialect=dialect)
7121    new_column = to_column(new_column_name, dialect=dialect)
7122    return AlterTable(
7123        this=table,
7124        actions=[
7125            RenameColumn(this=old_column, to=new_column, exists=exists),
7126        ],
7127    )

Build ALTER TABLE... RENAME COLUMN... expression

Arguments:
  • table_name: Name of the table
  • old_column: The old name of the column
  • new_column: The new name of the column
  • exists: Whether to add the IF EXISTS clause
  • dialect: The dialect to parse the table/column.
Returns:

Alter table expression

def convert(value: Any, copy: bool = False) -> Expression:
7130def convert(value: t.Any, copy: bool = False) -> Expression:
7131    """Convert a python value into an expression object.
7132
7133    Raises an error if a conversion is not possible.
7134
7135    Args:
7136        value: A python object.
7137        copy: Whether to copy `value` (only applies to Expressions and collections).
7138
7139    Returns:
7140        The equivalent expression object.
7141    """
7142    if isinstance(value, Expression):
7143        return maybe_copy(value, copy)
7144    if isinstance(value, str):
7145        return Literal.string(value)
7146    if isinstance(value, bool):
7147        return Boolean(this=value)
7148    if value is None or (isinstance(value, float) and math.isnan(value)):
7149        return null()
7150    if isinstance(value, numbers.Number):
7151        return Literal.number(value)
7152    if isinstance(value, bytes):
7153        return HexString(this=value.hex())
7154    if isinstance(value, datetime.datetime):
7155        datetime_literal = Literal.string(
7156            (value if value.tzinfo else value.replace(tzinfo=datetime.timezone.utc)).isoformat(
7157                sep=" "
7158            )
7159        )
7160        return TimeStrToTime(this=datetime_literal)
7161    if isinstance(value, datetime.date):
7162        date_literal = Literal.string(value.strftime("%Y-%m-%d"))
7163        return DateStrToDate(this=date_literal)
7164    if isinstance(value, tuple):
7165        if hasattr(value, "_fields"):
7166            return Struct(
7167                expressions=[
7168                    PropertyEQ(
7169                        this=to_identifier(k), expression=convert(getattr(value, k), copy=copy)
7170                    )
7171                    for k in value._fields
7172                ]
7173            )
7174        return Tuple(expressions=[convert(v, copy=copy) for v in value])
7175    if isinstance(value, list):
7176        return Array(expressions=[convert(v, copy=copy) for v in value])
7177    if isinstance(value, dict):
7178        return Map(
7179            keys=Array(expressions=[convert(k, copy=copy) for k in value]),
7180            values=Array(expressions=[convert(v, copy=copy) for v in value.values()]),
7181        )
7182    if hasattr(value, "__dict__"):
7183        return Struct(
7184            expressions=[
7185                PropertyEQ(this=to_identifier(k), expression=convert(v, copy=copy))
7186                for k, v in value.__dict__.items()
7187            ]
7188        )
7189    raise ValueError(f"Cannot convert {value}")

Convert a python value into an expression object.

Raises an error if a conversion is not possible.

Arguments:
  • value: A python object.
  • copy: Whether to copy value (only applies to Expressions and collections).
Returns:

The equivalent expression object.

def replace_children( expression: Expression, fun: Callable, *args, **kwargs) -> None:
7192def replace_children(expression: Expression, fun: t.Callable, *args, **kwargs) -> None:
7193    """
7194    Replace children of an expression with the result of a lambda fun(child) -> exp.
7195    """
7196    for k, v in tuple(expression.args.items()):
7197        is_list_arg = type(v) is list
7198
7199        child_nodes = v if is_list_arg else [v]
7200        new_child_nodes = []
7201
7202        for cn in child_nodes:
7203            if isinstance(cn, Expression):
7204                for child_node in ensure_collection(fun(cn, *args, **kwargs)):
7205                    new_child_nodes.append(child_node)
7206            else:
7207                new_child_nodes.append(cn)
7208
7209        expression.set(k, new_child_nodes if is_list_arg else seq_get(new_child_nodes, 0))

Replace children of an expression with the result of a lambda fun(child) -> exp.

def replace_tree( expression: Expression, fun: Callable, prune: Optional[Callable[[Expression], bool]] = None) -> Expression:
7212def replace_tree(
7213    expression: Expression,
7214    fun: t.Callable,
7215    prune: t.Optional[t.Callable[[Expression], bool]] = None,
7216) -> Expression:
7217    """
7218    Replace an entire tree with the result of function calls on each node.
7219
7220    This will be traversed in reverse dfs, so leaves first.
7221    If new nodes are created as a result of function calls, they will also be traversed.
7222    """
7223    stack = list(expression.dfs(prune=prune))
7224
7225    while stack:
7226        node = stack.pop()
7227        new_node = fun(node)
7228
7229        if new_node is not node:
7230            node.replace(new_node)
7231
7232            if isinstance(new_node, Expression):
7233                stack.append(new_node)
7234
7235    return new_node

Replace an entire tree with the result of function calls on each node.

This will be traversed in reverse dfs, so leaves first. If new nodes are created as a result of function calls, they will also be traversed.

def column_table_names( expression: Expression, exclude: str = '') -> Set[str]:
7238def column_table_names(expression: Expression, exclude: str = "") -> t.Set[str]:
7239    """
7240    Return all table names referenced through columns in an expression.
7241
7242    Example:
7243        >>> import sqlglot
7244        >>> sorted(column_table_names(sqlglot.parse_one("a.b AND c.d AND c.e")))
7245        ['a', 'c']
7246
7247    Args:
7248        expression: expression to find table names.
7249        exclude: a table name to exclude
7250
7251    Returns:
7252        A list of unique names.
7253    """
7254    return {
7255        table
7256        for table in (column.table for column in expression.find_all(Column))
7257        if table and table != exclude
7258    }

Return all table names referenced through columns in an expression.

Example:
>>> import sqlglot
>>> sorted(column_table_names(sqlglot.parse_one("a.b AND c.d AND c.e")))
['a', 'c']
Arguments:
  • expression: expression to find table names.
  • exclude: a table name to exclude
Returns:

A list of unique names.

def table_name( table: Table | str, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, identify: bool = False) -> str:
7261def table_name(table: Table | str, dialect: DialectType = None, identify: bool = False) -> str:
7262    """Get the full name of a table as a string.
7263
7264    Args:
7265        table: Table expression node or string.
7266        dialect: The dialect to generate the table name for.
7267        identify: Determines when an identifier should be quoted. Possible values are:
7268            False (default): Never quote, except in cases where it's mandatory by the dialect.
7269            True: Always quote.
7270
7271    Examples:
7272        >>> from sqlglot import exp, parse_one
7273        >>> table_name(parse_one("select * from a.b.c").find(exp.Table))
7274        'a.b.c'
7275
7276    Returns:
7277        The table name.
7278    """
7279
7280    table = maybe_parse(table, into=Table, dialect=dialect)
7281
7282    if not table:
7283        raise ValueError(f"Cannot parse {table}")
7284
7285    return ".".join(
7286        (
7287            part.sql(dialect=dialect, identify=True, copy=False)
7288            if identify or not SAFE_IDENTIFIER_RE.match(part.name)
7289            else part.name
7290        )
7291        for part in table.parts
7292    )

Get the full name of a table as a string.

Arguments:
  • table: Table expression node or string.
  • dialect: The dialect to generate the table name for.
  • identify: Determines when an identifier should be quoted. Possible values are: False (default): Never quote, except in cases where it's mandatory by the dialect. True: Always quote.
Examples:
>>> from sqlglot import exp, parse_one
>>> table_name(parse_one("select * from a.b.c").find(exp.Table))
'a.b.c'
Returns:

The table name.

def normalize_table_name( table: str | Table, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True) -> str:
7295def normalize_table_name(table: str | Table, dialect: DialectType = None, copy: bool = True) -> str:
7296    """Returns a case normalized table name without quotes.
7297
7298    Args:
7299        table: the table to normalize
7300        dialect: the dialect to use for normalization rules
7301        copy: whether to copy the expression.
7302
7303    Examples:
7304        >>> normalize_table_name("`A-B`.c", dialect="bigquery")
7305        'A-B.c'
7306    """
7307    from sqlglot.optimizer.normalize_identifiers import normalize_identifiers
7308
7309    return ".".join(
7310        p.name
7311        for p in normalize_identifiers(
7312            to_table(table, dialect=dialect, copy=copy), dialect=dialect
7313        ).parts
7314    )

Returns a case normalized table name without quotes.

Arguments:
  • table: the table to normalize
  • dialect: the dialect to use for normalization rules
  • copy: whether to copy the expression.
Examples:
>>> normalize_table_name("`A-B`.c", dialect="bigquery")
'A-B.c'
def replace_tables( expression: ~E, mapping: Dict[str, str], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True) -> ~E:
7317def replace_tables(
7318    expression: E, mapping: t.Dict[str, str], dialect: DialectType = None, copy: bool = True
7319) -> E:
7320    """Replace all tables in expression according to the mapping.
7321
7322    Args:
7323        expression: expression node to be transformed and replaced.
7324        mapping: mapping of table names.
7325        dialect: the dialect of the mapping table
7326        copy: whether to copy the expression.
7327
7328    Examples:
7329        >>> from sqlglot import exp, parse_one
7330        >>> replace_tables(parse_one("select * from a.b"), {"a.b": "c"}).sql()
7331        'SELECT * FROM c /* a.b */'
7332
7333    Returns:
7334        The mapped expression.
7335    """
7336
7337    mapping = {normalize_table_name(k, dialect=dialect): v for k, v in mapping.items()}
7338
7339    def _replace_tables(node: Expression) -> Expression:
7340        if isinstance(node, Table):
7341            original = normalize_table_name(node, dialect=dialect)
7342            new_name = mapping.get(original)
7343
7344            if new_name:
7345                table = to_table(
7346                    new_name,
7347                    **{k: v for k, v in node.args.items() if k not in TABLE_PARTS},
7348                    dialect=dialect,
7349                )
7350                table.add_comments([original])
7351                return table
7352        return node
7353
7354    return expression.transform(_replace_tables, copy=copy)  # type: ignore

Replace all tables in expression according to the mapping.

Arguments:
  • expression: expression node to be transformed and replaced.
  • mapping: mapping of table names.
  • dialect: the dialect of the mapping table
  • copy: whether to copy the expression.
Examples:
>>> from sqlglot import exp, parse_one
>>> replace_tables(parse_one("select * from a.b"), {"a.b": "c"}).sql()
'SELECT * FROM c /* a.b */'
Returns:

The mapped expression.

def replace_placeholders( expression: Expression, *args, **kwargs) -> Expression:
7357def replace_placeholders(expression: Expression, *args, **kwargs) -> Expression:
7358    """Replace placeholders in an expression.
7359
7360    Args:
7361        expression: expression node to be transformed and replaced.
7362        args: positional names that will substitute unnamed placeholders in the given order.
7363        kwargs: keyword arguments that will substitute named placeholders.
7364
7365    Examples:
7366        >>> from sqlglot import exp, parse_one
7367        >>> replace_placeholders(
7368        ...     parse_one("select * from :tbl where ? = ?"),
7369        ...     exp.to_identifier("str_col"), "b", tbl=exp.to_identifier("foo")
7370        ... ).sql()
7371        "SELECT * FROM foo WHERE str_col = 'b'"
7372
7373    Returns:
7374        The mapped expression.
7375    """
7376
7377    def _replace_placeholders(node: Expression, args, **kwargs) -> Expression:
7378        if isinstance(node, Placeholder):
7379            if node.this:
7380                new_name = kwargs.get(node.this)
7381                if new_name is not None:
7382                    return convert(new_name)
7383            else:
7384                try:
7385                    return convert(next(args))
7386                except StopIteration:
7387                    pass
7388        return node
7389
7390    return expression.transform(_replace_placeholders, iter(args), **kwargs)

Replace placeholders in an expression.

Arguments:
  • expression: expression node to be transformed and replaced.
  • args: positional names that will substitute unnamed placeholders in the given order.
  • kwargs: keyword arguments that will substitute named placeholders.
Examples:
>>> from sqlglot import exp, parse_one
>>> replace_placeholders(
...     parse_one("select * from :tbl where ? = ?"),
...     exp.to_identifier("str_col"), "b", tbl=exp.to_identifier("foo")
... ).sql()
"SELECT * FROM foo WHERE str_col = 'b'"
Returns:

The mapped expression.

def expand( expression: Expression, sources: Dict[str, Query], dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, copy: bool = True) -> Expression:
7393def expand(
7394    expression: Expression,
7395    sources: t.Dict[str, Query],
7396    dialect: DialectType = None,
7397    copy: bool = True,
7398) -> Expression:
7399    """Transforms an expression by expanding all referenced sources into subqueries.
7400
7401    Examples:
7402        >>> from sqlglot import parse_one
7403        >>> expand(parse_one("select * from x AS z"), {"x": parse_one("select * from y")}).sql()
7404        'SELECT * FROM (SELECT * FROM y) AS z /* source: x */'
7405
7406        >>> expand(parse_one("select * from x AS z"), {"x": parse_one("select * from y"), "y": parse_one("select * from z")}).sql()
7407        'SELECT * FROM (SELECT * FROM (SELECT * FROM z) AS y /* source: y */) AS z /* source: x */'
7408
7409    Args:
7410        expression: The expression to expand.
7411        sources: A dictionary of name to Queries.
7412        dialect: The dialect of the sources dict.
7413        copy: Whether to copy the expression during transformation. Defaults to True.
7414
7415    Returns:
7416        The transformed expression.
7417    """
7418    sources = {normalize_table_name(k, dialect=dialect): v for k, v in sources.items()}
7419
7420    def _expand(node: Expression):
7421        if isinstance(node, Table):
7422            name = normalize_table_name(node, dialect=dialect)
7423            source = sources.get(name)
7424            if source:
7425                subquery = source.subquery(node.alias or name)
7426                subquery.comments = [f"source: {name}"]
7427                return subquery.transform(_expand, copy=False)
7428        return node
7429
7430    return expression.transform(_expand, copy=copy)

Transforms an expression by expanding all referenced sources into subqueries.

Examples:
>>> from sqlglot import parse_one
>>> expand(parse_one("select * from x AS z"), {"x": parse_one("select * from y")}).sql()
'SELECT * FROM (SELECT * FROM y) AS z /* source: x */'
>>> expand(parse_one("select * from x AS z"), {"x": parse_one("select * from y"), "y": parse_one("select * from z")}).sql()
'SELECT * FROM (SELECT * FROM (SELECT * FROM z) AS y /* source: y */) AS z /* source: x */'
Arguments:
  • expression: The expression to expand.
  • sources: A dictionary of name to Queries.
  • dialect: The dialect of the sources dict.
  • copy: Whether to copy the expression during transformation. Defaults to True.
Returns:

The transformed expression.

def func( name: str, *args, copy: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **kwargs) -> Func:
7433def func(name: str, *args, copy: bool = True, dialect: DialectType = None, **kwargs) -> Func:
7434    """
7435    Returns a Func expression.
7436
7437    Examples:
7438        >>> func("abs", 5).sql()
7439        'ABS(5)'
7440
7441        >>> func("cast", this=5, to=DataType.build("DOUBLE")).sql()
7442        'CAST(5 AS DOUBLE)'
7443
7444    Args:
7445        name: the name of the function to build.
7446        args: the args used to instantiate the function of interest.
7447        copy: whether to copy the argument expressions.
7448        dialect: the source dialect.
7449        kwargs: the kwargs used to instantiate the function of interest.
7450
7451    Note:
7452        The arguments `args` and `kwargs` are mutually exclusive.
7453
7454    Returns:
7455        An instance of the function of interest, or an anonymous function, if `name` doesn't
7456        correspond to an existing `sqlglot.expressions.Func` class.
7457    """
7458    if args and kwargs:
7459        raise ValueError("Can't use both args and kwargs to instantiate a function.")
7460
7461    from sqlglot.dialects.dialect import Dialect
7462
7463    dialect = Dialect.get_or_raise(dialect)
7464
7465    converted: t.List[Expression] = [maybe_parse(arg, dialect=dialect, copy=copy) for arg in args]
7466    kwargs = {key: maybe_parse(value, dialect=dialect, copy=copy) for key, value in kwargs.items()}
7467
7468    constructor = dialect.parser_class.FUNCTIONS.get(name.upper())
7469    if constructor:
7470        if converted:
7471            if "dialect" in constructor.__code__.co_varnames:
7472                function = constructor(converted, dialect=dialect)
7473            else:
7474                function = constructor(converted)
7475        elif constructor.__name__ == "from_arg_list":
7476            function = constructor.__self__(**kwargs)  # type: ignore
7477        else:
7478            constructor = FUNCTION_BY_NAME.get(name.upper())
7479            if constructor:
7480                function = constructor(**kwargs)
7481            else:
7482                raise ValueError(
7483                    f"Unable to convert '{name}' into a Func. Either manually construct "
7484                    "the Func expression of interest or parse the function call."
7485                )
7486    else:
7487        kwargs = kwargs or {"expressions": converted}
7488        function = Anonymous(this=name, **kwargs)
7489
7490    for error_message in function.error_messages(converted):
7491        raise ValueError(error_message)
7492
7493    return function

Returns a Func expression.

Examples:
>>> func("abs", 5).sql()
'ABS(5)'
>>> func("cast", this=5, to=DataType.build("DOUBLE")).sql()
'CAST(5 AS DOUBLE)'
Arguments:
  • name: the name of the function to build.
  • args: the args used to instantiate the function of interest.
  • copy: whether to copy the argument expressions.
  • dialect: the source dialect.
  • kwargs: the kwargs used to instantiate the function of interest.
Note:

The arguments args and kwargs are mutually exclusive.

Returns:

An instance of the function of interest, or an anonymous function, if name doesn't correspond to an existing Func class.

def case( expression: Union[str, Expression, NoneType] = None, **opts) -> Case:
7496def case(
7497    expression: t.Optional[ExpOrStr] = None,
7498    **opts,
7499) -> Case:
7500    """
7501    Initialize a CASE statement.
7502
7503    Example:
7504        case().when("a = 1", "foo").else_("bar")
7505
7506    Args:
7507        expression: Optionally, the input expression (not all dialects support this)
7508        **opts: Extra keyword arguments for parsing `expression`
7509    """
7510    if expression is not None:
7511        this = maybe_parse(expression, **opts)
7512    else:
7513        this = None
7514    return Case(this=this, ifs=[])

Initialize a CASE statement.

Example:

case().when("a = 1", "foo").else_("bar")

Arguments:
  • expression: Optionally, the input expression (not all dialects support this)
  • **opts: Extra keyword arguments for parsing expression
def array( *expressions: Union[str, Expression], copy: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **kwargs) -> Array:
7517def array(
7518    *expressions: ExpOrStr, copy: bool = True, dialect: DialectType = None, **kwargs
7519) -> Array:
7520    """
7521    Returns an array.
7522
7523    Examples:
7524        >>> array(1, 'x').sql()
7525        'ARRAY(1, x)'
7526
7527    Args:
7528        expressions: the expressions to add to the array.
7529        copy: whether to copy the argument expressions.
7530        dialect: the source dialect.
7531        kwargs: the kwargs used to instantiate the function of interest.
7532
7533    Returns:
7534        An array expression.
7535    """
7536    return Array(
7537        expressions=[
7538            maybe_parse(expression, copy=copy, dialect=dialect, **kwargs)
7539            for expression in expressions
7540        ]
7541    )

Returns an array.

Examples:
>>> array(1, 'x').sql()
'ARRAY(1, x)'
Arguments:
  • expressions: the expressions to add to the array.
  • copy: whether to copy the argument expressions.
  • dialect: the source dialect.
  • kwargs: the kwargs used to instantiate the function of interest.
Returns:

An array expression.

def tuple_( *expressions: Union[str, Expression], copy: bool = True, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, **kwargs) -> Tuple:
7544def tuple_(
7545    *expressions: ExpOrStr, copy: bool = True, dialect: DialectType = None, **kwargs
7546) -> Tuple:
7547    """
7548    Returns an tuple.
7549
7550    Examples:
7551        >>> tuple_(1, 'x').sql()
7552        '(1, x)'
7553
7554    Args:
7555        expressions: the expressions to add to the tuple.
7556        copy: whether to copy the argument expressions.
7557        dialect: the source dialect.
7558        kwargs: the kwargs used to instantiate the function of interest.
7559
7560    Returns:
7561        A tuple expression.
7562    """
7563    return Tuple(
7564        expressions=[
7565            maybe_parse(expression, copy=copy, dialect=dialect, **kwargs)
7566            for expression in expressions
7567        ]
7568    )

Returns an tuple.

Examples:
>>> tuple_(1, 'x').sql()
'(1, x)'
Arguments:
  • expressions: the expressions to add to the tuple.
  • copy: whether to copy the argument expressions.
  • dialect: the source dialect.
  • kwargs: the kwargs used to instantiate the function of interest.
Returns:

A tuple expression.

def true() -> Boolean:
7571def true() -> Boolean:
7572    """
7573    Returns a true Boolean expression.
7574    """
7575    return Boolean(this=True)

Returns a true Boolean expression.

def false() -> Boolean:
7578def false() -> Boolean:
7579    """
7580    Returns a false Boolean expression.
7581    """
7582    return Boolean(this=False)

Returns a false Boolean expression.

def null() -> Null:
7585def null() -> Null:
7586    """
7587    Returns a Null expression.
7588    """
7589    return Null()

Returns a Null expression.

NONNULL_CONSTANTS = (<class 'Literal'>, <class 'Boolean'>)
CONSTANTS = (<class 'Literal'>, <class 'Boolean'>, <class 'Null'>)