Edit on GitHub

sqlglot.optimizer.optimizer

 1from __future__ import annotations
 2
 3import typing as t
 4
 5import sqlglot
 6from sqlglot import Schema, exp
 7from sqlglot.dialects.dialect import DialectType
 8from sqlglot.optimizer.annotate_types import annotate_types
 9from sqlglot.optimizer.canonicalize import canonicalize
10from sqlglot.optimizer.eliminate_ctes import eliminate_ctes
11from sqlglot.optimizer.eliminate_joins import eliminate_joins
12from sqlglot.optimizer.eliminate_subqueries import eliminate_subqueries
13from sqlglot.optimizer.merge_subqueries import merge_subqueries
14from sqlglot.optimizer.normalize import normalize
15from sqlglot.optimizer.optimize_joins import optimize_joins
16from sqlglot.optimizer.pushdown_predicates import pushdown_predicates
17from sqlglot.optimizer.pushdown_projections import pushdown_projections
18from sqlglot.optimizer.qualify import qualify
19from sqlglot.optimizer.qualify_columns import quote_identifiers
20from sqlglot.optimizer.simplify import simplify
21from sqlglot.optimizer.unnest_subqueries import unnest_subqueries
22from sqlglot.schema import ensure_schema
23
24RULES = (
25    qualify,
26    pushdown_projections,
27    normalize,
28    unnest_subqueries,
29    pushdown_predicates,
30    optimize_joins,
31    eliminate_subqueries,
32    merge_subqueries,
33    eliminate_joins,
34    eliminate_ctes,
35    quote_identifiers,
36    annotate_types,
37    canonicalize,
38    simplify,
39)
40
41
42def optimize(
43    expression: str | exp.Expression,
44    schema: t.Optional[dict | Schema] = None,
45    db: t.Optional[str] = None,
46    catalog: t.Optional[str] = None,
47    dialect: DialectType = None,
48    rules: t.Sequence[t.Callable] = RULES,
49    **kwargs,
50) -> exp.Expression:
51    """
52    Rewrite a sqlglot AST into an optimized form.
53
54    Args:
55        expression: expression to optimize
56        schema: database schema.
57            This can either be an instance of `sqlglot.optimizer.Schema` or a mapping in one of
58            the following forms:
59                1. {table: {col: type}}
60                2. {db: {table: {col: type}}}
61                3. {catalog: {db: {table: {col: type}}}}
62            If no schema is provided then the default schema defined at `sqlgot.schema` will be used
63        db: specify the default database, as might be set by a `USE DATABASE db` statement
64        catalog: specify the default catalog, as might be set by a `USE CATALOG c` statement
65        dialect: The dialect to parse the sql string.
66        rules: sequence of optimizer rules to use.
67            Many of the rules require tables and columns to be qualified.
68            Do not remove `qualify` from the sequence of rules unless you know what you're doing!
69        **kwargs: If a rule has a keyword argument with a same name in **kwargs, it will be passed in.
70
71    Returns:
72        The optimized expression.
73    """
74    schema = ensure_schema(schema or sqlglot.schema, dialect=dialect)
75    possible_kwargs = {
76        "db": db,
77        "catalog": catalog,
78        "schema": schema,
79        "dialect": dialect,
80        "isolate_tables": True,  # needed for other optimizations to perform well
81        "quote_identifiers": False,
82        **kwargs,
83    }
84
85    expression = exp.maybe_parse(expression, dialect=dialect, copy=True)
86    for rule in rules:
87        # Find any additional rule parameters, beyond `expression`
88        rule_params = rule.__code__.co_varnames
89        rule_kwargs = {
90            param: possible_kwargs[param] for param in rule_params if param in possible_kwargs
91        }
92        expression = rule(expression, **rule_kwargs)
93
94    return t.cast(exp.Expression, expression)
def optimize( expression: str | sqlglot.expressions.Expression, schema: Union[dict, sqlglot.schema.Schema, NoneType] = None, db: Optional[str] = None, catalog: Optional[str] = None, dialect: Union[str, sqlglot.dialects.dialect.Dialect, Type[sqlglot.dialects.dialect.Dialect], NoneType] = None, rules: Sequence[Callable] = (<function qualify at 0x7f73bfcf3c70>, <function pushdown_projections at 0x7f73bfcf3640>, <function normalize at 0x7f73bfcdb6d0>, <function unnest_subqueries at 0x7f73bfa9c040>, <function pushdown_predicates at 0x7f73bfcf24d0>, <function optimize_joins at 0x7f73bfcf2200>, <function eliminate_subqueries at 0x7f73bfcf1360>, <function merge_subqueries at 0x7f73bfcf13f0>, <function eliminate_joins at 0x7f73bfcdb5b0>, <function eliminate_ctes at 0x7f73bfcdb490>, <function quote_identifiers at 0x7f73bfcf35b0>, <function annotate_types at 0x7f73bfd47910>, <function canonicalize at 0x7f73bfcdaef0>, <function simplify at 0x7f73bfcdb880>), **kwargs) -> sqlglot.expressions.Expression:
43def optimize(
44    expression: str | exp.Expression,
45    schema: t.Optional[dict | Schema] = None,
46    db: t.Optional[str] = None,
47    catalog: t.Optional[str] = None,
48    dialect: DialectType = None,
49    rules: t.Sequence[t.Callable] = RULES,
50    **kwargs,
51) -> exp.Expression:
52    """
53    Rewrite a sqlglot AST into an optimized form.
54
55    Args:
56        expression: expression to optimize
57        schema: database schema.
58            This can either be an instance of `sqlglot.optimizer.Schema` or a mapping in one of
59            the following forms:
60                1. {table: {col: type}}
61                2. {db: {table: {col: type}}}
62                3. {catalog: {db: {table: {col: type}}}}
63            If no schema is provided then the default schema defined at `sqlgot.schema` will be used
64        db: specify the default database, as might be set by a `USE DATABASE db` statement
65        catalog: specify the default catalog, as might be set by a `USE CATALOG c` statement
66        dialect: The dialect to parse the sql string.
67        rules: sequence of optimizer rules to use.
68            Many of the rules require tables and columns to be qualified.
69            Do not remove `qualify` from the sequence of rules unless you know what you're doing!
70        **kwargs: If a rule has a keyword argument with a same name in **kwargs, it will be passed in.
71
72    Returns:
73        The optimized expression.
74    """
75    schema = ensure_schema(schema or sqlglot.schema, dialect=dialect)
76    possible_kwargs = {
77        "db": db,
78        "catalog": catalog,
79        "schema": schema,
80        "dialect": dialect,
81        "isolate_tables": True,  # needed for other optimizations to perform well
82        "quote_identifiers": False,
83        **kwargs,
84    }
85
86    expression = exp.maybe_parse(expression, dialect=dialect, copy=True)
87    for rule in rules:
88        # Find any additional rule parameters, beyond `expression`
89        rule_params = rule.__code__.co_varnames
90        rule_kwargs = {
91            param: possible_kwargs[param] for param in rule_params if param in possible_kwargs
92        }
93        expression = rule(expression, **rule_kwargs)
94
95    return t.cast(exp.Expression, expression)

Rewrite a sqlglot AST into an optimized form.

Arguments:
  • expression: expression to optimize
  • schema: database schema. This can either be an instance of sqlglot.optimizer.Schema or a mapping in one of the following forms: 1. {table: {col: type}} 2. {db: {table: {col: type}}} 3. {catalog: {db: {table: {col: type}}}} If no schema is provided then the default schema defined at sqlgot.schema will be used
  • db: specify the default database, as might be set by a USE DATABASE db statement
  • catalog: specify the default catalog, as might be set by a USE CATALOG c statement
  • dialect: The dialect to parse the sql string.
  • rules: sequence of optimizer rules to use. Many of the rules require tables and columns to be qualified. Do not remove qualify from the sequence of rules unless you know what you're doing!
  • *kwargs: If a rule has a keyword argument with a same name in *kwargs, it will be passed in.
Returns:

The optimized expression.