sql-glider 0.1.8__tar.gz → 0.1.10__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.
- {sql_glider-0.1.8 → sql_glider-0.1.10}/PKG-INFO +1 -1
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/_version.py +2 -2
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/lineage/analyzer.py +28 -1
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/lineage/test_analyzer.py +103 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/.github/workflows/ci.yml +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/.github/workflows/publish.yml +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/.gitignore +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/.python-version +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/ARCHITECTURE.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/CLAUDE.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/LICENSE +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/README.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-05-column-level-lineage.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-05-reverse-lineage.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-06-config-file-support.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-06-graph-lineage.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-06-unify-single-multi-query.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-07-sample-data-model.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-07-sql-templating.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-08-tables-command.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-09-graph-query-paths.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-13-dissect-command.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2025-12-14-tables-pull-command.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2026-01-25-fix-union-lineage-chain.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/plans/2026-01-26-file-scoped-schema-context.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/pyproject.toml +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/README.md +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/business/expire_dim_customer.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/business/load_fact_orders.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/business/load_fact_payments.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/business/merge_dim_customer.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/business/merge_dim_product.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/business/update_dim_customer_metrics.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/complex/conditional_merge.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/complex/cte_insert.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/complex/multi_table_transform.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/dim_customer.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/dim_product.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/fact_orders.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/fact_payments.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/raw_addresses.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/raw_customers.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/raw_order_items.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/raw_orders.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/raw_payments.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/raw_products.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/stg_customers.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/stg_orders.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/stg_payments.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/ddl/stg_products.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/incremental/incr_fact_orders.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/incremental/incr_fact_payments.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/incremental/incr_pres_sales_summary.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/maintenance/delete_expired_customers.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/maintenance/update_product_status.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/presentation/load_pres_customer_360.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/presentation/load_pres_customer_cohort.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/presentation/load_pres_product_performance.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/presentation/load_pres_sales_summary.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/staging/load_stg_customers.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/staging/load_stg_orders.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/staging/load_stg_payments.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/staging/load_stg_products.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/sqlglider.toml.example +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/catalog/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/catalog/base.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/catalog/databricks.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/catalog/registry.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/cli.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/dissection/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/dissection/analyzer.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/dissection/formatters.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/dissection/models.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/global_models.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/graph/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/graph/builder.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/graph/merge.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/graph/models.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/graph/query.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/graph/serialization.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/lineage/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/lineage/formatters.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/templating/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/templating/base.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/templating/jinja.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/templating/registry.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/templating/variables.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/utils/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/utils/config.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/src/sqlglider/utils/file_utils.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/multi_file_queries/analytics_pipeline.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/multi_file_queries/analytics_pipeline_union_merge.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/multi_file_queries/customers.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/multi_file_queries/orders.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/multi_file_queries/reports.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/multi_file_queries/view_based_merge.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_cte.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_cte_query.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_cte_view_star.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_generated_column_query.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_multi.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_multi_query.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_single_query.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_subquery.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_tables.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_view.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_view_window_cte.sql +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/sample_manifest.csv +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/catalog/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/catalog/test_base.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/catalog/test_databricks.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/catalog/test_registry.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/dissection/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/dissection/test_analyzer.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/dissection/test_formatters.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/dissection/test_models.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/graph/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/graph/test_builder.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/graph/test_merge.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/graph/test_models.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/graph/test_query.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/graph/test_serialization.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/lineage/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/lineage/test_formatters.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/templating/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/templating/test_base.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/templating/test_jinja.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/templating/test_registry.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/templating/test_variables.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/test_cli.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/utils/__init__.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/utils/test_config.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/tests/sqlglider/utils/test_file_utils.py +0 -0
- {sql_glider-0.1.8 → sql_glider-0.1.10}/uv.lock +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: sql-glider
|
|
3
|
-
Version: 0.1.
|
|
3
|
+
Version: 0.1.10
|
|
4
4
|
Summary: SQL Utility Toolkit for better understanding, use, and governance of your queries in a native environment.
|
|
5
5
|
Project-URL: Homepage, https://github.com/rycowhi/sql-glider/
|
|
6
6
|
Project-URL: Repository, https://github.com/rycowhi/sql-glider/
|
|
@@ -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.1.
|
|
32
|
-
__version_tuple__ = version_tuple = (0, 1,
|
|
31
|
+
__version__ = version = '0.1.10'
|
|
32
|
+
__version_tuple__ = version_tuple = (0, 1, 10)
|
|
33
33
|
|
|
34
34
|
__commit_id__ = commit_id = None
|
|
@@ -615,6 +615,12 @@ class LineageAnalyzer:
|
|
|
615
615
|
if isinstance(target, exp.Table):
|
|
616
616
|
return (self._get_qualified_table_name(target), ObjectType.UNKNOWN)
|
|
617
617
|
|
|
618
|
+
# CACHE TABLE
|
|
619
|
+
elif isinstance(self.expr, exp.Cache):
|
|
620
|
+
target = self.expr.this
|
|
621
|
+
if isinstance(target, exp.Table):
|
|
622
|
+
return (self._get_qualified_table_name(target), ObjectType.TABLE)
|
|
623
|
+
|
|
618
624
|
# DELETE FROM table
|
|
619
625
|
elif isinstance(self.expr, exp.Delete):
|
|
620
626
|
target = self.expr.this
|
|
@@ -706,6 +712,10 @@ class LineageAnalyzer:
|
|
|
706
712
|
elif isinstance(self.expr, exp.Drop):
|
|
707
713
|
return table_node is self.expr.this
|
|
708
714
|
|
|
715
|
+
# For CACHE TABLE, the target is self.expr.this
|
|
716
|
+
elif isinstance(self.expr, exp.Cache):
|
|
717
|
+
return table_node is self.expr.this
|
|
718
|
+
|
|
709
719
|
return False
|
|
710
720
|
|
|
711
721
|
def _analyze_column_lineage_internal(
|
|
@@ -741,7 +751,12 @@ class LineageAnalyzer:
|
|
|
741
751
|
|
|
742
752
|
lineage_items = []
|
|
743
753
|
# Get SQL for current expression only (not full multi-query SQL)
|
|
744
|
-
|
|
754
|
+
# For CACHE TABLE, pass just the SELECT since sqlglot.lineage doesn't
|
|
755
|
+
# natively understand CACHE statements
|
|
756
|
+
if isinstance(self.expr, exp.Cache) and self.expr.expression:
|
|
757
|
+
current_query_sql = self.expr.expression.sql(dialect=self.dialect)
|
|
758
|
+
else:
|
|
759
|
+
current_query_sql = self.expr.sql(dialect=self.dialect)
|
|
745
760
|
|
|
746
761
|
for col in columns_to_analyze:
|
|
747
762
|
try:
|
|
@@ -889,6 +904,7 @@ class LineageAnalyzer:
|
|
|
889
904
|
"Drop": f"DROP {getattr(target_expr, 'kind', '')}".strip(),
|
|
890
905
|
"Alter": "ALTER",
|
|
891
906
|
"Truncate": "TRUNCATE",
|
|
907
|
+
"Cache": "CACHE TABLE",
|
|
892
908
|
"Command": "COMMAND",
|
|
893
909
|
}
|
|
894
910
|
|
|
@@ -943,6 +959,17 @@ class LineageAnalyzer:
|
|
|
943
959
|
):
|
|
944
960
|
return (target_name, select_node)
|
|
945
961
|
|
|
962
|
+
# Check for CACHE TABLE AS SELECT
|
|
963
|
+
elif isinstance(self.expr, exp.Cache):
|
|
964
|
+
target = self.expr.this
|
|
965
|
+
if isinstance(target, exp.Table):
|
|
966
|
+
target_name = self._get_qualified_table_name(target)
|
|
967
|
+
select_node = self.expr.expression
|
|
968
|
+
if isinstance(
|
|
969
|
+
select_node, (exp.Select, exp.Union, exp.Intersect, exp.Except)
|
|
970
|
+
):
|
|
971
|
+
return (target_name, select_node)
|
|
972
|
+
|
|
946
973
|
# Check for MERGE statement
|
|
947
974
|
elif isinstance(self.expr, exp.Merge):
|
|
948
975
|
target = self.expr.this
|
|
@@ -2820,3 +2820,106 @@ class TestSemiAntiJoinColumnResolution:
|
|
|
2820
2820
|
analyzer_semi = LineageAnalyzer(sql_semi, dialect="spark")
|
|
2821
2821
|
analyzer_semi.analyze_queries(level=AnalysisLevel.COLUMN)
|
|
2822
2822
|
assert set(analyzer_semi._file_schema["v3"].keys()) == {"a"}
|
|
2823
|
+
|
|
2824
|
+
|
|
2825
|
+
class TestCacheTableStatements:
|
|
2826
|
+
"""Tests for Spark SQL CACHE TABLE statement support."""
|
|
2827
|
+
|
|
2828
|
+
def test_cache_table_as_select_column_lineage(self):
|
|
2829
|
+
"""CACHE TABLE t AS SELECT should trace columns through to sources."""
|
|
2830
|
+
sql = """
|
|
2831
|
+
CACHE TABLE cached_customers AS
|
|
2832
|
+
SELECT customer_id, customer_name FROM customers
|
|
2833
|
+
"""
|
|
2834
|
+
analyzer = LineageAnalyzer(sql, dialect="spark")
|
|
2835
|
+
results = analyzer.analyze_queries(level=AnalysisLevel.COLUMN)
|
|
2836
|
+
|
|
2837
|
+
assert len(results) == 1
|
|
2838
|
+
items = {
|
|
2839
|
+
item.output_name: item.source_name for item in results[0].lineage_items
|
|
2840
|
+
}
|
|
2841
|
+
assert items["cached_customers.customer_id"] == "customers.customer_id"
|
|
2842
|
+
assert items["cached_customers.customer_name"] == "customers.customer_name"
|
|
2843
|
+
|
|
2844
|
+
def test_cache_lazy_table_column_lineage(self):
|
|
2845
|
+
"""CACHE LAZY TABLE should trace columns identically to CACHE TABLE."""
|
|
2846
|
+
sql = """
|
|
2847
|
+
CACHE LAZY TABLE cached_customers AS
|
|
2848
|
+
SELECT customer_id, customer_name FROM customers
|
|
2849
|
+
"""
|
|
2850
|
+
analyzer = LineageAnalyzer(sql, dialect="spark")
|
|
2851
|
+
results = analyzer.analyze_queries(level=AnalysisLevel.COLUMN)
|
|
2852
|
+
|
|
2853
|
+
assert len(results) == 1
|
|
2854
|
+
items = {
|
|
2855
|
+
item.output_name: item.source_name for item in results[0].lineage_items
|
|
2856
|
+
}
|
|
2857
|
+
assert items["cached_customers.customer_id"] == "customers.customer_id"
|
|
2858
|
+
assert items["cached_customers.customer_name"] == "customers.customer_name"
|
|
2859
|
+
|
|
2860
|
+
def test_cache_table_as_select_table_extraction(self):
|
|
2861
|
+
"""CACHE TABLE t AS SELECT should show cached_orders as OUTPUT table."""
|
|
2862
|
+
sql = """
|
|
2863
|
+
CACHE TABLE cached_orders AS
|
|
2864
|
+
SELECT order_id, total FROM orders
|
|
2865
|
+
"""
|
|
2866
|
+
analyzer = LineageAnalyzer(sql, dialect="spark")
|
|
2867
|
+
results = analyzer.analyze_tables()
|
|
2868
|
+
|
|
2869
|
+
assert len(results) == 1
|
|
2870
|
+
tables_by_name = {t.name: t for t in results[0].tables}
|
|
2871
|
+
|
|
2872
|
+
assert "cached_orders" in tables_by_name
|
|
2873
|
+
assert tables_by_name["cached_orders"].usage.value == "OUTPUT"
|
|
2874
|
+
assert tables_by_name["cached_orders"].object_type.value == "TABLE"
|
|
2875
|
+
|
|
2876
|
+
assert "orders" in tables_by_name
|
|
2877
|
+
assert tables_by_name["orders"].usage.value == "INPUT"
|
|
2878
|
+
|
|
2879
|
+
def test_cache_table_as_select_with_join(self):
|
|
2880
|
+
"""CACHE TABLE with a JOIN query should trace all sources."""
|
|
2881
|
+
sql = """
|
|
2882
|
+
CACHE TABLE summary AS
|
|
2883
|
+
SELECT c.customer_id, o.total
|
|
2884
|
+
FROM customers c
|
|
2885
|
+
JOIN orders o ON c.id = o.customer_id
|
|
2886
|
+
"""
|
|
2887
|
+
analyzer = LineageAnalyzer(sql, dialect="spark")
|
|
2888
|
+
results = analyzer.analyze_tables()
|
|
2889
|
+
|
|
2890
|
+
assert len(results) == 1
|
|
2891
|
+
tables_by_name = {t.name: t for t in results[0].tables}
|
|
2892
|
+
|
|
2893
|
+
assert "summary" in tables_by_name
|
|
2894
|
+
assert tables_by_name["summary"].usage.value == "OUTPUT"
|
|
2895
|
+
assert "customers" in tables_by_name
|
|
2896
|
+
assert tables_by_name["customers"].usage.value == "INPUT"
|
|
2897
|
+
assert "orders" in tables_by_name
|
|
2898
|
+
assert tables_by_name["orders"].usage.value == "INPUT"
|
|
2899
|
+
|
|
2900
|
+
def test_bare_cache_table_is_skipped(self):
|
|
2901
|
+
"""CACHE TABLE t (without AS SELECT) should be skipped."""
|
|
2902
|
+
sql = "CACHE TABLE my_table"
|
|
2903
|
+
analyzer = LineageAnalyzer(sql, dialect="spark")
|
|
2904
|
+
results = analyzer.analyze_queries(level=AnalysisLevel.COLUMN)
|
|
2905
|
+
|
|
2906
|
+
assert len(results) == 0
|
|
2907
|
+
skipped = analyzer.skipped_queries
|
|
2908
|
+
assert len(skipped) == 1
|
|
2909
|
+
assert "CACHE" in skipped[0].statement_type
|
|
2910
|
+
|
|
2911
|
+
def test_cache_table_in_multi_query(self):
|
|
2912
|
+
"""CACHE TABLE should work alongside other statements in multi-query files."""
|
|
2913
|
+
sql = """
|
|
2914
|
+
SELECT id FROM users;
|
|
2915
|
+
CACHE TABLE cached_orders AS SELECT order_id FROM orders;
|
|
2916
|
+
DELETE FROM old_data;
|
|
2917
|
+
"""
|
|
2918
|
+
analyzer = LineageAnalyzer(sql, dialect="spark")
|
|
2919
|
+
results = analyzer.analyze_queries(level=AnalysisLevel.COLUMN)
|
|
2920
|
+
|
|
2921
|
+
# SELECT and CACHE TABLE should produce results; DELETE is skipped
|
|
2922
|
+
assert len(results) == 2
|
|
2923
|
+
skipped = analyzer.skipped_queries
|
|
2924
|
+
assert len(skipped) == 1
|
|
2925
|
+
assert "DELETE" in skipped[0].statement_type
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/business/update_dim_customer_metrics.sql
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/incremental/incr_pres_sales_summary.sql
RENAMED
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/maintenance/delete_expired_customers.sql
RENAMED
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/maintenance/update_product_status.sql
RENAMED
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/presentation/load_pres_customer_360.sql
RENAMED
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/presentation/load_pres_customer_cohort.sql
RENAMED
|
File without changes
|
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/sample_data_model/presentation/load_pres_sales_summary.sql
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/multi_file_queries/analytics_pipeline.sql
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/multi_file_queries/view_based_merge.sql
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_cte_view_star.sql
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_single_query.sql
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{sql_glider-0.1.8 → sql_glider-0.1.10}/tests/fixtures/original_queries/test_view_window_cte.sql
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|