sql-diff-explainer 0.1.3__tar.gz → 0.1.5__tar.gz

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.
Files changed (31) hide show
  1. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/PKG-INFO +130 -7
  2. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/README.md +129 -6
  3. sql_diff_explainer-0.1.5/examples/cte_lineage_after.sql +7 -0
  4. sql_diff_explainer-0.1.5/examples/cte_lineage_before.sql +7 -0
  5. sql_diff_explainer-0.1.5/examples/migration.sql +4 -0
  6. sql_diff_explainer-0.1.5/examples/output_contract_after.sql +4 -0
  7. sql_diff_explainer-0.1.5/examples/output_contract_before.sql +5 -0
  8. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/pyproject.toml +1 -1
  9. sql_diff_explainer-0.1.5/src/sql_diff_explainer/__init__.py +65 -0
  10. sql_diff_explainer-0.1.5/src/sql_diff_explainer/analysis.py +804 -0
  11. sql_diff_explainer-0.1.5/src/sql_diff_explainer/cli.py +257 -0
  12. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/src/sql_diff_explainer/core.py +235 -3
  13. sql_diff_explainer-0.1.5/src/sql_diff_explainer/reports.py +412 -0
  14. sql_diff_explainer-0.1.5/tests/test_core.py +794 -0
  15. sql_diff_explainer-0.1.3/src/sql_diff_explainer/__init__.py +0 -35
  16. sql_diff_explainer-0.1.3/src/sql_diff_explainer/cli.py +0 -127
  17. sql_diff_explainer-0.1.3/src/sql_diff_explainer/reports.py +0 -198
  18. sql_diff_explainer-0.1.3/tests/test_core.py +0 -390
  19. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/.github/workflows/ci.yml +0 -0
  20. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/.gitignore +0 -0
  21. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/LICENSE +0 -0
  22. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/after.sql +0 -0
  23. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/aggregation_after.sql +0 -0
  24. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/aggregation_before.sql +0 -0
  25. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/before.sql +0 -0
  26. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/distinct_after.sql +0 -0
  27. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/distinct_before.sql +0 -0
  28. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/filter_after.sql +0 -0
  29. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/filter_before.sql +0 -0
  30. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/join_after.sql +0 -0
  31. {sql_diff_explainer-0.1.3 → sql_diff_explainer-0.1.5}/examples/join_before.sql +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.5
2
2
  Name: sql-diff-explainer
3
- Version: 0.1.3
3
+ Version: 0.1.5
4
4
  Summary: Explain SQL schema and migration differences
5
5
  Author: zmodz1010
6
6
  License: MIT
@@ -20,7 +20,7 @@ SQL Diff Explainer compares the structure of two `SELECT` queries and returns
20
20
  the changes with a static risk signal, so reviews focus on query behavior rather
21
21
  than formatting.
22
22
 
