sqlmesh 0.210.1.dev1__py3-none-any.whl → 0.210.1.dev3__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
sqlmesh/_version.py CHANGED
@@ -28,7 +28,7 @@ version_tuple: VERSION_TUPLE
28
28
  commit_id: COMMIT_ID
29
29
  __commit_id__: COMMIT_ID
30
30
 
31
- __version__ = version = '0.210.1.dev1'
32
- __version_tuple__ = version_tuple = (0, 210, 1, 'dev1')
31
+ __version__ = version = '0.210.1.dev3'
32
+ __version_tuple__ = version_tuple = (0, 210, 1, 'dev3')
33
33
 
34
34
  __commit_id__ = commit_id = None
@@ -100,6 +100,7 @@ class ConnectionConfig(abc.ABC, BaseConfig):
100
100
  register_comments: bool
101
101
  pre_ping: bool
102
102
  pretty_sql: bool = False
103
+ schema_differ_overrides: t.Optional[t.Dict[str, t.Any]] = None
103
104
 
104
105
  # Whether to share a single connection across threads or create a new connection per thread.
105
106
  shared_connection: t.ClassVar[bool] = False
@@ -174,6 +175,7 @@ class ConnectionConfig(abc.ABC, BaseConfig):
174
175
  pre_ping=self.pre_ping,
175
176
  pretty_sql=self.pretty_sql,
176
177
  shared_connection=self.shared_connection,
178
+ schema_differ_overrides=self.schema_differ_overrides,
177
179
  **self._extra_engine_config,
178
180
  )
179
181
 
@@ -39,7 +39,7 @@ class AthenaEngineAdapter(PandasNativeFetchDFSupportMixin, RowDiffMixin):
39
39
  # CTAS, Views: No comment support at all
40
40
  COMMENT_CREATION_TABLE = CommentCreationTable.UNSUPPORTED
41
41
  COMMENT_CREATION_VIEW = CommentCreationView.UNSUPPORTED
42
- SCHEMA_DIFFER = TrinoEngineAdapter.SCHEMA_DIFFER
42
+ SCHEMA_DIFFER_KWARGS = TrinoEngineAdapter.SCHEMA_DIFFER_KWARGS
43
43
  MAX_TIMESTAMP_PRECISION = 3 # copied from Trino
44
44
  # Athena does not deal with comments well, e.g:
45
45
  # >>> self._execute('/* test */ DESCRIBE foo')
@@ -14,7 +14,7 @@ import itertools
14
14
  import logging
15
15
  import sys
16
16
  import typing as t
17
- from functools import partial
17
+ from functools import cached_property, partial
18
18
 
19
19
  from sqlglot import Dialect, exp
20
20
  from sqlglot.errors import ErrorLevel
@@ -109,7 +109,7 @@ class EngineAdapter:
109
109
  SUPPORTS_MANAGED_MODELS = False
110
110
  SUPPORTS_CREATE_DROP_CATALOG = False
111
111
  SUPPORTED_DROP_CASCADE_OBJECT_KINDS: t.List[str] = []
112
- SCHEMA_DIFFER = SchemaDiffer()
112
+ SCHEMA_DIFFER_KWARGS: t.Dict[str, t.Any] = {}
113
113
  SUPPORTS_TUPLE_IN = True
114
114
  HAS_VIEW_BINDING = False
115
115
  SUPPORTS_REPLACE_TABLE = True
@@ -132,6 +132,7 @@ class EngineAdapter:
132
132
  pretty_sql: bool = False,
133
133
  shared_connection: bool = False,
134
134
  correlation_id: t.Optional[CorrelationId] = None,
135
+ schema_differ_overrides: t.Optional[t.Dict[str, t.Any]] = None,
135
136
  **kwargs: t.Any,
136
137
  ):
137
138
  self.dialect = dialect.lower() or self.DIALECT
@@ -154,6 +155,7 @@ class EngineAdapter:
154
155
  self._pretty_sql = pretty_sql
155
156
  self._multithreaded = multithreaded
156
157
  self.correlation_id = correlation_id
158
+ self._schema_differ_overrides = schema_differ_overrides
157
159
 
158
160
  def with_settings(self, **kwargs: t.Any) -> EngineAdapter:
159
161
  extra_kwargs = {
@@ -204,6 +206,15 @@ class EngineAdapter:
204
206
  def catalog_support(self) -> CatalogSupport:
205
207
  return CatalogSupport.UNSUPPORTED
206
208
 
209
+ @cached_property
210
+ def schema_differ(self) -> SchemaDiffer:
211
+ return SchemaDiffer(
212
+ **{
213
+ **self.SCHEMA_DIFFER_KWARGS,
214
+ **(self._schema_differ_overrides or {}),
215
+ }
216
+ )
217
+
207
218
  @classmethod
208
219
  def _casted_columns(
209
220
  cls,
@@ -1101,7 +1112,7 @@ class EngineAdapter:
1101
1112
  """
1102
1113
  return t.cast(
1103
1114
  t.List[TableAlterOperation],
1104
- self.SCHEMA_DIFFER.compare_columns(
1115
+ self.schema_differ.compare_columns(
1105
1116
  current_table_name,
1106
1117
  self.columns(current_table_name),
1107
1118
  self.columns(target_table_name),
@@ -22,7 +22,7 @@ from sqlmesh.core.engine_adapter.shared import (
22
22
  set_catalog,
23
23
  )
24
24
  from sqlmesh.core.node import IntervalUnit
25
- from sqlmesh.core.schema_diff import SchemaDiffer, TableAlterOperation
25
+ from sqlmesh.core.schema_diff import TableAlterOperation, NestedSupport
26
26
  from sqlmesh.utils import optional_import, get_source_columns_to_types
27
27
  from sqlmesh.utils.date import to_datetime
28
28
  from sqlmesh.utils.errors import SQLMeshError
@@ -68,8 +68,8 @@ class BigQueryEngineAdapter(InsertOverwriteWithMergeMixin, ClusteredByMixin, Row
68
68
  MAX_COLUMN_COMMENT_LENGTH = 1024
69
69
  SUPPORTED_DROP_CASCADE_OBJECT_KINDS = ["SCHEMA"]
70
70
 
71
- SCHEMA_DIFFER = SchemaDiffer(
72
- compatible_types={
71
+ SCHEMA_DIFFER_KWARGS = {
72
+ "compatible_types": {
73
73
  exp.DataType.build("INT64", dialect=DIALECT): {
74
74
  exp.DataType.build("NUMERIC", dialect=DIALECT),
75
75
  exp.DataType.build("FLOAT64", dialect=DIALECT),
@@ -83,17 +83,17 @@ class BigQueryEngineAdapter(InsertOverwriteWithMergeMixin, ClusteredByMixin, Row
83
83
  exp.DataType.build("DATETIME", dialect=DIALECT),
84
84
  },
85
85
  },
86
- coerceable_types={
86
+ "coerceable_types": {
87
87
  exp.DataType.build("FLOAT64", dialect=DIALECT): {
88
88
  exp.DataType.build("BIGNUMERIC", dialect=DIALECT),
89
89
  },
90
90
  },
91
- support_coercing_compatible_types=True,
92
- parameterized_type_defaults={
91
+ "support_coercing_compatible_types": True,
92
+ "parameterized_type_defaults": {
93
93
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(38, 9), (0,)],
94
94
  exp.DataType.build("BIGDECIMAL", dialect=DIALECT).this: [(76.76, 38), (0,)],
95
95
  },
96
- types_with_unlimited_length={
96
+ "types_with_unlimited_length": {
97
97
  # parameterized `STRING(n)` can ALTER to unparameterized `STRING`
98
98
  exp.DataType.build("STRING", dialect=DIALECT).this: {
99
99
  exp.DataType.build("STRING", dialect=DIALECT).this,
@@ -103,9 +103,8 @@ class BigQueryEngineAdapter(InsertOverwriteWithMergeMixin, ClusteredByMixin, Row
103
103
  exp.DataType.build("BYTES", dialect=DIALECT).this,
104
104
  },
105
105
  },
106
- support_nested_operations=True,
107
- support_nested_drop=False,
108
- )
106
+ "nested_support": NestedSupport.ALL_BUT_DROP,
107
+ }
109
108
 
110
109
  @property
111
110
  def client(self) -> BigQueryClient:
@@ -15,7 +15,7 @@ from sqlmesh.core.engine_adapter.shared import (
15
15
  CommentCreationView,
16
16
  InsertOverwriteStrategy,
17
17
  )
18
- from sqlmesh.core.schema_diff import SchemaDiffer, TableAlterOperation
18
+ from sqlmesh.core.schema_diff import TableAlterOperation
19
19
  from sqlmesh.utils import get_source_columns_to_types
20
20
 
21
21
  if t.TYPE_CHECKING:
@@ -37,7 +37,7 @@ class ClickhouseEngineAdapter(EngineAdapterWithIndexSupport, LogicalMergeMixin):
37
37
  SUPPORTS_REPLACE_TABLE = False
38
38
  COMMENT_CREATION_VIEW = CommentCreationView.COMMENT_COMMAND_ONLY
39
39
 
40
- SCHEMA_DIFFER = SchemaDiffer()
40
+ SCHEMA_DIFFER_KWARGS = {}
41
41
 
42
42
  DEFAULT_TABLE_ENGINE = "MergeTree"
43
43
  ORDER_BY_TABLE_ENGINE_REGEX = "^.*?MergeTree.*$"
@@ -15,7 +15,7 @@ from sqlmesh.core.engine_adapter.shared import (
15
15
  )
16
16
  from sqlmesh.core.engine_adapter.spark import SparkEngineAdapter
17
17
  from sqlmesh.core.node import IntervalUnit
18
- from sqlmesh.core.schema_diff import SchemaDiffer
18
+ from sqlmesh.core.schema_diff import NestedSupport
19
19
  from sqlmesh.engines.spark.db_api.spark_session import connection, SparkSessionConnection
20
20
  from sqlmesh.utils.errors import SQLMeshError, MissingDefaultCatalogError
21
21
 
@@ -34,15 +34,14 @@ class DatabricksEngineAdapter(SparkEngineAdapter):
34
34
  SUPPORTS_CLONING = True
35
35
  SUPPORTS_MATERIALIZED_VIEWS = True
36
36
  SUPPORTS_MATERIALIZED_VIEW_SCHEMA = True
37
- SCHEMA_DIFFER = SchemaDiffer(
38
- support_positional_add=True,
39
- support_nested_operations=True,
40
- support_nested_drop=True,
41
- array_element_selector="element",
42
- parameterized_type_defaults={
37
+ SCHEMA_DIFFER_KWARGS = {
38
+ "support_positional_add": True,
39
+ "nested_support": NestedSupport.ALL,
40
+ "array_element_selector": "element",
41
+ "parameterized_type_defaults": {
43
42
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(10, 0), (0,)],
44
43
  },
45
- )
44
+ }
46
45
 
47
46
  def __init__(self, *args: t.Any, **kwargs: t.Any) -> None:
48
47
  super().__init__(*args, **kwargs)
@@ -18,7 +18,6 @@ from sqlmesh.core.engine_adapter.shared import (
18
18
  SourceQuery,
19
19
  set_catalog,
20
20
  )
21
- from sqlmesh.core.schema_diff import SchemaDiffer
22
21
 
23
22
  if t.TYPE_CHECKING:
24
23
  from sqlmesh.core._typing import SchemaName, TableName
@@ -29,11 +28,11 @@ if t.TYPE_CHECKING:
29
28
  class DuckDBEngineAdapter(LogicalMergeMixin, GetCurrentCatalogFromFunctionMixin, RowDiffMixin):
30
29
  DIALECT = "duckdb"
31
30
  SUPPORTS_TRANSACTIONS = False
32
- SCHEMA_DIFFER = SchemaDiffer(
33
- parameterized_type_defaults={
31
+ SCHEMA_DIFFER_KWARGS = {
32
+ "parameterized_type_defaults": {
34
33
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(18, 3), (0,)],
35
34
  },
36
- )
35
+ }
37
36
  COMMENT_CREATION_TABLE = CommentCreationTable.COMMENT_COMMAND_ONLY
38
37
  COMMENT_CREATION_VIEW = CommentCreationView.COMMENT_COMMAND_ONLY
39
38
  SUPPORTS_CREATE_DROP_CATALOG = True
@@ -259,9 +259,9 @@ class VarcharSizeWorkaroundMixin(EngineAdapter):
259
259
  ) -> t.Dict[str, exp.DataType]:
260
260
  # get default lengths for types that support "max" length
261
261
  types_with_max_default_param = {
262
- k: [self.SCHEMA_DIFFER.parameterized_type_defaults[k][0][0]]
263
- for k in self.SCHEMA_DIFFER.max_parameter_length
264
- if k in self.SCHEMA_DIFFER.parameterized_type_defaults
262
+ k: [self.schema_differ.parameterized_type_defaults[k][0][0]]
263
+ for k in self.schema_differ.max_parameter_length
264
+ if k in self.schema_differ.parameterized_type_defaults
265
265
  }
266
266
 
267
267
  # Redshift and MSSQL have a bug where CTAS statements have non-deterministic types. If a LIMIT
@@ -270,7 +270,7 @@ class VarcharSizeWorkaroundMixin(EngineAdapter):
270
270
  # and supports "max" length, we convert it to "max" length to prevent inadvertent data truncation.
271
271
  for col_name, col_type in columns_to_types.items():
272
272
  if col_type.this in types_with_max_default_param and col_type.expressions:
273
- parameter = self.SCHEMA_DIFFER.get_type_parameters(col_type)
273
+ parameter = self.schema_differ.get_type_parameters(col_type)
274
274
  type_default = types_with_max_default_param[col_type.this]
275
275
  if parameter == type_default:
276
276
  col_type.set("expressions", [exp.DataTypeParam(this=exp.var("max"))])
@@ -30,7 +30,6 @@ from sqlmesh.core.engine_adapter.shared import (
30
30
  SourceQuery,
31
31
  set_catalog,
32
32
  )
33
- from sqlmesh.core.schema_diff import SchemaDiffer
34
33
  from sqlmesh.utils import get_source_columns_to_types
35
34
 
36
35
  if t.TYPE_CHECKING:
@@ -54,8 +53,8 @@ class MSSQLEngineAdapter(
54
53
  COMMENT_CREATION_TABLE = CommentCreationTable.UNSUPPORTED
55
54
  COMMENT_CREATION_VIEW = CommentCreationView.UNSUPPORTED
56
55
  SUPPORTS_REPLACE_TABLE = False
57
- SCHEMA_DIFFER = SchemaDiffer(
58
- parameterized_type_defaults={
56
+ SCHEMA_DIFFER_KWARGS = {
57
+ "parameterized_type_defaults": {
59
58
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(18, 0), (0,)],
60
59
  exp.DataType.build("BINARY", dialect=DIALECT).this: [(1,)],
61
60
  exp.DataType.build("VARBINARY", dialect=DIALECT).this: [(1,)],
@@ -67,12 +66,12 @@ class MSSQLEngineAdapter(
67
66
  exp.DataType.build("DATETIME2", dialect=DIALECT).this: [(7,)],
68
67
  exp.DataType.build("DATETIMEOFFSET", dialect=DIALECT).this: [(7,)],
69
68
  },
70
- max_parameter_length={
69
+ "max_parameter_length": {
71
70
  exp.DataType.build("VARBINARY", dialect=DIALECT).this: 2147483647, # 2 GB
72
71
  exp.DataType.build("VARCHAR", dialect=DIALECT).this: 2147483647,
73
72
  exp.DataType.build("NVARCHAR", dialect=DIALECT).this: 2147483647,
74
73
  },
75
- )
74
+ }
76
75
  VARIABLE_LENGTH_DATA_TYPES = {"binary", "varbinary", "char", "varchar", "nchar", "nvarchar"}
77
76
 
78
77
  @property
@@ -19,7 +19,6 @@ from sqlmesh.core.engine_adapter.shared import (
19
19
  DataObjectType,
20
20
  set_catalog,
21
21
  )
22
- from sqlmesh.core.schema_diff import SchemaDiffer
23
22
 
24
23
  if t.TYPE_CHECKING:
25
24
  from sqlmesh.core._typing import SchemaName, TableName
@@ -40,8 +39,8 @@ class MySQLEngineAdapter(
40
39
  MAX_COLUMN_COMMENT_LENGTH = 1024
41
40
  SUPPORTS_REPLACE_TABLE = False
42
41
  MAX_IDENTIFIER_LENGTH = 64
43
- SCHEMA_DIFFER = SchemaDiffer(
44
- parameterized_type_defaults={
42
+ SCHEMA_DIFFER_KWARGS = {
43
+ "parameterized_type_defaults": {
45
44
  exp.DataType.build("BIT", dialect=DIALECT).this: [(1,)],
46
45
  exp.DataType.build("BINARY", dialect=DIALECT).this: [(1,)],
47
46
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(10, 0), (0,)],
@@ -52,7 +51,7 @@ class MySQLEngineAdapter(
52
51
  exp.DataType.build("DATETIME", dialect=DIALECT).this: [(0,)],
53
52
  exp.DataType.build("TIMESTAMP", dialect=DIALECT).this: [(0,)],
54
53
  },
55
- )
54
+ }
56
55
 
57
56
  def get_current_catalog(self) -> t.Optional[str]:
58
57
  """Returns the catalog name of the current connection."""
@@ -14,7 +14,6 @@ from sqlmesh.core.engine_adapter.mixins import (
14
14
  logical_merge,
15
15
  )
16
16
  from sqlmesh.core.engine_adapter.shared import set_catalog
17
- from sqlmesh.core.schema_diff import SchemaDiffer
18
17
 
19
18
  if t.TYPE_CHECKING:
20
19
  from sqlmesh.core._typing import TableName
@@ -36,15 +35,15 @@ class PostgresEngineAdapter(
36
35
  CURRENT_CATALOG_EXPRESSION = exp.column("current_catalog")
37
36
  SUPPORTS_REPLACE_TABLE = False
38
37
  MAX_IDENTIFIER_LENGTH = 63
39
- SCHEMA_DIFFER = SchemaDiffer(
40
- parameterized_type_defaults={
38
+ SCHEMA_DIFFER_KWARGS = {
39
+ "parameterized_type_defaults": {
41
40
  # DECIMAL without precision is "up to 131072 digits before the decimal point; up to 16383 digits after the decimal point"
42
41
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(131072 + 16383, 16383), (0,)],
43
42
  exp.DataType.build("CHAR", dialect=DIALECT).this: [(1,)],
44
43
  exp.DataType.build("TIME", dialect=DIALECT).this: [(6,)],
45
44
  exp.DataType.build("TIMESTAMP", dialect=DIALECT).this: [(6,)],
46
45
  },
47
- types_with_unlimited_length={
46
+ "types_with_unlimited_length": {
48
47
  # all can ALTER to `TEXT`
49
48
  exp.DataType.build("TEXT", dialect=DIALECT).this: {
50
49
  exp.DataType.build("VARCHAR", dialect=DIALECT).this,
@@ -63,8 +62,8 @@ class PostgresEngineAdapter(
63
62
  exp.DataType.build("BPCHAR", dialect=DIALECT).this
64
63
  },
65
64
  },
66
- drop_cascade=True,
67
- )
65
+ "drop_cascade": True,
66
+ }
68
67
 
69
68
  def _fetch_native_df(
70
69
  self, query: t.Union[exp.Expression, str], quote_identifiers: bool = False
@@ -22,7 +22,6 @@ from sqlmesh.core.engine_adapter.shared import (
22
22
  SourceQuery,
23
23
  set_catalog,
24
24
  )
25
- from sqlmesh.core.schema_diff import SchemaDiffer
26
25
  from sqlmesh.utils.errors import SQLMeshError
27
26
 
28
27
  if t.TYPE_CHECKING:
@@ -48,8 +47,8 @@ class RedshiftEngineAdapter(
48
47
  COMMENT_CREATION_VIEW = CommentCreationView.UNSUPPORTED
49
48
  SUPPORTS_REPLACE_TABLE = False
50
49
 
51
- SCHEMA_DIFFER = SchemaDiffer(
52
- parameterized_type_defaults={
50
+ SCHEMA_DIFFER_KWARGS = {
51
+ "parameterized_type_defaults": {
53
52
  exp.DataType.build("VARBYTE", dialect=DIALECT).this: [(64000,)],
54
53
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(18, 0), (0,)],
55
54
  exp.DataType.build("CHAR", dialect=DIALECT).this: [(1,)],
@@ -57,13 +56,13 @@ class RedshiftEngineAdapter(
57
56
  exp.DataType.build("NCHAR", dialect=DIALECT).this: [(1,)],
58
57
  exp.DataType.build("NVARCHAR", dialect=DIALECT).this: [(256,)],
59
58
  },
60
- max_parameter_length={
59
+ "max_parameter_length": {
61
60
  exp.DataType.build("CHAR", dialect=DIALECT).this: 4096,
62
61
  exp.DataType.build("VARCHAR", dialect=DIALECT).this: 65535,
63
62
  },
64
- precision_increase_allowed_types={exp.DataType.build("VARCHAR", dialect=DIALECT).this},
65
- drop_cascade=True,
66
- )
63
+ "precision_increase_allowed_types": {exp.DataType.build("VARCHAR", dialect=DIALECT).this},
64
+ "drop_cascade": True,
65
+ }
67
66
  VARIABLE_LENGTH_DATA_TYPES = {
68
67
  "char",
69
68
  "character",
@@ -23,7 +23,6 @@ from sqlmesh.core.engine_adapter.shared import (
23
23
  SourceQuery,
24
24
  set_catalog,
25
25
  )
26
- from sqlmesh.core.schema_diff import SchemaDiffer
27
26
  from sqlmesh.utils import optional_import, get_source_columns_to_types
28
27
  from sqlmesh.utils.errors import SQLMeshError
29
28
  from sqlmesh.utils.pandas import columns_to_types_from_dtypes
@@ -56,8 +55,8 @@ class SnowflakeEngineAdapter(GetCurrentCatalogFromFunctionMixin, ClusteredByMixi
56
55
  CURRENT_CATALOG_EXPRESSION = exp.func("current_database")
57
56
  SUPPORTS_CREATE_DROP_CATALOG = True
58
57
  SUPPORTED_DROP_CASCADE_OBJECT_KINDS = ["DATABASE", "SCHEMA", "TABLE"]
59
- SCHEMA_DIFFER = SchemaDiffer(
60
- parameterized_type_defaults={
58
+ SCHEMA_DIFFER_KWARGS = {
59
+ "parameterized_type_defaults": {
61
60
  exp.DataType.build("BINARY", dialect=DIALECT).this: [(8388608,)],
62
61
  exp.DataType.build("VARBINARY", dialect=DIALECT).this: [(8388608,)],
63
62
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(38, 0), (0,)],
@@ -70,7 +69,7 @@ class SnowflakeEngineAdapter(GetCurrentCatalogFromFunctionMixin, ClusteredByMixi
70
69
  exp.DataType.build("TIMESTAMP_NTZ", dialect=DIALECT).this: [(9,)],
71
70
  exp.DataType.build("TIMESTAMP_TZ", dialect=DIALECT).this: [(9,)],
72
71
  },
73
- )
72
+ }
74
73
  MANAGED_TABLE_KIND = "DYNAMIC TABLE"
75
74
  SNOWPARK = "snowpark"
76
75
 
@@ -22,7 +22,6 @@ from sqlmesh.core.engine_adapter.shared import (
22
22
  SourceQuery,
23
23
  set_catalog,
24
24
  )
25
- from sqlmesh.core.schema_diff import SchemaDiffer
26
25
  from sqlmesh.utils import classproperty, get_source_columns_to_types
27
26
  from sqlmesh.utils.errors import SQLMeshError
28
27
 
@@ -61,12 +60,12 @@ class SparkEngineAdapter(
61
60
 
62
61
  WAP_PREFIX = "wap_"
63
62
  BRANCH_PREFIX = "branch_"
64
- SCHEMA_DIFFER = SchemaDiffer(
65
- parameterized_type_defaults={
63
+ SCHEMA_DIFFER_KWARGS = {
64
+ "parameterized_type_defaults": {
66
65
  # default decimal precision varies across backends
67
66
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(), (0,)],
68
67
  },
69
- )
68
+ }
70
69
 
71
70
  @property
72
71
  def connection(self) -> SparkSessionConnection:
@@ -26,7 +26,6 @@ from sqlmesh.core.engine_adapter.shared import (
26
26
  SourceQuery,
27
27
  set_catalog,
28
28
  )
29
- from sqlmesh.core.schema_diff import SchemaDiffer
30
29
  from sqlmesh.utils import get_source_columns_to_types
31
30
  from sqlmesh.utils.errors import SQLMeshError
32
31
  from sqlmesh.utils.date import TimeLike
@@ -56,14 +55,14 @@ class TrinoEngineAdapter(
56
55
  SUPPORTED_DROP_CASCADE_OBJECT_KINDS = ["SCHEMA"]
57
56
  DEFAULT_CATALOG_TYPE = "hive"
58
57
  QUOTE_IDENTIFIERS_IN_VIEWS = False
59
- SCHEMA_DIFFER = SchemaDiffer(
60
- parameterized_type_defaults={
58
+ SCHEMA_DIFFER_KWARGS = {
59
+ "parameterized_type_defaults": {
61
60
  # default decimal precision varies across backends
62
61
  exp.DataType.build("DECIMAL", dialect=DIALECT).this: [(), (0,)],
63
62
  exp.DataType.build("CHAR", dialect=DIALECT).this: [(1,)],
64
63
  exp.DataType.build("TIMESTAMP", dialect=DIALECT).this: [(3,)],
65
64
  },
66
- )
65
+ }
67
66
  # some catalogs support microsecond (precision 6) but it has to be specifically enabled (Hive) or just isnt available (Delta / TIMESTAMP WITH TIME ZONE)
68
67
  # and even if you have a TIMESTAMP(6) the date formatting functions still only support millisecond precision
69
68
  MAX_TIMESTAMP_PRECISION = 3
@@ -5,6 +5,8 @@ import logging
5
5
  import typing as t
6
6
  from dataclasses import dataclass
7
7
  from collections import defaultdict
8
+ from enum import Enum
9
+
8
10
  from pydantic import Field
9
11
  from sqlglot import exp
10
12
  from sqlglot.helper import ensure_list, seq_get
@@ -132,14 +134,15 @@ class TableAlterDropColumnOperation(TableAlterColumnOperation):
132
134
  @dataclass(frozen=True)
133
135
  class TableAlterChangeColumnTypeOperation(TableAlterTypedColumnOperation):
134
136
  current_type: exp.DataType
137
+ is_part_of_destructive_change: bool = False
135
138
 
136
139
  @property
137
140
  def is_additive(self) -> bool:
138
- return True
141
+ return not self.is_part_of_destructive_change
139
142
 
140
143
  @property
141
144
  def is_destructive(self) -> bool:
142
- return False
145
+ return self.is_part_of_destructive_change
143
146
 
144
147
  @property
145
148
  def _alter_actions(self) -> t.List[exp.Expression]:
@@ -278,6 +281,33 @@ class TableAlterColumnPosition:
278
281
  return exp.ColumnPosition(this=column, position=position)
279
282
 
280
283
 
284
+ class NestedSupport(str, Enum):
285
+ # Supports all nested data type operations
286
+ ALL = "ALL"
287
+ # Does not support any nested data type operations
288
+ NONE = "NONE"
289
+ # Supports nested data type operations except for those that require dropping a nested field
290
+ ALL_BUT_DROP = "ALL_BUT_DROP"
291
+ # Ignores all nested data type operations
292
+ IGNORE = "IGNORE"
293
+
294
+ @property
295
+ def is_all(self) -> bool:
296
+ return self == NestedSupport.ALL
297
+
298
+ @property
299
+ def is_none(self) -> bool:
300
+ return self == NestedSupport.NONE
301
+
302
+ @property
303
+ def is_all_but_drop(self) -> bool:
304
+ return self == NestedSupport.ALL_BUT_DROP
305
+
306
+ @property
307
+ def is_ignore(self) -> bool:
308
+ return self == NestedSupport.IGNORE
309
+
310
+
281
311
  class SchemaDiffer(PydanticModel):
282
312
  """
283
313
  Compares a source schema against a target schema and returns a list of alter statements to have the source
@@ -297,10 +327,7 @@ class SchemaDiffer(PydanticModel):
297
327
  Args:
298
328
  support_positional_add: Whether the engine for which the diff is being computed supports adding columns in a
299
329
  specific position in the set of existing columns.
300
- support_nested_operations: Whether the engine for which the diff is being computed supports modifications to
301
- nested data types like STRUCTs and ARRAYs.
302
- support_nested_drop: Whether the engine for which the diff is being computed supports removing individual
303
- columns of nested STRUCTs.
330
+ nested_support: How the engine for which the diff is being computed supports nested types.
304
331
  compatible_types: Types that are compatible and automatically coerced in actions like UNION ALL. Dict key is data
305
332
  type, and value is the set of types that are compatible with it.
306
333
  coerceable_types: The mapping from a current type to all types that can be safely coerced to the current one without
@@ -323,11 +350,14 @@ class SchemaDiffer(PydanticModel):
323
350
  max_parameter_length: Numeric parameter values corresponding to "max". Example: `VARCHAR(max)` -> `VARCHAR(65535)`.
324
351
  types_with_unlimited_length: Data types that accept values of any length up to system limits. Any explicitly
325
352
  parameterized type can ALTER to its unlimited length version, along with different types in some engines.
353
+ treat_alter_data_type_as_destructive: The SchemaDiffer will only output change data type operations if it
354
+ concludes the change is compatible and won't result in data loss. If this flag is set to True, it will
355
+ flag these data type changes as destructive. This was added for dbt adapter support and likely shouldn't
356
+ be set outside of that context.
326
357
  """
327
358
 
328
359
  support_positional_add: bool = False
329
- support_nested_operations: bool = False
330
- support_nested_drop: bool = False
360
+ nested_support: NestedSupport = NestedSupport.NONE
331
361
  array_element_selector: str = ""
332
362
  compatible_types: t.Dict[exp.DataType, t.Set[exp.DataType]] = {}
333
363
  coerceable_types_: t.Dict[exp.DataType, t.Set[exp.DataType]] = Field(
@@ -341,6 +371,7 @@ class SchemaDiffer(PydanticModel):
341
371
  ] = {}
342
372
  max_parameter_length: t.Dict[exp.DataType.Type, t.Union[int, float]] = {}
343
373
  types_with_unlimited_length: t.Dict[exp.DataType.Type, t.Set[exp.DataType.Type]] = {}
374
+ treat_alter_data_type_as_destructive: bool = False
344
375
 
345
376
  _coerceable_types: t.Dict[exp.DataType, t.Set[exp.DataType]] = {}
346
377
 
@@ -575,9 +606,11 @@ class SchemaDiffer(PydanticModel):
575
606
  # We don't copy on purpose here because current_type may need to be mutated inside
576
607
  # _get_operations (struct.expressions.pop and struct.expressions.insert)
577
608
  current_type = exp.DataType.build(current_type, copy=False)
578
- if self.support_nested_operations:
609
+ if not self.nested_support.is_none:
579
610
  if new_type.this == current_type.this == exp.DataType.Type.STRUCT:
580
- if self.support_nested_drop or not self._requires_drop_alteration(
611
+ if self.nested_support.is_ignore:
612
+ return []
613
+ if self.nested_support.is_all or not self._requires_drop_alteration(
581
614
  current_type, new_type
582
615
  ):
583
616
  return self._get_operations(
@@ -597,7 +630,9 @@ class SchemaDiffer(PydanticModel):
597
630
  new_array_type = new_type.expressions[0]
598
631
  current_array_type = current_type.expressions[0]
599
632
  if new_array_type.this == current_array_type.this == exp.DataType.Type.STRUCT:
600
- if self.support_nested_drop or not self._requires_drop_alteration(
633
+ if self.nested_support.is_ignore:
634
+ return []
635
+ if self.nested_support.is_all or not self._requires_drop_alteration(
601
636
  current_array_type, new_array_type
602
637
  ):
603
638
  return self._get_operations(
@@ -624,6 +659,7 @@ class SchemaDiffer(PydanticModel):
624
659
  current_type=current_type,
625
660
  expected_table_struct=root_struct.copy(),
626
661
  array_element_selector=self.array_element_selector,
662
+ is_part_of_destructive_change=self.treat_alter_data_type_as_destructive,
627
663
  )
628
664
  ]
629
665
  if ignore_destructive:
@@ -806,12 +842,15 @@ def get_additive_column_names(alter_expressions: t.List[TableAlterOperation]) ->
806
842
  ]
807
843
 
808
844
 
809
- def get_schema_differ(dialect: str) -> SchemaDiffer:
845
+ def get_schema_differ(
846
+ dialect: str, overrides: t.Optional[t.Dict[str, t.Any]] = None
847
+ ) -> SchemaDiffer:
810
848
  """
811
849
  Returns the appropriate SchemaDiffer for a given dialect without initializing the engine adapter.
812
850
 
813
851
  Args:
814
852
  dialect: The dialect for which to get the schema differ.
853
+ overrides: Optional dictionary of overrides to apply to the SchemaDiffer instance.
815
854
 
816
855
  Returns:
817
856
  The SchemaDiffer instance configured for the given dialect.
@@ -825,7 +864,12 @@ def get_schema_differ(dialect: str) -> SchemaDiffer:
825
864
  dialect = dialect.lower()
826
865
  dialect = DIALECT_ALIASES.get(dialect, dialect)
827
866
  engine_adapter_class = DIALECT_TO_ENGINE_ADAPTER.get(dialect, EngineAdapter)
828
- return getattr(engine_adapter_class, "SCHEMA_DIFFER", SchemaDiffer())
867
+ return SchemaDiffer(
868
+ **{
869
+ **getattr(engine_adapter_class, "SCHEMA_DIFFER_KWARGS"),
870
+ **(overrides or {}),
871
+ }
872
+ )
829
873
 
830
874
 
831
875
  def _get_name_and_type(struct: exp.ColumnDef) -> t.Tuple[exp.Identifier, exp.DataType]:
sqlmesh/dbt/target.py CHANGED
@@ -29,6 +29,7 @@ from sqlmesh.core.model import (
29
29
  IncrementalByUniqueKeyKind,
30
30
  IncrementalUnmanagedKind,
31
31
  )
32
+ from sqlmesh.core.schema_diff import NestedSupport
32
33
  from sqlmesh.dbt.common import DbtConfig
33
34
  from sqlmesh.dbt.relation import Policy
34
35
  from sqlmesh.dbt.util import DBT_VERSION
@@ -50,6 +51,25 @@ SERIALIZABLE_FIELDS = {
50
51
  "schema_",
51
52
  }
52
53
 
54
+ SCHEMA_DIFFER_OVERRIDES = {
55
+ "schema_differ_overrides": {
56
+ "treat_alter_data_type_as_destructive": True,
57
+ "nested_support": NestedSupport.IGNORE,
58
+ }
59
+ }
60
+
61
+
62
+ def with_schema_differ_overrides(
63
+ func: t.Callable[..., ConnectionConfig],
64
+ ) -> t.Callable[..., ConnectionConfig]:
65
+ """Decorator that merges default config with kwargs."""
66
+
67
+ def wrapper(self: TargetConfig, **kwargs: t.Any) -> ConnectionConfig:
68
+ merged_kwargs = {**SCHEMA_DIFFER_OVERRIDES, **kwargs}
69
+ return func(self, **merged_kwargs)
70
+
71
+ return wrapper
72
+
53
73
 
54
74
  class TargetConfig(abc.ABC, DbtConfig):
55
75
  """
@@ -92,6 +112,7 @@ class TargetConfig(abc.ABC, DbtConfig):
92
112
  """The default incremental strategy for the db"""
93
113
  raise NotImplementedError
94
114
 
115
+ @with_schema_differ_overrides
95
116
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
96
117
  """Converts target config to SQLMesh connection config"""
97
118
  raise NotImplementedError
@@ -177,6 +198,7 @@ class DuckDbConfig(TargetConfig):
177
198
 
178
199
  return DuckDBRelation
179
200
 
201
+ @with_schema_differ_overrides
180
202
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
181
203
  if self.extensions is not None:
182
204
  kwargs["extensions"] = self.extensions
@@ -286,6 +308,7 @@ class SnowflakeConfig(TargetConfig):
286
308
 
287
309
  return SnowflakeColumn
288
310
 
311
+ @with_schema_differ_overrides
289
312
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
290
313
  return SnowflakeConnectionConfig(
291
314
  user=self.user,
@@ -359,6 +382,7 @@ class PostgresConfig(TargetConfig):
359
382
  def default_incremental_strategy(self, kind: IncrementalKind) -> str:
360
383
  return "delete+insert" if kind is IncrementalByUniqueKeyKind else "append"
361
384
 
385
+ @with_schema_differ_overrides
362
386
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
363
387
  return PostgresConnectionConfig(
364
388
  host=self.host,
@@ -454,6 +478,7 @@ class RedshiftConfig(TargetConfig):
454
478
  return RedshiftColumn
455
479
  return super(RedshiftConfig, cls).column_class
456
480
 
481
+ @with_schema_differ_overrides
457
482
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
458
483
  return RedshiftConnectionConfig(
459
484
  user=self.user,
@@ -504,6 +529,7 @@ class DatabricksConfig(TargetConfig):
504
529
 
505
530
  return DatabricksColumn
506
531
 
532
+ @with_schema_differ_overrides
507
533
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
508
534
  return DatabricksConnectionConfig(
509
535
  server_hostname=self.host,
@@ -605,6 +631,7 @@ class BigQueryConfig(TargetConfig):
605
631
 
606
632
  return BigQueryColumn
607
633
 
634
+ @with_schema_differ_overrides
608
635
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
609
636
  job_retries = self.job_retries if self.job_retries is not None else self.retries
610
637
  job_execution_timeout_seconds = (
@@ -778,6 +805,7 @@ class MSSQLConfig(TargetConfig):
778
805
  def dialect(self) -> str:
779
806
  return "tsql"
780
807
 
808
+ @with_schema_differ_overrides
781
809
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
782
810
  return MSSQLConnectionConfig(
783
811
  host=self.host,
@@ -892,6 +920,7 @@ class TrinoConfig(TargetConfig):
892
920
 
893
921
  return TrinoColumn
894
922
 
923
+ @with_schema_differ_overrides
895
924
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
896
925
  return TrinoConnectionConfig(
897
926
  method=self._method_to_auth_enum[self.method],
@@ -1002,6 +1031,7 @@ class ClickhouseConfig(TargetConfig):
1002
1031
 
1003
1032
  return ClickHouseColumn
1004
1033
 
1034
+ @with_schema_differ_overrides
1005
1035
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
1006
1036
  return ClickhouseConnectionConfig(
1007
1037
  host=self.host,
@@ -1085,6 +1115,7 @@ class AthenaConfig(TargetConfig):
1085
1115
  def default_incremental_strategy(self, kind: IncrementalKind) -> str:
1086
1116
  return "insert_overwrite"
1087
1117
 
1118
+ @with_schema_differ_overrides
1088
1119
  def to_sqlmesh(self, **kwargs: t.Any) -> ConnectionConfig:
1089
1120
  return AthenaConnectionConfig(
1090
1121
  type="athena",
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: sqlmesh
3
- Version: 0.210.1.dev1
3
+ Version: 0.210.1.dev3
4
4
  Summary: Next-generation data transformation framework
5
5
  Author-email: "TobikoData Inc." <engineering@tobikodata.com>
6
6
  License: Apache License
@@ -1,5 +1,5 @@
1
1
  sqlmesh/__init__.py,sha256=QjwaamJIdW7voXoS880yAx7tHm-Im4_mqGA-XJgafos,7631
2
- sqlmesh/_version.py,sha256=tXYl1pXPZNWu4zsdNtp6evnoOv4qHvxh7QWbA-49P2U,721
2
+ sqlmesh/_version.py,sha256=dCRRgTe4oT0uz4TQwVjMAmo_ETorB9kxQko0-T1rDBg,721
3
3
  sqlmesh/magics.py,sha256=xLh3u4eqpVrKRVN5KF3X84RPRqjygAB9AJP1TXwH8hg,42086
4
4
  sqlmesh/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
5
5
  sqlmesh/cicd/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -25,7 +25,7 @@ sqlmesh/core/notification_target.py,sha256=PPGoDrgbRKxr27vJEu03XqNTQLYTw0ZF_b0yA
25
25
  sqlmesh/core/reference.py,sha256=k7OSkLqTjPR8WJjNeFj0xAJ297nZUMgb_iTVwKRRKjc,4875
26
26
  sqlmesh/core/renderer.py,sha256=PMUmmtwqk3FA5lN-16OWl6buCbrVa1M8NIgRXCYEB8k,26805
27
27
  sqlmesh/core/scheduler.py,sha256=H3_fjzfYI8wSRoWnGXE7OXYRkRpL-GYRfQOwGO7wrHE,46806
28
- sqlmesh/core/schema_diff.py,sha256=aVbZtGg91GpoW5jJTHz4CR2ICs-a9EGyBLtPZ_jpIuw,32143
28
+ sqlmesh/core/schema_diff.py,sha256=QRQfiVuptTfDAVf7zkuGo7beqXKRno3MUvRjYB6q0nk,33702
29
29
  sqlmesh/core/schema_loader.py,sha256=_Pq2RSw91uthqv1vNi_eHmLlzhtGz_APMJ0wAJZYuvk,3677
30
30
  sqlmesh/core/selector.py,sha256=9bqtBx7Onl8zZb-G4OsGVYVwkdm24j_qnp5HgXLFhR4,12837
31
31
  sqlmesh/core/signal.py,sha256=yVLXewYP6eH0vt-EwaIaI2WwHz6hWsVr-Kb2m4kP1FU,1353
@@ -41,7 +41,7 @@ sqlmesh/core/config/__init__.py,sha256=b7oIU9VA0oJD2FxrHkXrcLdzELeObSveT9f22QBGd
41
41
  sqlmesh/core/config/base.py,sha256=t8NQmsgQoZSc-k0dlDiCb8t1jj0AMYdGZ-6se9q_Pks,4898
42
42
  sqlmesh/core/config/categorizer.py,sha256=6vzUoNLjR6GOEb_2mYVz2TwmMv2BfldgHX2u-Le5HZs,1975
43
43
  sqlmesh/core/config/common.py,sha256=9V6PltBAjYeWLOU5dAbqL55BSFfpg8z8t2Op1x_PLhU,6418
44
- sqlmesh/core/config/connection.py,sha256=7WMwDy6WeDNO7XQHK2Tf4w4gZHBZHO-4DIxQIBXP9Cw,90182
44
+ sqlmesh/core/config/connection.py,sha256=w-3gQHHQA0Mqf2aQ3N4xUVCZXqdtXf28thP5BvLcDXg,90315
45
45
  sqlmesh/core/config/format.py,sha256=6CXFbvnor56xbldKE-Vrm9k_ABRoY4v6vgIb3mCihiQ,1355
46
46
  sqlmesh/core/config/gateway.py,sha256=tYngyqwd_4Qr9lhcv2hlvLvb_2pgYYtKu6hdGsTr-4I,1931
47
47
  sqlmesh/core/config/janitor.py,sha256=NP0i51V8XwMrHw8uuwQknivuudIleNiFBtBnMuXmfIY,362
@@ -57,24 +57,24 @@ sqlmesh/core/config/scheduler.py,sha256=LVEHIln7dqv8ygo4uniji4j9-gfuJlk-WpQU9FAq
57
57
  sqlmesh/core/config/ui.py,sha256=jsO-S6_d9NkLZGG5pT4mgKgxMF34KzkDociZAMvCX3U,278
58
58
  sqlmesh/core/engine_adapter/__init__.py,sha256=y9jZAFdMBkkkRrf0ymfsJJn6s_7Ya6OpDgR4Bf1OG_U,2383
59
59
  sqlmesh/core/engine_adapter/_typing.py,sha256=QSXXdxtTHXTwJyiv-9ArAJHvwmJPfa7tShuD_3vGwfg,1010
60
- sqlmesh/core/engine_adapter/athena.py,sha256=hO97fMAHiCLPuUMCGKj0eoCSnTSO71JH1f2TkPsqNkc,26742
61
- sqlmesh/core/engine_adapter/base.py,sha256=i1zz1pCwXYXtIcOV4sYtvlErykh5VtwYKQIn6eh5zfU,113201
60
+ sqlmesh/core/engine_adapter/athena.py,sha256=UlZTHy1bGq0Wqzp9hmbphCpL-P6duOALNGNBSNEHYnk,26756
61
+ sqlmesh/core/engine_adapter/base.py,sha256=Nzd6Rg--W0BGuEgWVxgAfarabc-HPJcR9gUQXZjj16g,113607
62
62
  sqlmesh/core/engine_adapter/base_postgres.py,sha256=U4Y_0-M6_0_RcKbljX57DIUSwIa70w02k-UoDOnWPxQ,7016
63
- sqlmesh/core/engine_adapter/bigquery.py,sha256=2vyJUtdbY7Dcf9ELLlJdf13_SVQoz7rApLIOUERYQxs,53945
64
- sqlmesh/core/engine_adapter/clickhouse.py,sha256=-n2O9HG4zTNv4xuXVj8JZfIKNZvZq-_za0l3MpPREa8,35873
65
- sqlmesh/core/engine_adapter/databricks.py,sha256=1a5hmdKgf-5TMHVUOAVe1Z-NbRKgZv95dLF69aaW4_w,14613
66
- sqlmesh/core/engine_adapter/duckdb.py,sha256=G0sa8QF9e9sdRPPgNZms9j0AYGDnvTa6-tkoIETtJZs,7348
63
+ sqlmesh/core/engine_adapter/bigquery.py,sha256=dtzRk6BlCLJxnwXeoz1ANAXbIrhtiJEAruasHzJYj0M,53935
64
+ sqlmesh/core/engine_adapter/clickhouse.py,sha256=yBVEorfoaHp-O0qi3UXOnGlDwM7_Yo6lw6pOUMEjwB4,35854
65
+ sqlmesh/core/engine_adapter/databricks.py,sha256=B6OkHelGrxxehZlYno5cZ8MB_bHirQS_imznSZdQGrY,14589
66
+ sqlmesh/core/engine_adapter/duckdb.py,sha256=yH_I9qxlLYNlreOZXP-60aIhgCkBeeu44z4_RCALuxU,7296
67
67
  sqlmesh/core/engine_adapter/fabric.py,sha256=OByNUHUshC1LZ0P7lwtBUhmtf5k9Sgv284mS6jDwFKI,11936
68
- sqlmesh/core/engine_adapter/mixins.py,sha256=SX4OqiMZHG8k09Eu-d01xhB_R0U_61bcRfUlLUluh58,23607
69
- sqlmesh/core/engine_adapter/mssql.py,sha256=Ttqn89ArFXOAz-6R7q9Iwm9cI8b9BGieH85Y0E0o99I,18274
70
- sqlmesh/core/engine_adapter/mysql.py,sha256=lVC-siXZK3iSfqCmBjZNw8uy09Z8la8v8_oUZ-E2OwI,6966
71
- sqlmesh/core/engine_adapter/postgres.py,sha256=30zSHxiXHBB96jg2ydVKMGeFoPxjZF8kfjNxzckMa-k,5129
72
- sqlmesh/core/engine_adapter/redshift.py,sha256=UUUHPqHmCyXyK04BbTCTuw2-tSP_6ykHMV7vlupqbaQ,17537
68
+ sqlmesh/core/engine_adapter/mixins.py,sha256=JoITl_xbY5io5LtiTenqEhjWE9VCv2cK4Ue025Bkm7Y,23607
69
+ sqlmesh/core/engine_adapter/mssql.py,sha256=xLX15SrL-2ukv_YLy9a_4g9pxPga-1WcwxWUBIFY-f4,18225
70
+ sqlmesh/core/engine_adapter/mysql.py,sha256=071qYHeJ_7gDdC7YWJoRCorjhxGAVkhtqWL-KetfPCg,6914
71
+ sqlmesh/core/engine_adapter/postgres.py,sha256=v6fD7ci22-DrZBtry_03Lfq5m7SNgSPq5X_BZ1dWLhk,5083
72
+ sqlmesh/core/engine_adapter/redshift.py,sha256=bfrgxY3Fqcbz5inAF4cxOQCmRdfuC--aPu5U3ks29LA,17494
73
73
  sqlmesh/core/engine_adapter/risingwave.py,sha256=GY0u085TWerl8kTRNJpEutdD5FBsoPijQ0CcOkWOJEE,2359
74
74
  sqlmesh/core/engine_adapter/shared.py,sha256=pvYU-sC2WEIOENm4oG4UrOCWXF56h-FEmlAqAR8TYoA,13500
75
- sqlmesh/core/engine_adapter/snowflake.py,sha256=SZU1aI5hGOkNBHAZ6x1GgZzd5f5EJsAL0_cd8lcdfXo,30056
76
- sqlmesh/core/engine_adapter/spark.py,sha256=SndnX3zY9oqDywtrFJ3dOS-CvCJuBxmBVvDO4Yt1L54,22420
77
- sqlmesh/core/engine_adapter/trino.py,sha256=fe0g8U1LMQpCvgsgwN0IVuYLDi0ducum2e-ktHh7-ow,16341
75
+ sqlmesh/core/engine_adapter/snowflake.py,sha256=5vlEaDRROI4pUHCkkRUNMCl0-R7p24Q5goJZ-FmJ9EQ,30004
76
+ sqlmesh/core/engine_adapter/spark.py,sha256=YTFLBBF7Io6iZAhfsyzqtaqxddCCHxt0J9XiclUalf0,22368
77
+ sqlmesh/core/engine_adapter/trino.py,sha256=euroG7zMlQyv8hlo7SBo-deZuj1gti5jRy-9zToNTGE,16289
78
78
  sqlmesh/core/linter/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
79
79
  sqlmesh/core/linter/definition.py,sha256=JDJTkhByUw4Tr3nF-BOHKFAx_eASQqEqzX6AUVQUz8I,5659
80
80
  sqlmesh/core/linter/helpers.py,sha256=cwKXP4sL6azRtNVGbMfJ5_6Hqq5Xx2M2rRLCgH3Y3ag,10743
@@ -140,7 +140,7 @@ sqlmesh/dbt/project.py,sha256=bXW2VL0023mhOr0GRAcYsomIcR3qTpflWgZO3oMwtOE,4102
140
140
  sqlmesh/dbt/relation.py,sha256=rgDJQUuENjqq7kpMJJ6AdlgwYmcYjA1oFj6LCYCS-Hg,227
141
141
  sqlmesh/dbt/seed.py,sha256=w7oGWiTGUSgGyIdouM1rcLh-yMNrb5msSrgMtYt1acE,4194
142
142
  sqlmesh/dbt/source.py,sha256=IZK-aOV-KdWIOPuXqRjJZAZ7phW1HUXoHtE-3clgkx4,4125
143
- sqlmesh/dbt/target.py,sha256=r_Q5aac8OsSkbUUnL1Bc9RzCBs8szp0aWx2HneU87Gk,42963
143
+ sqlmesh/dbt/target.py,sha256=7KMQAyd0Jy2TaAJ0rydswWFz1sfHXg4aWeMgcmPanR8,43941
144
144
  sqlmesh/dbt/test.py,sha256=aOTKqYpVafff-TU4Xhbc9eZr6QAuFLMxIu_sV-18JLQ,8282
145
145
  sqlmesh/dbt/util.py,sha256=BdtfQ7sxnZ8y8CFJStkePpmRE-KntHCXTefRnXR5Pag,905
146
146
  sqlmesh/dbt/converter/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -293,7 +293,7 @@ sqlmesh/utils/pydantic.py,sha256=o_NsXbIpDqNpUA1Uc5xF0ZzoXQYYB0DfHwdRxBwXPNk,120
293
293
  sqlmesh/utils/rich.py,sha256=cwQ5nJ6sgz64xHtoh6_ec7ReV5YpsOGhMtUJnwoRfEI,3549
294
294
  sqlmesh/utils/windows.py,sha256=r7Yin4WEwbvH7sKA3hOJtRsclmscNuBeCklCfVPvtQs,611
295
295
  sqlmesh/utils/yaml.py,sha256=hvo5lmybYLcIx4p6CQwufS8X4MbwS60lEBnCmYJCXmU,2336
296
- sqlmesh-0.210.1.dev1.dist-info/licenses/LICENSE,sha256=OlMefUjgWJdULtf84BLW0AZZcY8DwdgQqb_1j2862j8,11346
296
+ sqlmesh-0.210.1.dev3.dist-info/licenses/LICENSE,sha256=OlMefUjgWJdULtf84BLW0AZZcY8DwdgQqb_1j2862j8,11346
297
297
  sqlmesh_dbt/__init__.py,sha256=awYS5y5mz-1NUmx6i5h5NSTJ7tidRl9NC0FAnFWSF6U,350
298
298
  sqlmesh_dbt/cli.py,sha256=Enh699Mq1L5t-9F-GsZDmao6YQc1YbpatOFpr_FqcEU,2711
299
299
  sqlmesh_dbt/console.py,sha256=1B0B5_R1DlrEkyWVDl8G78-B6_K-ZtLPsQEhqPCfLEU,188
@@ -416,8 +416,8 @@ web/server/api/endpoints/models.py,sha256=kwj0s7uve3iZSMfmjkoPVMFMeY1sD0peTeyrWf
416
416
  web/server/api/endpoints/modules.py,sha256=8hqqgonGay_mJmpCw0IdbjsPhWlQH2VLdKAqha-myac,468
417
417
  web/server/api/endpoints/plan.py,sha256=bbbY50W_2MsZSTxOHWMKz0tbIm75nsRSlPy8GI2fg9Q,9306
418
418
  web/server/api/endpoints/table_diff.py,sha256=8XTwgOh6QBbNy_hTM1JuHgRjbnie-pGPrphiW-FNLjQ,6058
419
- sqlmesh-0.210.1.dev1.dist-info/METADATA,sha256=gDmGiZ5zCA3rI7iJtvb75io7XBc0Rjb_MsYBhX9fvfs,26756
420
- sqlmesh-0.210.1.dev1.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
421
- sqlmesh-0.210.1.dev1.dist-info/entry_points.txt,sha256=sHAf6tQczIM8xZoduN4qaUjV7QEPVUUW_LCT8EDUMv4,155
422
- sqlmesh-0.210.1.dev1.dist-info/top_level.txt,sha256=RQ-33FPe2IgL0rgossAfJkCRtqslz9b7wFARqiWLC5Q,24
423
- sqlmesh-0.210.1.dev1.dist-info/RECORD,,
419
+ sqlmesh-0.210.1.dev3.dist-info/METADATA,sha256=hfDf-yLyxx-pOlFFqe3owiLiC1nNnx4zP7ydYm4yjPg,26756
420
+ sqlmesh-0.210.1.dev3.dist-info/WHEEL,sha256=_zCd3N1l69ArxyTb8rzEoP9TpbYXkqRFSNOD5OuxnTs,91
421
+ sqlmesh-0.210.1.dev3.dist-info/entry_points.txt,sha256=sHAf6tQczIM8xZoduN4qaUjV7QEPVUUW_LCT8EDUMv4,155
422
+ sqlmesh-0.210.1.dev3.dist-info/top_level.txt,sha256=RQ-33FPe2IgL0rgossAfJkCRtqslz9b7wFARqiWLC5Q,24
423
+ sqlmesh-0.210.1.dev3.dist-info/RECORD,,