databricks-labs-lakebridge 0.10.5__tar.gz → 0.10.7__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.
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/PKG-INFO +1 -1
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/__about__.py +1 -1
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/analyzer/lakebridge_analyzer.py +95 -0
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/base_install.py +34 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/cli.py +57 -72
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/config.py +1 -1
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/contexts/application.py +11 -4
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/deployment/dashboard.py +2 -1
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/deployment/installation.py +11 -11
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/deployment/job.py +2 -2
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/helpers/file_utils.py +36 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/install.py +228 -278
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/compare.py +70 -33
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/connectors/data_source.py +19 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/connectors/databricks.py +11 -1
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/connectors/dialect_utils.py +126 -0
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/connectors/models.py +7 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/connectors/oracle.py +11 -1
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/connectors/snowflake.py +14 -2
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/connectors/tsql.py +27 -2
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/constants.py +4 -3
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/execute.py +119 -0
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/normalize_recon_config_service.py +133 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/query_builder/base.py +3 -7
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/recon_config.py +3 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/recon_output_config.py +2 -1
- databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/reconcile/execute.py → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/reconciliation.py +48 -460
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/schema_compare.py +26 -19
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/trigger_recon_aggregate_service.py +98 -0
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/trigger_recon_service.py +253 -0
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/utils.py +38 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/lsp/lsp_engine.py +48 -63
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/transpiler/repository.py +123 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/sqlglot/dialect_utils.py +2 -0
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/transpiler/sqlglot/parsers/__init__.py +0 -0
- databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/transpiler/transpile_engine.py +29 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/pyproject.toml +4 -2
- databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/base_install.py +0 -13
- databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/transpiler/transpile_engine.py +0 -47
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/.gitignore +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/LICENSE +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/NOTICE +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/README.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/connections → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/analyzer}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/assessments/configure_assessment.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/assessments/pipeline.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/assessments/profiler_config.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/contexts → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/connections}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/connections/credential_manager.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/connections/database_manager.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/connections/env_getter.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/coverage → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/contexts}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/deployment → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/coverage}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/coverage/commons.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/coverage/lakebridge_snow_transpilation_coverage.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/coverage/local_report.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/coverage/sqlglot_snow_transpilation_coverage.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/coverage/sqlglot_tsql_transpilation_coverage.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/helpers → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/deployment}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/deployment/configurator.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/deployment/recon.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/deployment/table.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/deployment/upgrade_common.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/discovery/table.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/discovery/table_definition.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/discovery/tsql_table_definition.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/errors/exceptions.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/intermediate → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/helpers}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/helpers/db_sql.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/helpers/execution_time.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/helpers/metastore.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/helpers/recon_config_utils.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/helpers/string_utils.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/helpers/telemetry_utils.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/helpers/validation.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/reconcile → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/intermediate}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/intermediate/dag.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/intermediate/engine_adapter.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/intermediate/root_tables.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/jvmproxy.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/lineage.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/reconcile/connectors → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/reconcile/query_builder → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/connectors}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/connectors/jdbc_reader.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/connectors/secrets.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/connectors/source_adapter.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/exception.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/resources → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/reconcile/query_builder}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/query_builder/aggregate_query.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/query_builder/count_query.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/query_builder/expression_generator.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/query_builder/hash_query.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/query_builder/sampling_query.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/query_builder/threshold_query.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/recon_capture.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/runner.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/reconcile/sampler.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/resources/reconcile → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/resources}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/config/credentials.yml +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/resources/reconcile/dashboards → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/resources/reconcile}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/resources/reconcile/queries → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/resources/reconcile/dashboards}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/00_0_aggregate_recon_header.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/01_0_recon_id.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/01_1_executed_by.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/01_2_started_at.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/02_0_source_type.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/02_1_source_table.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/02_2_target_table.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/04_0_aggregate_summary_table.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/05_0_aggregate_recon_drilldown_header.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/06_0_recon_id.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/06_1_category.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/06_2_aggregate_type.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/07_0_target_table.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/07_1_source_table.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/08_0_aggregate_details_table.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/09_0_aggregate_missing_mismatch_header.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/10_0_aggr_mismatched_records.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/11_0_aggr_missing_in_databricks.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/11_1_aggr_missing_in_source.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/aggregate_reconciliation_metrics/dashboard.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/00_0_recon_main.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/01_0_recon_id.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/01_1_report_type.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/01_2_executed_by.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/02_0_source_type.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/02_1_source_table.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/02_2_target_table.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/03_0_started_at.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/05_0_summary_table.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/06_0_schema_comparison_header.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/07_0_schema_details_table.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/08_0_drill_down_header.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/09_0_recon_id.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/09_1_category.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/10_0_target_table.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/10_1_source_table.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/11_0_recon_details_pivot.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/12_0_daily_data_validation_issue_header.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/13_0_success_fail_.filter.yml +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/14_0_failed_recon_ids.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/15_0_total_failed_runs.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/15_1_failed_targets.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/15_2_successful_targets.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/16_0_missing_mismatch_header.md +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/17_0_mismatched_records.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/17_1_threshold_mismatches.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/18_0_missing_in_databricks.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/18_1_missing_in_source.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/dashboards/reconciliation_metrics/dashboard.yml +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/resources/reconcile/queries/installation → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/resources/reconcile/queries}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/transpiler → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/resources/reconcile/queries/installation}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/queries/installation/aggregate_details.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/queries/installation/aggregate_metrics.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/queries/installation/aggregate_rules.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/queries/installation/details.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/queries/installation/main.sql +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/resources/reconcile/queries/installation/metrics.sql +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/transpiler/lsp → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/transpiler}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/execute.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/transpiler/sqlglot → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/transpiler/lsp}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/transpiler/sqlglot/generator → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/transpiler/sqlglot}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5/databricks/labs/lakebridge/transpiler/sqlglot/parsers → databricks_labs_lakebridge-0.10.7/databricks/labs/lakebridge/transpiler/sqlglot/generator}/__init__.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/sqlglot/generator/databricks.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/sqlglot/lca_utils.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/sqlglot/local_expression.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/sqlglot/parsers/oracle.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/sqlglot/parsers/presto.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/sqlglot/parsers/snowflake.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/sqlglot/sqlglot_engine.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/transpiler/transpile_status.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/uninstall.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/upgrades/v0.4.0_add_main_table_operation_name_column.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/databricks/labs/lakebridge/upgrades/v0.6.0_alter_metrics_datatype.py +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/docs/lakebridge/src/components/Button.tsx +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/docs/lakebridge/src/components/ReconcileTabs.tsx +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/docs/lakebridge/src/css/custom.css +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/docs/lakebridge/src/css/table.css +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/docs/lakebridge/src/pages/index.tsx +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/docs/lakebridge/src/theme/DocSidebarItems/index.tsx +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/docs/lakebridge/src/theme/Footer/index.tsx +0 -0
- {databricks_labs_lakebridge-0.10.5 → databricks_labs_lakebridge-0.10.7}/docs/lakebridge/src/theme/Layout/index.tsx +0 -0
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.4
|
2
2
|
Name: databricks-labs-lakebridge
|
3
|
-
Version: 0.10.
|
3
|
+
Version: 0.10.7
|
4
4
|
Summary: Fast and predictable migrations to Databricks Lakehouse Platform. This tool is designed to help you migrate your data and workloads to the Databricks Lakehouse Platform in a fast, predictable, and reliable way. It provides a set of tools and utilities to help you reconcile your data and workloads, assess your current state, and plan your migration.
|
5
5
|
Project-URL: Documentation, https://databrickslabs.github.io/lakebridge
|
6
6
|
Project-URL: Issues, https://github.com/databrickslabs/lakebridge/issues
|
@@ -1,2 +1,2 @@
|
|
1
1
|
# DO NOT MODIFY THIS FILE
|
2
|
-
__version__ = "0.10.
|
2
|
+
__version__ = "0.10.7"
|
@@ -0,0 +1,95 @@
|
|
1
|
+
import tempfile
|
2
|
+
from pathlib import Path
|
3
|
+
|
4
|
+
from databricks.sdk.service.iam import User
|
5
|
+
from databricks.sdk.core import with_user_agent_extra
|
6
|
+
|
7
|
+
from databricks.labs.blueprint.entrypoint import get_logger
|
8
|
+
from databricks.labs.blueprint.tui import Prompts
|
9
|
+
|
10
|
+
from databricks.labs.bladespector.analyzer import Analyzer, _PLATFORM_TO_SOURCE_TECHNOLOGY
|
11
|
+
|
12
|
+
from databricks.labs.lakebridge.helpers.telemetry_utils import make_alphanum_or_semver
|
13
|
+
from databricks.labs.lakebridge.helpers.file_utils import check_path, move_tmp_file
|
14
|
+
|
15
|
+
logger = get_logger(__file__)
|
16
|
+
|
17
|
+
|
18
|
+
class LakebridgeAnalyzer(Analyzer):
|
19
|
+
def __init__(self, current_user: User, prompts: Prompts, is_debug: bool = False):
|
20
|
+
self._current_user = current_user
|
21
|
+
self._prompts = prompts
|
22
|
+
self._is_debug = is_debug
|
23
|
+
super().__init__()
|
24
|
+
|
25
|
+
def _get_source_directory(self) -> Path:
|
26
|
+
"""Get and validate the source directory from user input."""
|
27
|
+
directory_str = self._prompts.question(
|
28
|
+
"Enter full path to the source directory",
|
29
|
+
default=Path.cwd().as_posix(),
|
30
|
+
validate=check_path,
|
31
|
+
)
|
32
|
+
return Path(directory_str).resolve()
|
33
|
+
|
34
|
+
def _get_result_file_path(self, directory: Path) -> Path:
|
35
|
+
"""Get the result file path - accepts either filename or full path."""
|
36
|
+
filename = self._prompts.question(
|
37
|
+
"Enter report file name or custom export path including file name without extension",
|
38
|
+
default=f"{directory.as_posix()}/lakebridge-analyzer-results.xlsx",
|
39
|
+
validate=check_path,
|
40
|
+
)
|
41
|
+
return directory / Path(filename) if len(filename.split("/")) == 1 else Path(filename)
|
42
|
+
|
43
|
+
def _get_source_tech(self, platform: str | None = None) -> str:
|
44
|
+
"""Validate source technology or prompt for a valid source"""
|
45
|
+
if platform is None or platform not in self.supported_source_technologies():
|
46
|
+
if platform is not None:
|
47
|
+
logger.warning(f"Invalid source technology {platform}")
|
48
|
+
platform = self._prompts.choice("Select the source technology", self.supported_source_technologies())
|
49
|
+
with_user_agent_extra("analyzer_source_tech", make_alphanum_or_semver(platform))
|
50
|
+
logger.debug(f"User: {self._current_user}")
|
51
|
+
return _PLATFORM_TO_SOURCE_TECHNOLOGY[platform]
|
52
|
+
|
53
|
+
@staticmethod
|
54
|
+
def _temp_xlsx_path(results_dir: Path | str) -> Path:
|
55
|
+
return (Path(tempfile.mkdtemp()) / Path(results_dir).name).with_suffix(".xlsx")
|
56
|
+
|
57
|
+
def _run_prompt_analyzer(self):
|
58
|
+
"""Run the analyzer: prompt guided"""
|
59
|
+
source_dir = self._get_source_directory()
|
60
|
+
results_dir = self._get_result_file_path(source_dir)
|
61
|
+
tmp_dir = self._temp_xlsx_path(results_dir)
|
62
|
+
technology = self._get_source_tech()
|
63
|
+
|
64
|
+
self._run_binary(source_dir, tmp_dir, technology, self._is_debug)
|
65
|
+
|
66
|
+
move_tmp_file(tmp_dir, results_dir)
|
67
|
+
|
68
|
+
logger.info(f"Successfully Analyzed files in ${source_dir} for ${technology} and saved report to {results_dir}")
|
69
|
+
|
70
|
+
def _run_arg_analyzer(self, source_dir: str | None, results_dir: str | None, technology: str | None):
|
71
|
+
"""Run the analyzer: arg guided"""
|
72
|
+
if source_dir is None or results_dir is None or technology is None:
|
73
|
+
logger.error("All arguments (--source-directory, --report-file, --source-tech) must be provided")
|
74
|
+
return
|
75
|
+
|
76
|
+
if check_path(source_dir) and check_path(results_dir):
|
77
|
+
tmp_dir = self._temp_xlsx_path(results_dir)
|
78
|
+
technology = self._get_source_tech(technology)
|
79
|
+
self._run_binary(Path(source_dir), tmp_dir, technology, self._is_debug)
|
80
|
+
|
81
|
+
move_tmp_file(tmp_dir, Path(results_dir))
|
82
|
+
|
83
|
+
logger.info(
|
84
|
+
f"Successfully Analyzed files in ${source_dir} for ${technology} and saved report to {results_dir}"
|
85
|
+
)
|
86
|
+
|
87
|
+
def run_analyzer(
|
88
|
+
self, source_dir: str | None = None, results_dir: str | None = None, technology: str | None = None
|
89
|
+
):
|
90
|
+
"""Run the analyzer."""
|
91
|
+
if not any([source_dir, results_dir, technology]):
|
92
|
+
self._run_prompt_analyzer()
|
93
|
+
return
|
94
|
+
|
95
|
+
self._run_arg_analyzer(source_dir, results_dir, technology)
|
@@ -0,0 +1,34 @@
|
|
1
|
+
from databricks.labs.blueprint.logger import install_logger
|
2
|
+
from databricks.labs.blueprint.entrypoint import get_logger
|
3
|
+
from databricks.sdk import WorkspaceClient
|
4
|
+
from databricks.sdk.core import with_user_agent_extra
|
5
|
+
|
6
|
+
from databricks.labs.lakebridge import __version__
|
7
|
+
from databricks.labs.lakebridge.install import installer as _installer
|
8
|
+
from databricks.labs.lakebridge.transpiler.repository import TranspilerRepository
|
9
|
+
|
10
|
+
|
11
|
+
def main() -> None:
|
12
|
+
install_logger()
|
13
|
+
with_user_agent_extra("cmd", "install")
|
14
|
+
|
15
|
+
logger = get_logger(__file__)
|
16
|
+
logger.setLevel("INFO")
|
17
|
+
|
18
|
+
installer = _installer(
|
19
|
+
WorkspaceClient(product="lakebridge", product_version=__version__),
|
20
|
+
transpiler_repository=TranspilerRepository.user_home(),
|
21
|
+
)
|
22
|
+
if installer.has_installed_transpilers():
|
23
|
+
logger.warning(
|
24
|
+
"Detected existing Lakebridge transpilers; run 'databricks labs lakebridge install-transpile' to upgrade them."
|
25
|
+
)
|
26
|
+
else:
|
27
|
+
logger.debug("No existing Lakebridge transpilers detected; assuming fresh installation.")
|
28
|
+
|
29
|
+
logger.info("Successfully Setup Lakebridge Components Locally")
|
30
|
+
logger.info("For more information, please visit https://databrickslabs.github.io/lakebridge/")
|
31
|
+
|
32
|
+
|
33
|
+
if __name__ == "__main__":
|
34
|
+
main()
|
@@ -19,28 +19,23 @@ from databricks.labs.blueprint.entrypoint import get_logger, is_in_debug
|
|
19
19
|
from databricks.labs.blueprint.installation import RootJsonValue
|
20
20
|
from databricks.labs.blueprint.tui import Prompts
|
21
21
|
|
22
|
-
from databricks.labs.bladespector.analyzer import Analyzer
|
23
|
-
|
24
22
|
|
25
23
|
from databricks.labs.lakebridge.assessments.configure_assessment import (
|
26
24
|
create_assessment_configurator,
|
27
25
|
PROFILER_SOURCE_SYSTEM,
|
28
26
|
)
|
29
27
|
|
30
|
-
from databricks.labs.lakebridge.__about__ import __version__
|
31
28
|
from databricks.labs.lakebridge.config import TranspileConfig
|
32
29
|
from databricks.labs.lakebridge.contexts.application import ApplicationContext
|
33
30
|
from databricks.labs.lakebridge.helpers.recon_config_utils import ReconConfigPrompts
|
34
31
|
from databricks.labs.lakebridge.helpers.telemetry_utils import make_alphanum_or_semver
|
35
|
-
from databricks.labs.lakebridge.install import
|
36
|
-
from databricks.labs.lakebridge.install import TranspilerInstaller
|
32
|
+
from databricks.labs.lakebridge.install import installer
|
37
33
|
from databricks.labs.lakebridge.reconcile.runner import ReconcileRunner
|
38
34
|
from databricks.labs.lakebridge.lineage import lineage_generator
|
39
35
|
from databricks.labs.lakebridge.reconcile.recon_config import RECONCILE_OPERATION_NAME, AGG_RECONCILE_OPERATION_NAME
|
40
36
|
from databricks.labs.lakebridge.transpiler.execute import transpile as do_transpile
|
41
|
-
|
42
|
-
|
43
37
|
from databricks.labs.lakebridge.transpiler.lsp.lsp_engine import LSPEngine
|
38
|
+
from databricks.labs.lakebridge.transpiler.repository import TranspilerRepository
|
44
39
|
from databricks.labs.lakebridge.transpiler.sqlglot.sqlglot_engine import SqlglotEngine
|
45
40
|
from databricks.labs.lakebridge.transpiler.transpile_engine import TranspileEngine
|
46
41
|
|
@@ -54,19 +49,6 @@ def raise_validation_exception(msg: str) -> NoReturn:
|
|
54
49
|
raise ValueError(msg)
|
55
50
|
|
56
51
|
|
57
|
-
def _installer(ws: WorkspaceClient) -> WorkspaceInstaller:
|
58
|
-
app_context = ApplicationContext(_verify_workspace_client(ws))
|
59
|
-
return WorkspaceInstaller(
|
60
|
-
app_context.workspace_client,
|
61
|
-
app_context.prompts,
|
62
|
-
app_context.installation,
|
63
|
-
app_context.install_state,
|
64
|
-
app_context.product_info,
|
65
|
-
app_context.resource_configurator,
|
66
|
-
app_context.workspace_installation,
|
67
|
-
)
|
68
|
-
|
69
|
-
|
70
52
|
def _create_warehouse(ws: WorkspaceClient) -> str:
|
71
53
|
|
72
54
|
dbsql = ws.warehouses.create_and_wait(
|
@@ -90,19 +72,6 @@ def _remove_warehouse(ws: WorkspaceClient, warehouse_id: str):
|
|
90
72
|
logger.info(f"Removed warehouse post installation with id: {warehouse_id}")
|
91
73
|
|
92
74
|
|
93
|
-
def _verify_workspace_client(ws: WorkspaceClient) -> WorkspaceClient:
|
94
|
-
"""
|
95
|
-
[Private] Verifies and updates the workspace client configuration.
|
96
|
-
"""
|
97
|
-
|
98
|
-
# Using reflection to set right value for _product_info for telemetry
|
99
|
-
product_info = getattr(ws.config, '_product_info')
|
100
|
-
if product_info[0] != "lakebridge":
|
101
|
-
setattr(ws.config, '_product_info', ('lakebridge', __version__))
|
102
|
-
|
103
|
-
return ws
|
104
|
-
|
105
|
-
|
106
75
|
@lakebridge.command
|
107
76
|
def transpile(
|
108
77
|
w: WorkspaceClient,
|
@@ -114,12 +83,13 @@ def transpile(
|
|
114
83
|
skip_validation: str | None = None,
|
115
84
|
catalog_name: str | None = None,
|
116
85
|
schema_name: str | None = None,
|
86
|
+
transpiler_repository: TranspilerRepository = TranspilerRepository.user_home(),
|
117
87
|
):
|
118
88
|
"""Transpiles source dialect to databricks dialect"""
|
119
89
|
ctx = ApplicationContext(w)
|
120
90
|
logger.debug(f"Preconfigured transpiler config: {ctx.transpile_config!r}")
|
121
91
|
with_user_agent_extra("cmd", "execute-transpile")
|
122
|
-
checker = _TranspileConfigChecker(ctx.transpile_config, ctx.prompts)
|
92
|
+
checker = _TranspileConfigChecker(ctx.transpile_config, ctx.prompts, transpiler_repository)
|
123
93
|
checker.use_transpiler_config_path(transpiler_config_path)
|
124
94
|
checker.use_source_dialect(source_dialect)
|
125
95
|
checker.use_input_source(input_source)
|
@@ -188,14 +158,19 @@ class _TranspileConfigChecker:
|
|
188
158
|
|
189
159
|
_config: TranspileConfig
|
190
160
|
"""The workspace configuration for transpiling, updated from command-line arguments."""
|
191
|
-
# _engine: TranspileEngine | None
|
192
|
-
# """The transpiler engine to use for transpiling, lazily loaded based on the configuration."""
|
193
161
|
_prompts: Prompts
|
194
162
|
"""Prompting system, for requesting configuration that hasn't been provided."""
|
195
163
|
_source_dialect_override: str | None = None
|
196
164
|
"""The source dialect provided on the command-line, if any."""
|
197
|
-
|
198
|
-
|
165
|
+
_transpiler_repository: TranspilerRepository
|
166
|
+
"""The repository where available transpilers are installed."""
|
167
|
+
|
168
|
+
def __init__(
|
169
|
+
self,
|
170
|
+
config: TranspileConfig | None,
|
171
|
+
prompts: Prompts,
|
172
|
+
transpiler_repository: TranspilerRepository,
|
173
|
+
) -> None:
|
199
174
|
if config is None:
|
200
175
|
logger.warning(
|
201
176
|
"No workspace transpile configuration, use 'install-transpile' to (re)install and configure; using defaults for now."
|
@@ -203,6 +178,7 @@ class _TranspileConfigChecker:
|
|
203
178
|
config = TranspileConfig()
|
204
179
|
self._config = config
|
205
180
|
self._prompts = prompts
|
181
|
+
self._transpiler_repository = transpiler_repository
|
206
182
|
self._source_dialect_override = None
|
207
183
|
|
208
184
|
@staticmethod
|
@@ -334,7 +310,7 @@ class _TranspileConfigChecker:
|
|
334
310
|
def _configure_transpiler_config_path(self, source_dialect: str) -> TranspileEngine | None:
|
335
311
|
"""Configure the transpiler config path based on the requested source dialect."""
|
336
312
|
# Names of compatible transpiler engines for the given dialect.
|
337
|
-
compatible_transpilers =
|
313
|
+
compatible_transpilers = self._transpiler_repository.transpilers_with_dialect(source_dialect)
|
338
314
|
match len(compatible_transpilers):
|
339
315
|
case 0:
|
340
316
|
# Nothing found for the specified dialect, fail.
|
@@ -349,10 +325,10 @@ class _TranspileConfigChecker:
|
|
349
325
|
f"Multiple transpilers available for dialect {source_dialect!r}: {compatible_transpilers!r}"
|
350
326
|
)
|
351
327
|
transpiler_name = self._prompts.choice("Select the transpiler:", list(compatible_transpilers))
|
352
|
-
transpiler_config_path =
|
328
|
+
transpiler_config_path = self._transpiler_repository.transpiler_config_path(transpiler_name)
|
353
329
|
logger.info(f"Lakebridge will use the {transpiler_name} transpiler.")
|
354
330
|
self._config = dataclasses.replace(self._config, transpiler_config_path=str(transpiler_config_path))
|
355
|
-
return
|
331
|
+
return LSPEngine.from_config_path(transpiler_config_path)
|
356
332
|
|
357
333
|
def _configure_source_dialect(
|
358
334
|
self, source_dialect: str, engine: TranspileEngine | None, msg_prefix: str
|
@@ -361,7 +337,7 @@ class _TranspileConfigChecker:
|
|
361
337
|
if engine is None:
|
362
338
|
engine = self._configure_transpiler_config_path(source_dialect)
|
363
339
|
if engine is None:
|
364
|
-
supported_dialects = ", ".join(
|
340
|
+
supported_dialects = ", ".join(self._transpiler_repository.all_dialects())
|
365
341
|
msg = f"{msg_prefix}: {source_dialect!r} (supported dialects: {supported_dialects})"
|
366
342
|
raise_validation_exception(msg)
|
367
343
|
else:
|
@@ -375,7 +351,7 @@ class _TranspileConfigChecker:
|
|
375
351
|
|
376
352
|
def _prompt_source_dialect(self) -> TranspileEngine:
|
377
353
|
# This is similar to the post-install prompting for the source dialect.
|
378
|
-
supported_dialects =
|
354
|
+
supported_dialects = self._transpiler_repository.all_dialects()
|
379
355
|
match len(supported_dialects):
|
380
356
|
case 0:
|
381
357
|
msg = "No transpilers are available, install using 'install-transpile' or use --transpiler-conf-path'."
|
@@ -420,14 +396,15 @@ class _TranspileConfigChecker:
|
|
420
396
|
#
|
421
397
|
|
422
398
|
# Step 1: Check the transpiler config path.
|
399
|
+
engine: TranspileEngine | None
|
423
400
|
transpiler_config_path = self._config.transpiler_config_path
|
424
401
|
if transpiler_config_path is not None:
|
425
402
|
self._validate_transpiler_config_path(
|
426
403
|
transpiler_config_path,
|
427
|
-
f"Invalid transpiler
|
404
|
+
f"Error: Invalid value for '--transpiler-config-path': '{str(transpiler_config_path)}', file does not exist.",
|
428
405
|
)
|
429
406
|
path = Path(transpiler_config_path)
|
430
|
-
engine =
|
407
|
+
engine = LSPEngine.from_config_path(path)
|
431
408
|
else:
|
432
409
|
engine = None
|
433
410
|
del transpiler_config_path
|
@@ -522,7 +499,7 @@ async def _transpile(ctx: ApplicationContext, config: TranspileConfig, engine: T
|
|
522
499
|
return [status]
|
523
500
|
|
524
501
|
|
525
|
-
def _override_workspace_client_config(ctx: ApplicationContext, overrides: dict[str, str] | None):
|
502
|
+
def _override_workspace_client_config(ctx: ApplicationContext, overrides: dict[str, str] | None) -> None:
|
526
503
|
"""
|
527
504
|
Override the Workspace client's SDK config with the user provided SDK config.
|
528
505
|
Users can provide the cluster_id and warehouse_id during the installation.
|
@@ -541,7 +518,7 @@ def _override_workspace_client_config(ctx: ApplicationContext, overrides: dict[s
|
|
541
518
|
|
542
519
|
|
543
520
|
@lakebridge.command
|
544
|
-
def reconcile(w: WorkspaceClient):
|
521
|
+
def reconcile(w: WorkspaceClient) -> None:
|
545
522
|
"""[EXPERIMENTAL] Reconciles source to Databricks datasets"""
|
546
523
|
with_user_agent_extra("cmd", "execute-reconcile")
|
547
524
|
ctx = ApplicationContext(w)
|
@@ -557,7 +534,7 @@ def reconcile(w: WorkspaceClient):
|
|
557
534
|
|
558
535
|
|
559
536
|
@lakebridge.command
|
560
|
-
def aggregates_reconcile(w: WorkspaceClient):
|
537
|
+
def aggregates_reconcile(w: WorkspaceClient) -> None:
|
561
538
|
"""[EXPERIMENTAL] Reconciles Aggregated source to Databricks datasets"""
|
562
539
|
with_user_agent_extra("cmd", "execute-aggregates-reconcile")
|
563
540
|
ctx = ApplicationContext(w)
|
@@ -574,7 +551,13 @@ def aggregates_reconcile(w: WorkspaceClient):
|
|
574
551
|
|
575
552
|
|
576
553
|
@lakebridge.command
|
577
|
-
def generate_lineage(
|
554
|
+
def generate_lineage(
|
555
|
+
w: WorkspaceClient,
|
556
|
+
*,
|
557
|
+
source_dialect: str | None = None,
|
558
|
+
input_source: str,
|
559
|
+
output_folder: str,
|
560
|
+
) -> None:
|
578
561
|
"""[Experimental] Generates a lineage of source SQL files or folder"""
|
579
562
|
ctx = ApplicationContext(w)
|
580
563
|
logger.debug(f"User: {ctx.current_user}")
|
@@ -595,7 +578,7 @@ def generate_lineage(w: WorkspaceClient, *, source_dialect: str | None = None, i
|
|
595
578
|
|
596
579
|
|
597
580
|
@lakebridge.command
|
598
|
-
def configure_secrets(w: WorkspaceClient):
|
581
|
+
def configure_secrets(w: WorkspaceClient) -> None:
|
599
582
|
"""Setup reconciliation connection profile details as Secrets on Databricks Workspace"""
|
600
583
|
recon_conf = ReconConfigPrompts(w)
|
601
584
|
|
@@ -607,7 +590,7 @@ def configure_secrets(w: WorkspaceClient):
|
|
607
590
|
|
608
591
|
|
609
592
|
@lakebridge.command(is_unauthenticated=True)
|
610
|
-
def configure_database_profiler():
|
593
|
+
def configure_database_profiler() -> None:
|
611
594
|
"""[Experimental] Install the lakebridge Assessment package"""
|
612
595
|
prompts = Prompts()
|
613
596
|
|
@@ -622,19 +605,26 @@ def configure_database_profiler():
|
|
622
605
|
|
623
606
|
|
624
607
|
@lakebridge.command()
|
625
|
-
def install_transpile(
|
626
|
-
|
608
|
+
def install_transpile(
|
609
|
+
w: WorkspaceClient,
|
610
|
+
artifact: str | None = None,
|
611
|
+
transpiler_repository: TranspilerRepository = TranspilerRepository.user_home(),
|
612
|
+
) -> None:
|
613
|
+
"""Install or upgrade the Lakebridge transpilers."""
|
627
614
|
with_user_agent_extra("cmd", "install-transpile")
|
628
615
|
if artifact:
|
629
616
|
with_user_agent_extra("artifact-overload", Path(artifact).name)
|
630
617
|
user = w.current_user
|
631
618
|
logger.debug(f"User: {user}")
|
632
|
-
|
633
|
-
|
619
|
+
transpile_installer = installer(w, transpiler_repository)
|
620
|
+
transpile_installer.run(module="transpile", artifact=artifact)
|
634
621
|
|
635
622
|
|
636
623
|
@lakebridge.command(is_unauthenticated=False)
|
637
|
-
def configure_reconcile(
|
624
|
+
def configure_reconcile(
|
625
|
+
w: WorkspaceClient,
|
626
|
+
transpiler_repository: TranspilerRepository = TranspilerRepository.user_home(),
|
627
|
+
) -> None:
|
638
628
|
"""Configure the Lakebridge reconciliation module"""
|
639
629
|
with_user_agent_extra("cmd", "configure-reconcile")
|
640
630
|
user = w.current_user
|
@@ -643,28 +633,23 @@ def configure_reconcile(w: WorkspaceClient):
|
|
643
633
|
dbsql_id = _create_warehouse(w)
|
644
634
|
w.config.warehouse_id = dbsql_id
|
645
635
|
logger.debug(f"Warehouse ID used for configuring reconcile: {w.config.warehouse_id}.")
|
646
|
-
|
647
|
-
|
636
|
+
reconcile_installer = installer(w, transpiler_repository)
|
637
|
+
reconcile_installer.run(module="reconcile")
|
648
638
|
|
649
639
|
|
650
640
|
@lakebridge.command()
|
651
|
-
def analyze(
|
641
|
+
def analyze(
|
642
|
+
w: WorkspaceClient,
|
643
|
+
source_directory: str | None = None,
|
644
|
+
report_file: str | None = None,
|
645
|
+
source_tech: str | None = None,
|
646
|
+
):
|
652
647
|
"""Run the Analyzer"""
|
653
648
|
with_user_agent_extra("cmd", "analyze")
|
654
649
|
ctx = ApplicationContext(w)
|
655
|
-
|
656
|
-
|
657
|
-
|
658
|
-
if source_tech is None:
|
659
|
-
source_tech = prompts.choice("Select the source technology", Analyzer.supported_source_technologies())
|
660
|
-
with_user_agent_extra("analyzer_source_tech", make_alphanum_or_semver(source_tech))
|
661
|
-
user = ctx.current_user
|
662
|
-
logger.debug(f"User: {user}")
|
663
|
-
is_debug = logger.getEffectiveLevel() == logging.DEBUG
|
664
|
-
Analyzer.analyze(Path(input_folder), Path(output_file), source_tech, is_debug=is_debug)
|
665
|
-
logger.info(
|
666
|
-
f"Successfully Analyzed files in ${source_directory} for ${source_tech} and saved report to {report_file}"
|
667
|
-
)
|
650
|
+
|
651
|
+
logger.debug(f"User: {ctx.current_user}")
|
652
|
+
ctx.analyzer.run_analyzer(source_directory, report_file, source_tech)
|
668
653
|
|
669
654
|
|
670
655
|
if __name__ == "__main__":
|
@@ -12,7 +12,8 @@ from databricks.sdk.config import Config
|
|
12
12
|
from databricks.sdk.errors import NotFound
|
13
13
|
from databricks.sdk.service.iam import User
|
14
14
|
|
15
|
-
from databricks.labs.lakebridge.
|
15
|
+
from databricks.labs.lakebridge.analyzer.lakebridge_analyzer import LakebridgeAnalyzer
|
16
|
+
from databricks.labs.lakebridge.config import TranspileConfig, ReconcileConfig, LakebridgeConfiguration
|
16
17
|
from databricks.labs.lakebridge.deployment.configurator import ResourceConfigurator
|
17
18
|
from databricks.labs.lakebridge.deployment.dashboard import DashboardDeployment
|
18
19
|
from databricks.labs.lakebridge.deployment.installation import WorkspaceInstallation
|
@@ -22,6 +23,7 @@ from databricks.labs.lakebridge.helpers.metastore import CatalogOperations
|
|
22
23
|
logger = logging.getLogger(__name__)
|
23
24
|
|
24
25
|
|
26
|
+
# pylint: disable=too-many-public-methods
|
25
27
|
class ApplicationContext:
|
26
28
|
def __init__(self, ws: WorkspaceClient):
|
27
29
|
self._ws = ws
|
@@ -42,7 +44,7 @@ class ApplicationContext:
|
|
42
44
|
|
43
45
|
@cached_property
|
44
46
|
def product_info(self) -> ProductInfo:
|
45
|
-
return ProductInfo.from_class(
|
47
|
+
return ProductInfo.from_class(LakebridgeConfiguration)
|
46
48
|
|
47
49
|
@cached_property
|
48
50
|
def installation(self) -> Installation:
|
@@ -65,8 +67,8 @@ class ApplicationContext:
|
|
65
67
|
return None
|
66
68
|
|
67
69
|
@cached_property
|
68
|
-
def remorph_config(self) ->
|
69
|
-
return
|
70
|
+
def remorph_config(self) -> LakebridgeConfiguration:
|
71
|
+
return LakebridgeConfiguration(transpile=self.transpile_config, reconcile=self.recon_config)
|
70
72
|
|
71
73
|
@cached_property
|
72
74
|
def connect_config(self) -> Config:
|
@@ -131,3 +133,8 @@ class ApplicationContext:
|
|
131
133
|
@cached_property
|
132
134
|
def upgrades(self):
|
133
135
|
return Upgrades(self.product_info, self.installation)
|
136
|
+
|
137
|
+
@cached_property
|
138
|
+
def analyzer(self):
|
139
|
+
is_debug = logger.getEffectiveLevel() == logging.DEBUG
|
140
|
+
return LakebridgeAnalyzer(self.current_user, self.prompts, is_debug)
|
@@ -54,7 +54,8 @@ class DashboardDeployment:
|
|
54
54
|
|
55
55
|
valid_dashboard_refs = set()
|
56
56
|
for dashboard_folder in folder.iterdir():
|
57
|
-
|
57
|
+
# Make sure the directory contains a dashboard
|
58
|
+
if not (dashboard_folder.is_dir() and dashboard_folder.joinpath("dashboard.yml").exists()):
|
58
59
|
continue
|
59
60
|
valid_dashboard_refs.add(self._dashboard_reference(dashboard_folder))
|
60
61
|
dashboard = self._update_or_create_dashboard(dashboard_folder, parent_path, config.metadata_config)
|
@@ -11,7 +11,7 @@ from databricks.sdk.errors import NotFound
|
|
11
11
|
from databricks.sdk.mixins.compute import SemVer
|
12
12
|
from databricks.sdk.errors.platform import InvalidParameterValue, ResourceDoesNotExist
|
13
13
|
|
14
|
-
from databricks.labs.lakebridge.config import
|
14
|
+
from databricks.labs.lakebridge.config import LakebridgeConfiguration
|
15
15
|
from databricks.labs.lakebridge.deployment.recon import ReconDeployment
|
16
16
|
|
17
17
|
logger = logging.getLogger("databricks.labs.lakebridge.install")
|
@@ -54,14 +54,14 @@ class WorkspaceInstallation:
|
|
54
54
|
return Version(
|
55
55
|
version=local_installed_version,
|
56
56
|
date=local_installed_date,
|
57
|
-
wheel=f"
|
57
|
+
wheel=f"databricks_labs_lakebridge-{local_installed_version}-py3-none-any.whl",
|
58
58
|
)
|
59
59
|
|
60
60
|
def _get_ws_version(self):
|
61
61
|
try:
|
62
62
|
return self._installation.load(Version)
|
63
|
-
except ResourceDoesNotExist
|
64
|
-
logger.
|
63
|
+
except ResourceDoesNotExist:
|
64
|
+
logger.debug("No existing version found in workspace; assuming fresh installation.")
|
65
65
|
return None
|
66
66
|
|
67
67
|
def _apply_upgrades(self):
|
@@ -91,21 +91,21 @@ class WorkspaceInstallation:
|
|
91
91
|
wheel_paths = [f"/Workspace{wheel}" for wheel in wheel_paths]
|
92
92
|
return wheel_paths
|
93
93
|
|
94
|
-
def install(self, config:
|
94
|
+
def install(self, config: LakebridgeConfiguration):
|
95
95
|
self._apply_upgrades()
|
96
96
|
wheel_paths: list[str] = self._upload_wheel()
|
97
97
|
if config.reconcile:
|
98
|
-
logger.info("Installing
|
98
|
+
logger.info("Installing Lakebridge reconcile Metadata components.")
|
99
99
|
self._recon_deployment.install(config.reconcile, wheel_paths)
|
100
100
|
|
101
|
-
def uninstall(self, config:
|
102
|
-
# This will remove all the
|
101
|
+
def uninstall(self, config: LakebridgeConfiguration):
|
102
|
+
# This will remove all the Lakebridge modules
|
103
103
|
if not self._prompts.confirm(
|
104
|
-
"Do you want to uninstall
|
105
|
-
"remove
|
104
|
+
"Do you want to uninstall Lakebridge from the workspace too, this would "
|
105
|
+
"remove Lakebridge project folder, jobs, metadata and dashboards"
|
106
106
|
):
|
107
107
|
return
|
108
|
-
logger.info(f"Uninstalling
|
108
|
+
logger.info(f"Uninstalling Lakebridge from {self._ws.config.host}.")
|
109
109
|
try:
|
110
110
|
self._installation.files()
|
111
111
|
except NotFound:
|
@@ -112,8 +112,8 @@ class JobDeployment:
|
|
112
112
|
libraries = [
|
113
113
|
compute.Library(whl=remorph_wheel_path),
|
114
114
|
]
|
115
|
-
|
116
|
-
if
|
115
|
+
|
116
|
+
if recon_config.data_source == ReconSourceType.ORACLE.value:
|
117
117
|
# TODO: Automatically fetch a version list for `ojdbc8`
|
118
118
|
oracle_driver_version = "23.4.0.24.05"
|
119
119
|
libraries.append(
|
@@ -1,8 +1,13 @@
|
|
1
1
|
import contextlib
|
2
|
+
import logging
|
2
3
|
import os
|
3
4
|
from pathlib import Path
|
5
|
+
from shutil import move, Error
|
6
|
+
from datetime import datetime
|
4
7
|
from collections.abc import Generator
|
5
8
|
|
9
|
+
logger = logging.getLogger(__name__)
|
10
|
+
|
6
11
|
|
7
12
|
def is_sql_file(file: str | Path) -> bool:
|
8
13
|
"""
|
@@ -63,3 +68,34 @@ def chdir(new_path: Path) -> Generator[None, None, None]:
|
|
63
68
|
yield
|
64
69
|
finally:
|
65
70
|
os.chdir(saved_path)
|
71
|
+
|
72
|
+
|
73
|
+
def check_path(path: str) -> bool:
|
74
|
+
"""Validates a path for both existing files and writable files."""
|
75
|
+
try:
|
76
|
+
path_obj = Path(path) if not isinstance(path, Path) else path
|
77
|
+
|
78
|
+
if path_obj.exists():
|
79
|
+
return os.access(path_obj, os.W_OK)
|
80
|
+
|
81
|
+
parent = path_obj.parent
|
82
|
+
return parent.exists() and os.access(parent, os.W_OK)
|
83
|
+
|
84
|
+
except OSError as e:
|
85
|
+
logger.warning(f"Could not validate path: {path}, error: {e}")
|
86
|
+
return False
|
87
|
+
|
88
|
+
|
89
|
+
def move_tmp_file(tmp_path: Path, output_path: Path) -> None:
|
90
|
+
"""Process file from a temp directory"""
|
91
|
+
try:
|
92
|
+
move(tmp_path, output_path.parent)
|
93
|
+
except (FileExistsError, Error):
|
94
|
+
timestamp = datetime.now().strftime("%Y%m%d-%H%M%S")
|
95
|
+
new_output_path = output_path.parent / timestamp
|
96
|
+
new_output_path.mkdir(exist_ok=True)
|
97
|
+
|
98
|
+
move(tmp_path, new_output_path)
|
99
|
+
finally:
|
100
|
+
tmp_path.parent.rmdir()
|
101
|
+
logger.info(f"Results store at {output_path}")
|