23
- [![PyPI version](https://img.shields.io/pypi/v/sql-diff-explainer)](https://pypi.org/project/sql-diff-explainer/)
23
+ [![PyPI version](https://img.shields.io/pypi/v/sql-diff-explainer?cacheSeconds=60)](https://pypi.org/project/sql-diff-explainer/)
24
24
  [![Python 3.10+](https://img.shields.io/badge/python-3.10%2B-blue)](https://pypi.org/project/sql-diff-explainer/)
25
25
  [![License: MIT](https://img.shields.io/pypi/l/sql-diff-explainer)](LICENSE)
26
26
 
@@ -29,7 +29,9 @@ than formatting.
29
29
  - [Quick start](#quick-start)
30
30
  - [Command-line usage](#command-line-usage)
31
31
  - [Directory comparison](#directory-comparison)
32
+ - [Git-aware pull-request comparison](#git-aware-pull-request-comparison)
32
33
  - [SARIF and HTML reports](#sarif-and-html-reports)
34
+ - [Additional SQL QA analyses](#additional-sql-qa-analyses)
33
35
  - [What it compares](#what-it-compares)
34
36
  - [Use cases](#use-cases)
35
37
  - [Scope and limitations](#scope-and-limitations)
@@ -113,8 +115,15 @@ Try the runnable before/after pairs in [`examples/`](examples/):
113
115
  sql-diff-explainer examples/filter_before.sql examples/filter_after.sql --format json
114
116
  sql-diff-explainer examples/aggregation_before.sql examples/aggregation_after.sql
115
117
  sql-diff-explainer examples/distinct_before.sql examples/distinct_after.sql
118
+ sql-diff-explainer examples/cte_lineage_before.sql examples/cte_lineage_after.sql --format json
119
+ sql-diff-explainer examples/output_contract_before.sql examples/output_contract_after.sql --format json
120
+ sql-diff-explainer --analyze-migration examples/migration.sql --format json
116
121
  ```
117
122
 
123
+ `--analyze-migration FILE` accepts multi-statement migration scripts and emits
124
+ text or JSON. It supports common `ALTER TABLE` column operations; SARIF and
125
+ HTML formats are not available for this separate migration mode.
126
+
118
127
  ### Directory comparison
119
128
 
120
129
  Compare two directory trees recursively. SQL files are paired by their exact
@@ -141,6 +150,59 @@ result = compare_sql_directories("models/main", "models/review")
141
150
  print(result.to_dict())
142
151
  ```
143
152
 
153
+ ### Git-aware pull-request comparison
154
+
155
+ Compare SQL paths Git reports as changed between a base ref and the current
156
+ worktree. Modified files and SQL-to-SQL renames are compared semantically;
157
+ added or removed SQL files are reported explicitly as high risk. Untracked
158
+ files are not included. The base can be a branch, tag, or commit:
159
+
160
+ ```console
161
+ sql-diff-explainer --git-base origin/main --format json
162
+ sql-diff-explainer --git-base "$GITHUB_BASE_REF" --format sarif --output sql-diff.sarif
163
+ sql-diff-explainer --git-base origin/main --fail-on-risk high
164
+ ```
165
+
166
+ For GitHub Actions, fetch the base history and use the pull request's base
167
+ commit. This example checks out the pull-request worktree, installs this
168
+ repository's source (so the CLI includes the feature), emits SARIF, and fails
169
+ the job on high-risk changes:
170
+
171
+ ```yaml
172
+ name: SQL review
173
+ on:
174
+ pull_request:
175
+
176
+ jobs:
177
+ sql-diff:
178
+ runs-on: ubuntu-latest
179
+ steps:
180
+ - uses: actions/checkout@v4
181
+ with:
182
+ fetch-depth: 0
183
+ - uses: actions/setup-python@v5
184
+ with:
185
+ python-version: "3.12"
186
+ - run: python -m pip install .
187
+ - name: Analyze changed SQL
188
+ run: >-
189
+ sql-diff-explainer
190
+ --git-base "${{ github.event.pull_request.base.sha }}"
191
+ --format sarif
192
+ --output sql-diff.sarif
193
+ --fail-on-risk high
194
+ - name: Upload SQL findings
195
+ if: always() && hashFiles('sql-diff.sarif') != ''
196
+ uses: github/codeql-action/upload-sarif@v3
197
+ with:
198
+ sarif_file: sql-diff.sarif
199
+ ```
200
+
201
+ An unresolved base ref, Git failure, unreadable SQL, or invalid SQL exits with
202
+ status `2` and a diagnostic. Renames appear in every report; a rename does not
203
+ raise risk by itself, while semantic changes in its content retain their
204
+ normal risk level.
205
+
144
206
  ### SARIF and HTML reports
145
207
 
146
208
  Emit SARIF 2.1.0 results for GitHub code scanning integrations, or generate a
@@ -158,6 +220,63 @@ and file paths. Python callers can use `to_sarif(result)` or
158
220
  `render_html_report(result)` with either `SQLDiffResult` or
159
221
  `SQLDirectoryDiffResult`.
160
222
 
223
+ ## Additional SQL QA analyses
224
+
225
+ Query comparisons include three static QA views in `SQLDiffResult` and JSON
226
+ output:
227
+
228
+ - **CTE lineage** (`lineage`) traces explicit output expressions through
229
+ non-recursive CTE chains to their source columns. Changed sources or
230
+ expressions are also included in `changes` and the risk summary. Lineage
231
+ requires explicit projections, aliases for calculated expressions, and
232
+ direct table/CTE sources; recursive CTEs, wildcard projections, nested
233
+ subqueries, CTE column alias lists, and ambiguous unqualified columns are
234
+ reported as unsupported.
235
+ - **Output-schema contracts** (`schema_contract`) report added, removed,
236
+ renamed, reordered, changed, and supported type-changed output columns.
237
+ Types are inferred only for explicit casts and aliased literals; column types
238
+ that require a database catalog remain unknown. Wildcard projections, unnamed
239
+ expressions, and set operations are reported as unsupported.
240
+ - **Validation suggestions** (`validation_checks`) provide a checklist and,
241
+ when the before/after output columns are compatible, SQL for unmatched-row
242
+ and duplicate checks. The unmatched-row query uses `EXCEPT`; adapt it for
243
+ dialects that use different set-difference syntax. These checks are
244
+ suggestions only: SQL Diff Explainer never connects to a database or
245
+ executes generated SQL.
246
+
247
+ Use the analysis helpers directly when needed:
248
+
249
+ ```python
250
+ from sql_diff_explainer import (
251
+ analyze_migration,
252
+ compare_output_schema,
253
+ trace_cte_lineage,
254
+ )
255
+
256
+ before_sql = """
257
+ WITH totals AS (SELECT customer_id, amount FROM sales)
258
+ SELECT customer_id, amount FROM totals
259
+ """
260
+ after_sql = """
261
+ WITH totals AS (SELECT customer_id, net_amount AS amount FROM sales)
262
+ SELECT customer_id, amount FROM totals
263
+ """
264
+
265
+ lineage = trace_cte_lineage(before_sql, after_sql)
266
+ contract = compare_output_schema(before_sql, after_sql)
267
+ migration = analyze_migration(
268
+ "ALTER TABLE users ADD COLUMN email TEXT;"
269
+ "ALTER TABLE users RENAME COLUMN old_email TO email_address;"
270
+ )
271
+ print(lineage.to_dict(), contract.to_dict(), migration.to_dict())
272
+ ```
273
+
274
+ Migration analysis recognizes `ADD COLUMN`, `DROP COLUMN`, `RENAME COLUMN`,
275
+ `ALTER COLUMN ... TYPE`, and `ALTER COLUMN ... SET/DROP NOT NULL`. Other
276
+ statements and ALTER actions are listed as unsupported rather than being
277
+ silently treated as analyzed. Use `--analyze-migration` for a file or
278
+ `analyze_migration(sql)` from Python.
279
+
161
280
  ## What it compares
162
281
 
163
282
  The analyzer compares supported `SELECT` query features and reports additions,
@@ -171,6 +290,7 @@ removals, or changes with a low, medium, or high risk classification:
171
290
  | Aggregation | Aggregate functions and `GROUP BY` expressions |
172
291
  | Ordering and pagination | `ORDER BY`, `LIMIT`, and `OFFSET` |
173
292
  | Duplicate handling | `DISTINCT` added or removed |
293
+ | Output schema | Result-column additions, removals, renames, ordering, and known type changes |
174
294
 
175
295
  Join or filter changes can alter which rows qualify; grouping or aggregation
176
296
  changes can change a metric's meaning or result grain; and pagination changes
@@ -190,11 +310,14 @@ can affect which rows downstream consumers receive.
190
310
  This is static analysis, not a SQL execution engine or correctness proof. It
191
311
  does not connect to a database, validate schemas or permissions, estimate query
192
312
  plans or cost, inspect table statistics or null rates, or decide whether a
193
- business metric is correct. It compares supported query structure; it does not
194
- analyze a multi-statement migration file or guarantee complete semantic
195
- equivalence across SQL dialects. Risk levels are review signals, not
196
- predictions. Pair the report with warehouse tests, representative row-count
197
- checks, query-plan review, and domain-owner input.
313
+ business metric is correct. Output-column types that require database metadata
314
+ are unknown. CTE lineage and query validation SQL support only the documented
315
+ static cases, and migration analysis recognizes only the listed `ALTER TABLE`
316
+ operations. Generated validation SQL is not executed and may need dialect
317
+ adaptation. The analyzer does not guarantee complete semantic equivalence
318
+ across SQL dialects. Risk levels are review signals, not predictions. Pair the
319
+ report with warehouse tests, representative row-count checks, query-plan
320
+ review, and domain-owner input.
198
321
 
199
322
  ## Development
200
323
 
@@ -6,7 +6,7 @@ SQL Diff Explainer compares the structure of two `SELECT` queries and returns
6
6
  the changes with a static risk signal, so reviews focus on query behavior rather
7
7
  than formatting.
8
8
 
9
- [![PyPI version](https://img.shields.io/pypi/v/sql-diff-explainer)](https://pypi.org/project/sql-diff-explainer/)
9
+ [![PyPI version](https://img.shields.io/pypi/v/sql-diff-explainer?cacheSeconds=60)](https://pypi.org/project/sql-diff-explainer/)
10
10
  [![Python 3.10+](https://img.shields.io/badge/python-3.10%2B-blue)](https://pypi.org/project/sql-diff-explainer/)
11
11
  [![License: MIT](https://img.shields.io/pypi/l/sql-diff-explainer)](LICENSE)
12
12
 
@@ -15,7 +15,9 @@ than formatting.
15
15
  - [Quick start](#quick-start)
16
16
  - [Command-line usage](#command-line-usage)
17
17
  - [Directory comparison](#directory-comparison)
18
+ - [Git-aware pull-request comparison](#git-aware-pull-request-comparison)
18
19
  - [SARIF and HTML reports](#sarif-and-html-reports)
20
+ - [Additional SQL QA analyses](#additional-sql-qa-analyses)
19
21
  - [What it compares](#what-it-compares)
20
22
  - [Use cases](#use-cases)
21
23
  - [Scope and limitations](#scope-and-limitations)
@@ -99,8 +101,15 @@ Try the runnable before/after pairs in [`examples/`](examples/):
99
101
  sql-diff-explainer examples/filter_before.sql examples/filter_after.sql --format json
100
102
  sql-diff-explainer examples/aggregation_before.sql examples/aggregation_after.sql
101
103
  sql-diff-explainer examples/distinct_before.sql examples/distinct_after.sql
104
+ sql-diff-explainer examples/cte_lineage_before.sql examples/cte_lineage_after.sql --format json
105
+ sql-diff-explainer examples/output_contract_before.sql examples/output_contract_after.sql --format json
106
+ sql-diff-explainer --analyze-migration examples/migration.sql --format json
102
107
  ```
103
108
 
109
+ `--analyze-migration FILE` accepts multi-statement migration scripts and emits
110
+ text or JSON. It supports common `ALTER TABLE` column operations; SARIF and
111
+ HTML formats are not available for this separate migration mode.
112
+
104
113
  ### Directory comparison
105
114
 
106
115
  Compare two directory trees recursively. SQL files are paired by their exact
@@ -127,6 +136,59 @@ result = compare_sql_directories("models/main", "models/review")
127
136
  print(result.to_dict())
128
137
  ```
129
138
 
139
+ ### Git-aware pull-request comparison
140
+
141
+ Compare SQL paths Git reports as changed between a base ref and the current
142
+ worktree. Modified files and SQL-to-SQL renames are compared semantically;
143
+ added or removed SQL files are reported explicitly as high risk. Untracked
144
+ files are not included. The base can be a branch, tag, or commit:
145
+
146
+ ```console
147
+ sql-diff-explainer --git-base origin/main --format json
148
+ sql-diff-explainer --git-base "$GITHUB_BASE_REF" --format sarif --output sql-diff.sarif
149
+ sql-diff-explainer --git-base origin/main --fail-on-risk high
150
+ ```
151
+
152
+ For GitHub Actions, fetch the base history and use the pull request's base
153
+ commit. This example checks out the pull-request worktree, installs this
154
+ repository's source (so the CLI includes the feature), emits SARIF, and fails
155
+ the job on high-risk changes:
156
+
157
+ ```yaml
158
+ name: SQL review
159
+ on:
160
+ pull_request:
161
+
162
+ jobs:
163
+ sql-diff:
164
+ runs-on: ubuntu-latest
165
+ steps:
166
+ - uses: actions/checkout@v4
167
+ with:
168
+ fetch-depth: 0
169
+ - uses: actions/setup-python@v5
170
+ with:
171
+ python-version: "3.12"
172
+ - run: python -m pip install .
173
+ - name: Analyze changed SQL
174
+ run: >-
175
+ sql-diff-explainer
176
+ --git-base "${{ github.event.pull_request.base.sha }}"
177
+ --format sarif
178
+ --output sql-diff.sarif
179
+ --fail-on-risk high
180
+ - name: Upload SQL findings
181
+ if: always() && hashFiles('sql-diff.sarif') != ''
182
+ uses: github/codeql-action/upload-sarif@v3
183
+ with:
184
+ sarif_file: sql-diff.sarif
185
+ ```
186
+
187
+ An unresolved base ref, Git failure, unreadable SQL, or invalid SQL exits with
188
+ status `2` and a diagnostic. Renames appear in every report; a rename does not
189
+ raise risk by itself, while semantic changes in its content retain their
190
+ normal risk level.
191
+
130
192
  ### SARIF and HTML reports
131
193
 
132
194
  Emit SARIF 2.1.0 results for GitHub code scanning integrations, or generate a
@@ -144,6 +206,63 @@ and file paths. Python callers can use `to_sarif(result)` or
144
206
  `render_html_report(result)` with either `SQLDiffResult` or
145
207
  `SQLDirectoryDiffResult`.
146
208
 
209
+ ## Additional SQL QA analyses
210
+
211
+ Query comparisons include three static QA views in `SQLDiffResult` and JSON
212
+ output:
213
+
214
+ - **CTE lineage** (`lineage`) traces explicit output expressions through
215
+ non-recursive CTE chains to their source columns. Changed sources or
216
+ expressions are also included in `changes` and the risk summary. Lineage
217
+ requires explicit projections, aliases for calculated expressions, and
218
+ direct table/CTE sources; recursive CTEs, wildcard projections, nested
219
+ subqueries, CTE column alias lists, and ambiguous unqualified columns are
220
+ reported as unsupported.
221
+ - **Output-schema contracts** (`schema_contract`) report added, removed,
222
+ renamed, reordered, changed, and supported type-changed output columns.
223
+ Types are inferred only for explicit casts and aliased literals; column types
224
+ that require a database catalog remain unknown. Wildcard projections, unnamed
225
+ expressions, and set operations are reported as unsupported.
226
+ - **Validation suggestions** (`validation_checks`) provide a checklist and,
227
+ when the before/after output columns are compatible, SQL for unmatched-row
228
+ and duplicate checks. The unmatched-row query uses `EXCEPT`; adapt it for
229
+ dialects that use different set-difference syntax. These checks are
230
+ suggestions only: SQL Diff Explainer never connects to a database or
231
+ executes generated SQL.
232
+
233
+ Use the analysis helpers directly when needed:
234
+
235
+ ```python
236
+ from sql_diff_explainer import (
237
+ analyze_migration,
238
+ compare_output_schema,
239
+ trace_cte_lineage,
240
+ )
241
+
242
+ before_sql = """
243
+ WITH totals AS (SELECT customer_id, amount FROM sales)
244
+ SELECT customer_id, amount FROM totals
245
+ """
246
+ after_sql = """
247
+ WITH totals AS (SELECT customer_id, net_amount AS amount FROM sales)
248
+ SELECT customer_id, amount FROM totals
249
+ """
250
+
251
+ lineage = trace_cte_lineage(before_sql, after_sql)
252
+ contract = compare_output_schema(before_sql, after_sql)
253
+ migration = analyze_migration(
254
+ "ALTER TABLE users ADD COLUMN email TEXT;"
255
+ "ALTER TABLE users RENAME COLUMN old_email TO email_address;"
256
+ )
257
+ print(lineage.to_dict(), contract.to_dict(), migration.to_dict())
258
+ ```
259
+
260
+ Migration analysis recognizes `ADD COLUMN`, `DROP COLUMN`, `RENAME COLUMN`,
261
+ `ALTER COLUMN ... TYPE`, and `ALTER COLUMN ... SET/DROP NOT NULL`. Other
262
+ statements and ALTER actions are listed as unsupported rather than being
263
+ silently treated as analyzed. Use `--analyze-migration` for a file or
264
+ `analyze_migration(sql)` from Python.
265
+
147
266
  ## What it compares
148
267
 
149
268
  The analyzer compares supported `SELECT` query features and reports additions,
@@ -157,6 +276,7 @@ removals, or changes with a low, medium, or high risk classification:
157
276
  | Aggregation | Aggregate functions and `GROUP BY` expressions |
158
277
  | Ordering and pagination | `ORDER BY`, `LIMIT`, and `OFFSET` |
159
278
  | Duplicate handling | `DISTINCT` added or removed |
279
+ | Output schema | Result-column additions, removals, renames, ordering, and known type changes |
160
280
 
161
281
  Join or filter changes can alter which rows qualify; grouping or aggregation
162
282
  changes can change a metric's meaning or result grain; and pagination changes
@@ -176,11 +296,14 @@ can affect which rows downstream consumers receive.
176
296
  This is static analysis, not a SQL execution engine or correctness proof. It
177
297
  does not connect to a database, validate schemas or permissions, estimate query
178
298
  plans or cost, inspect table statistics or null rates, or decide whether a
179
- business metric is correct. It compares supported query structure; it does not
180
- analyze a multi-statement migration file or guarantee complete semantic
181
- equivalence across SQL dialects. Risk levels are review signals, not
182
- predictions. Pair the report with warehouse tests, representative row-count
183
- checks, query-plan review, and domain-owner input.
299
+ business metric is correct. Output-column types that require database metadata
300
+ are unknown. CTE lineage and query validation SQL support only the documented
301
+ static cases, and migration analysis recognizes only the listed `ALTER TABLE`
302
+ operations. Generated validation SQL is not executed and may need dialect
303
+ adaptation. The analyzer does not guarantee complete semantic equivalence
304
+ across SQL dialects. Risk levels are review signals, not predictions. Pair the
305
+ report with warehouse tests, representative row-count checks, query-plan
306
+ review, and domain-owner input.
184
307
 
185
308
  ## Development
186
309
 
@@ -0,0 +1,7 @@
1
+ WITH order_totals AS (
2
+ SELECT customer_id, SUM(net_amount) AS total_amount
3
+ FROM orders
4
+ GROUP BY customer_id
5
+ )
6
+ SELECT customer_id, total_amount
7
+ FROM order_totals
@@ -0,0 +1,7 @@
1
+ WITH order_totals AS (
2
+ SELECT customer_id, SUM(amount) AS total_amount
3
+ FROM orders
4
+ GROUP BY customer_id
5
+ )
6
+ SELECT customer_id, total_amount
7
+ FROM order_totals
@@ -0,0 +1,4 @@
1
+ ALTER TABLE customers ADD COLUMN email TEXT;
2
+ ALTER TABLE customers RENAME COLUMN name TO display_name;
3
+ ALTER TABLE customers ALTER COLUMN customer_id TYPE BIGINT;
4
+ ALTER TABLE customers DROP COLUMN legacy_status;
@@ -0,0 +1,4 @@
1
+ SELECT
2
+ CAST(customer_id AS BIGINT) AS customer_id,
3
+ name AS display_name
4
+ FROM customers
@@ -0,0 +1,5 @@
1
+ SELECT
2
+ CAST(customer_id AS INT) AS customer_id,
3
+ name AS customer_name,
4
+ legacy_status
5
+ FROM customers
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
4
4
 
5
5
  [project]
6
6
  name = "sql-diff-explainer"
7
- version = "0.1.3"
7
+ version = "0.1.5"
8
8
  description = "Explain SQL schema and migration differences"
9
9
  readme = "README.md"
10
10
  requires-python = ">=3.10"
@@ -0,0 +1,65 @@
1
+ """Tools for explaining SQL query differences."""
2
+
3
+ from .analysis import (
4
+ CTELineageDiff,
5
+ LineageChange,
6
+ MigrationAnalysisResult,
7
+ MigrationOperation,
8
+ OutputLineage,
9
+ SchemaChange,
10
+ SchemaColumn,
11
+ SchemaContractDiff,
12
+ UnsupportedMigrationStatement,
13
+ ValidationSuggestion,
14
+ analyze_migration,
15
+ compare_output_schema,
16
+ trace_cte_lineage,
17
+ )
18
+ from .core import (
19
+ SQLChange,
20
+ SQLDiffError,
21
+ SQLDiffResult,
22
+ SQLDirectoryDiffResult,
23
+ SQLFileDiff,
24
+ SqlglotParser,
25
+ SQLParseError,
26
+ SQLParser,
27
+ UnsupportedSQL,
28
+ compare_sql_directories,
29
+ compare_sql_git,
30
+ explain_diff,
31
+ explain_sql_change,
32
+ )
33
+ from .reports import render_html_report, to_sarif
34
+
35
+ __all__ = [
36
+ "CTELineageDiff",
37
+ "LineageChange",
38
+ "MigrationAnalysisResult",
39
+ "MigrationOperation",
40
+ "OutputLineage",
41
+ "SchemaChange",
42
+ "SchemaColumn",
43
+ "SchemaContractDiff",
44
+ "SQLChange",
45
+ "SQLDirectoryDiffResult",
46
+ "SQLDiffError",
47
+ "SQLDiffResult",
48
+ "SQLFileDiff",
49
+ "SQLParseError",
50
+ "SQLParser",
51
+ "SqlglotParser",
52
+ "UnsupportedSQL",
53
+ "UnsupportedMigrationStatement",
54
+ "ValidationSuggestion",
55
+ "analyze_migration",
56
+ "compare_sql_directories",
57
+ "compare_sql_git",
58
+ "compare_output_schema",
59
+ "explain_diff",
60
+ "explain_sql_change",
61
+ "render_html_report",
62
+ "trace_cte_lineage",
63
+ "to_sarif",
64
+ ]
65
+ __version__ = "0.1.5"