churnkit 1.2.8a5__tar.gz → 1.2.8a7__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.
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/PKG-INFO +1 -1
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/pyproject.toml +1 -1
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/__init__.py +1 -1
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/databricks_renderer.py +63 -27
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/findings_parser.py +29 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/.gitignore +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/LICENSE +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/README.md +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/accounts_view.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/archetype_view.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/customer_profile.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/data.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/default_profile.css +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/default_profile.html +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/masthead.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/state.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/template.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/theme.css +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/apps/databricks_app/src/treemap.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/causal_notebooks/c01_publish_definitions.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/causal_notebooks/c02_archetype_derivation.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/causal_notebooks/c03_approval_gate.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/causal_notebooks/c04_batch_inference.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/causal_notebooks/c05_snapshot_and_dashboard.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/constraints/.gitkeep +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/-1_sample_datasets.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/00_start_here.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/01_data_discovery.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/01a_a_temporal_text_deep_dive.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/01a_temporal_deep_dive.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/01b_temporal_quality.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/01c_temporal_patterns.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/01d_event_aggregation.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/02_source_integrity.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/03_dataset_merge.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/04_column_deep_dive.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/04a_text_columns_deep_dive.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/05_relationship_analysis.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/06_feature_opportunities.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/07_modeling_readiness.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/08_baseline_experiments.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/09_business_alignment.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/10_spec_generation.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/11_scoring_validation.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/12_view_documentation.ipynb +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/.claude/settings.local.json +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/README.md +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/build_framework_phase_map.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/data/create_snapshot.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/data/generate_edi_ticketing_dataset.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/data/generate_retail_dataset.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/data/generate_test_data.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/data/migrate_parquet_to_delta.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/data/migrate_to_temporal.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/databricks/build_wheel.sh +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/databricks/capture_runtime.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/databricks/dbr_init.sh +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/databricks/deploy_dev.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/databricks/generate_constraints.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/databricks/notebook_setup.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/experiments/capture_notebook_outputs.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/experiments/cell_profiling.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/experiments/compare_exploration_runs.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/experiments/compare_versions.sh +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/experiments/patch_dataset_config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/generate_requirements.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/build_causal_notebooks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/clean_notebook_outputs.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/export_tutorial_html.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/init_project.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/migrate_notebook_cell_ids.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/plotly_image_preprocessor.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/run_exploration.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/sync_notebooks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/tag_framework_cells.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/tag_markdown_cells.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/notebooks/test_notebooks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/release.sh +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/seed_playbooks_volume.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/templates/tutorial_html/conf.json +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/templates/tutorial_html/index.html.j2 +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/scripts/update_notebook_paths.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/active_dataset_store.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/analysis_context.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/column_describer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/dataset_fingerprinter.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/entity_timestamp_deriver.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/exploration_manager.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/explorer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/field_availability_audit.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/findings.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/intent_defaults.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/key_resolver.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/layered_recommendations.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/objective_support_communicator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/prediction_objective_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/project_context.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/recommendation_builder.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/recommendations.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/run_namespace.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/sampling.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/schema_report.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/service_unit_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/session.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/skip_logic.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/snapshot_grid.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/ab_test_designer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/fairness_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/intervention_matcher.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/ratio_features.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/report_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/risk_profile.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/roi_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/calibration_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/cv_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/error_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/exploration_ledger.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/feature_provenance.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/feature_stability.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/leakage_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/model_diagnostics_report.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/noise_tester.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/overfitting_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/parity_report.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/segment_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/discovery/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/discovery/config_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/discovery/discovery_flow.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/discovery/type_inferencer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/interpretability/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/interpretability/cohort_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/interpretability/counterfactual.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/interpretability/individual_explainer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/interpretability/pdp_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/interpretability/shap_explainer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/jupyter_save_hook.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/notebook_html_exporter.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/notebook_progress.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/plotly_preprocessor.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/base.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/cleaning/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/cleaning/consistency.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/cleaning/deduplicate.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/cleaning/impute.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/cleaning/outlier.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/datetime/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/datetime/extract.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/encoding/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/encoding/categorical.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/pipeline.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/registry.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/selection/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/selection/drop_column.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/transform/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/transform/power.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/recommendations/transform/scale.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/visualization/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/visualization/attention_scorer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/visualization/chart_builder.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/visualization/column_paginator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/visualization/console.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/visualization/display.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/visualization/number_formatter.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/artifacts/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/artifacts/fit_artifact_registry.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/cli.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/bulk_profiling.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/cell_profiling_hooks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/detection.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/ops.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/pandas_backend.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/remote_path.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/spark_backend.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/compat/timing.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/base.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/deployer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/explainer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/feature_eng.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/ingester.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/profiler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/trainer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/transformer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/components/validator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/enums.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/orchestrator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/components/registry.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/config/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/config/column_config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/config/experiments.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/config/pipeline_config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/config/source_config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/naming.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/utils/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/utils/leakage.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/utils/severity.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/core/utils/statistics.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/base.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/cell_builder.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/databricks_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/local_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/project_init.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/runner.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/scoring_replay.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/script_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/base_stage.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/causal_setup_cell.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s01_ingestion.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s02_profiling.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s03_cleaning.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s04_transformation.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s05_feature_engineering.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s06_feature_selection.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s07_model_training.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s08_deployment.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s09_monitoring.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s10_batch_inference.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s11_feature_store.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s_c01_publish_definitions.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s_c02_archetype_derivation.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s_c03_approval_gate.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s_c04_batch_inference.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_generator/stages/s_c05_snapshot_and_dashboard.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_merge/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_merge/cli.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_merge/config_merger.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_merge/config_parser.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_merge/conflict.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_merge/merge_engine.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_merge/merge_report.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_sync/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_sync/cell_id_standardizer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_sync/cell_types.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_sync/cli.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_sync/sync_engine.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/notebook_sync/sync_report.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/orchestration/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/orchestration/code_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/orchestration/context.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/orchestration/data_materializer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/orchestration/databricks_exporter.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/orchestration/doc_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/databricks_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/exploration_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/generation_manifest.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/gold_transform_applicator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/llm_docs_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/models.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/override_merge.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/protocols.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/renderer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/pipeline_generator/user_extensions_emitter.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/spec_generator/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/generators/spec_generator/mlflow_pipeline_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/base.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/factory.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/feature_store/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/feature_store/base.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/feature_store/databricks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/feature_store/feast_adapter.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/feature_store/local.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/mlflow/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/mlflow/base.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/mlflow/databricks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/mlflow/experiment_tracker.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/mlflow/local.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/storage/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/storage/base.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/storage/databricks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/adapters/storage/local.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/databricks_init.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/databricks_job_capture.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/feature_store/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/feature_store/definitions.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/feature_store/manager.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/feature_store/registry.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/iteration/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/iteration/context.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/iteration/feedback_collector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/iteration/orchestrator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/iteration/recommendation_tracker.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/iteration/signals.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/llm_context/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/llm_context/context_builder.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/llm_context/prompts.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/requirements_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/streaming/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/streaming/batch_integration.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/streaming/early_warning_model.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/streaming/event_schema.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/streaming/online_store_writer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/streaming/realtime_scorer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/streaming/trigger_engine.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/integrations/streaming/window_aggregator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/api.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/dataset_resolution.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/decorator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/flags.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/harvest.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/logging.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/persistence.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/registry.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/replay.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/summary.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/runtime/validation.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/approval_gate.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/clusterer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/column_descriptions_writer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/dashboard_profile_override.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/dashboard_views.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/delta_writer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/derivation.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/feature_meta_writer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/archetype_context.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/business_phrase.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/discovery.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/enrichment_pipeline.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/feature_meta_builder.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/llm_prompt.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/markdown_bootstrap.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/predicate_prose.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/prose_backfill.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/quantile_phrasing.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/interpretation/sidecars.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/llm_namer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/playbook_loader.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/playbook_mapper.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/policy_loader.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/population_stats.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/predicate_compiler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/rule_extractor.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/run_context_writer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/schemas.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/seed_yamls/decision_policy.yaml +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/seed_yamls/response_schemas.yaml +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/seed_yamls/vocabularies.yaml +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/shap_runner.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/snapshot_writer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/sql/dashboard_views.sql +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/causal/top_drivers_writer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/cleaning/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/cleaning/base.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/cleaning/missing_handler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/cleaning/outlier_handler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/deployment/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/deployment/batch_scorer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/deployment/champion_challenger.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/deployment/model_registry.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/deployment/retraining_trigger.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/behavioral_features.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/customer_segmentation.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/feature_definitions.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/feature_engineer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/feature_manifest.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/feature_selector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/interaction_features.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/features/temporal_features.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/ingestion/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/ingestion/load_result.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/ingestion/loaders.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/ingestion/source_registry.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/lifecycle/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/lifecycle/config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/lifecycle/enrich.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/lifecycle/validation.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/baseline_trainer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/cross_validator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/data_splitter.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/feature_profile.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/feature_scaler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/feature_spec.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/hyperparameter_tuner.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/imbalance_handler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/mlflow_logger.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/model_comparator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/model_evaluator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/shap_attribution.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/spark_baseline_trainer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/spark_classifier_wrapper.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/spark_feature_scaler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/threshold_optimizer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/modeling/training_preparator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/monitoring/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/monitoring/alert_manager.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/monitoring/drift_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/monitoring/performance_monitor.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/preprocessing/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/preprocessing/transformer_manager.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/categorical_distribution.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/categorical_target_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/column_profiler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/distribution_analysis.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/drift_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/feature_capacity.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/pattern_analysis_config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/profile_result.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/quality_checks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/recommendation_filter.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/relationship_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/relationship_recommender.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/report_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/scd_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/segment_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/segment_aware_outlier.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/spark_segment_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/spark_temporal_feature_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/spark_temporal_feature_engineer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/spark_time_window_aggregator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/stats_helpers.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/target_level_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/target_validator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/temporal_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/temporal_coverage.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/temporal_feature_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/temporal_feature_engineer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/temporal_pattern_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/temporal_quality_checks.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/temporal_target_analyzer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/text_embedder.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/text_processor.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/text_reducer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/time_series_profiler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/time_window_aggregator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/type_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/profiling/window_recommendation.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scd_history/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scd_history/augment.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scd_history/config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scd_history/reconstruct.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scd_history/validation.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scoring/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scoring/batch_inference.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scoring/config.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scoring/data_loader.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scoring/exceptions.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/scoring/pipeline_discovery.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/access_guard.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/data_preparer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/point_in_time_join.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/point_in_time_registry.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/scenario_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/snapshot_manager.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/spark_temporal_merger.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/synthetic_coordinator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/temporal_merger.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/timestamp_discovery.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/temporal/timestamp_manager.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/transformation/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/transformation/binary_handler.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/transformation/categorical_encoder.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/transformation/datetime_transformer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/transformation/numeric_transformer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/transformation/pipeline.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/adversarial_scoring_validator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/business_sense_gate.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/data_quality_gate.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/data_validators.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/feature_quality_gate.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/gates.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/leakage_gate.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/model_validity_gate.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/pipeline_validation_runner.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/quality_scorer.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/rule_generator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/scoring_pipeline_validator.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/stages/validation/timeseries_detector.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/transforms/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/transforms/artifact_store.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/transforms/executor.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/transforms/fitted.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/transforms/ops.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/transforms/spark_ops.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/tests/exploration_notebooks/test_distributed_dtype_safety.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/tests/exploration_notebooks/test_nb10_run_pipeline_ordering.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/tests/scripts/__init__.py +0 -0
- {churnkit-1.2.8a5 → churnkit-1.2.8a7}/tests/scripts/test_build_framework_phase_map.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: churnkit
|
|
3
|
-
Version: 1.2.
|
|
3
|
+
Version: 1.2.8a7
|
|
4
4
|
Summary: Structured ML framework for customer churn prediction -- from exploration notebooks to production pipelines, locally or on Databricks.
|
|
5
5
|
Project-URL: Homepage, https://github.com/aladjov/CR
|
|
6
6
|
Project-URL: Documentation, https://github.com/aladjov/CR/wiki
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
[project]
|
|
2
2
|
name = "churnkit"
|
|
3
|
-
version = "1.02.
|
|
3
|
+
version = "1.02.8a7"
|
|
4
4
|
description = "Structured ML framework for customer churn prediction -- from exploration notebooks to production pipelines, locally or on Databricks."
|
|
5
5
|
readme = "README.md"
|
|
6
6
|
license = {text = "Apache-2.0"}
|
|
@@ -30,20 +30,28 @@ def render_spark_step_call(step: TransformationStep) -> str:
|
|
|
30
30
|
|
|
31
31
|
|
|
32
32
|
def _impute_null(col, p):
|
|
33
|
+
# Guard against recommendations that target a column not in this stage's
|
|
34
|
+
# input — same rationale as the per-column transforms below.
|
|
33
35
|
value = p.get("value", 0)
|
|
34
36
|
if isinstance(value, str):
|
|
35
|
-
return f'df.fillna("{value}", subset=["{col}"])'
|
|
36
|
-
return f'df.fillna({value}, subset=["{col}"])'
|
|
37
|
+
return f'(df.fillna("{value}", subset=["{col}"]) if "{col}" in df.columns else df)'
|
|
38
|
+
return f'(df.fillna({value}, subset=["{col}"]) if "{col}" in df.columns else df)'
|
|
37
39
|
|
|
38
40
|
|
|
39
41
|
def _cap_outlier(col, p):
|
|
40
42
|
lower = p.get("lower", 0)
|
|
41
43
|
upper = p.get("upper", 1000000)
|
|
44
|
+
# Recommendations registered against exploration's silver-merged frame can
|
|
45
|
+
# target columns that don't exist in this stage's input (e.g. silver-derived
|
|
46
|
+
# `days_since_*`/`days_until_*` recency features mistakenly attributed to
|
|
47
|
+
# bronze). Guard the withColumn so the rec degrades to a no-op at runtime
|
|
48
|
+
# instead of failing the stage with UNRESOLVED_COLUMN.
|
|
42
49
|
return (
|
|
43
|
-
f'df.withColumn("{col}", '
|
|
50
|
+
f'(df.withColumn("{col}", '
|
|
44
51
|
f'F.when(F.col("{col}") < {lower}, {lower})'
|
|
45
52
|
f'.when(F.col("{col}") > {upper}, {upper})'
|
|
46
|
-
f'.otherwise(F.col("{col}")))'
|
|
53
|
+
f'.otherwise(F.col("{col}"))) '
|
|
54
|
+
f'if "{col}" in df.columns else df)'
|
|
47
55
|
)
|
|
48
56
|
|
|
49
57
|
|
|
@@ -54,20 +62,28 @@ def _drop_column(col, _p):
|
|
|
54
62
|
def _winsorize(col, p):
|
|
55
63
|
lower = p.get("lower_bound", 0)
|
|
56
64
|
upper = p.get("upper_bound", 1000000)
|
|
65
|
+
# See `_cap_outlier` — same column-existence guard.
|
|
57
66
|
return (
|
|
58
|
-
f'df.withColumn("{col}", '
|
|
67
|
+
f'(df.withColumn("{col}", '
|
|
59
68
|
f'F.when(F.col("{col}") < {lower}, {lower})'
|
|
60
69
|
f'.when(F.col("{col}") > {upper}, {upper})'
|
|
61
|
-
f'.otherwise(F.col("{col}")))'
|
|
70
|
+
f'.otherwise(F.col("{col}"))) '
|
|
71
|
+
f'if "{col}" in df.columns else df)'
|
|
62
72
|
)
|
|
63
73
|
|
|
64
74
|
|
|
65
75
|
def _log_transform(col, _p):
|
|
66
|
-
return
|
|
76
|
+
return (
|
|
77
|
+
f'(df.withColumn("{col}", F.log1p(F.col("{col}"))) '
|
|
78
|
+
f'if "{col}" in df.columns else df)'
|
|
79
|
+
)
|
|
67
80
|
|
|
68
81
|
|
|
69
82
|
def _sqrt_transform(col, _p):
|
|
70
|
-
return
|
|
83
|
+
return (
|
|
84
|
+
f'(df.withColumn("{col}", F.sqrt(F.abs(F.col("{col}")))) '
|
|
85
|
+
f'if "{col}" in df.columns else df)'
|
|
86
|
+
)
|
|
71
87
|
|
|
72
88
|
|
|
73
89
|
def _encode_one_hot(col, _p):
|
|
@@ -86,8 +102,9 @@ def _derived_ratio(col, p):
|
|
|
86
102
|
num = p.get("numerator", "")
|
|
87
103
|
den = p.get("denominator", "")
|
|
88
104
|
return (
|
|
89
|
-
f'df.withColumn("{col}", '
|
|
90
|
-
f'F.col("{num}") / F.when(F.col("{den}") != 0, F.col("{den}")).otherwise(F.lit(None)))'
|
|
105
|
+
f'(df.withColumn("{col}", '
|
|
106
|
+
f'F.col("{num}") / F.when(F.col("{den}") != 0, F.col("{den}")).otherwise(F.lit(None))) '
|
|
107
|
+
f'if all(c in df.columns for c in ["{num}", "{den}"]) else df)'
|
|
91
108
|
)
|
|
92
109
|
|
|
93
110
|
|
|
@@ -95,7 +112,10 @@ def _derived_interaction(col, p):
|
|
|
95
112
|
features = p.get("features", [])
|
|
96
113
|
col_a = features[0] if len(features) > 0 else p.get("col_a", "")
|
|
97
114
|
col_b = features[1] if len(features) > 1 else p.get("col_b", "")
|
|
98
|
-
return
|
|
115
|
+
return (
|
|
116
|
+
f'(df.withColumn("{col}", F.col("{col_a}") * F.col("{col_b}")) '
|
|
117
|
+
f'if all(c in df.columns for c in ["{col_a}", "{col_b}"]) else df)'
|
|
118
|
+
)
|
|
99
119
|
|
|
100
120
|
|
|
101
121
|
def _derived_composite(col, p):
|
|
@@ -103,23 +123,31 @@ def _derived_composite(col, p):
|
|
|
103
123
|
if not columns:
|
|
104
124
|
raise ValueError(f"Composite derived column '{col}' requires non-empty 'columns' parameter")
|
|
105
125
|
expr_parts = " + ".join(f'F.col("{c}")' for c in columns)
|
|
106
|
-
|
|
126
|
+
cols_repr = "[" + ", ".join(f'"{c}"' for c in columns) + "]"
|
|
127
|
+
return (
|
|
128
|
+
f'(df.withColumn("{col}", ({expr_parts}) / {len(columns)}) '
|
|
129
|
+
f'if all(c in df.columns for c in {cols_repr}) else df)'
|
|
130
|
+
)
|
|
107
131
|
|
|
108
132
|
|
|
109
133
|
def _segment_aware_cap(col, p):
|
|
110
134
|
n_segments = p.get("n_segments", 2)
|
|
111
|
-
return
|
|
135
|
+
return (
|
|
136
|
+
f'(_segment_aware_cap(df, "{col}", n_segments={n_segments}) '
|
|
137
|
+
f'if "{col}" in df.columns else df)'
|
|
138
|
+
)
|
|
112
139
|
|
|
113
140
|
|
|
114
141
|
def _zero_inflation_handling(col, _p):
|
|
115
142
|
return (
|
|
116
|
-
f'df.withColumn("{col}_is_zero", F.when(F.col("{col}") == 0, 1).otherwise(0))'
|
|
117
|
-
f'.withColumn("{col}_log", F.when(F.col("{col}") > 0, F.log1p(F.col("{col}"))).otherwise(0))'
|
|
143
|
+
f'(df.withColumn("{col}_is_zero", F.when(F.col("{col}") == 0, 1).otherwise(0))'
|
|
144
|
+
f'.withColumn("{col}_log", F.when(F.col("{col}") > 0, F.log1p(F.col("{col}"))).otherwise(0)) '
|
|
145
|
+
f'if "{col}" in df.columns else df)'
|
|
118
146
|
)
|
|
119
147
|
|
|
120
148
|
|
|
121
149
|
def _cap_then_log(col, _p):
|
|
122
|
-
return f'_cap_then_log(df, "{col}")'
|
|
150
|
+
return f'(_cap_then_log(df, "{col}") if "{col}" in df.columns else df)'
|
|
123
151
|
|
|
124
152
|
|
|
125
153
|
def _type_cast(col, p):
|
|
@@ -194,10 +222,11 @@ def _derived_recency(col, p):
|
|
|
194
222
|
return f'df # silver_derived recency {col!r}: source unresolvable'
|
|
195
223
|
src = sources[0]
|
|
196
224
|
return (
|
|
197
|
-
f'df.withColumn("{col}", '
|
|
225
|
+
f'(df.withColumn("{col}", '
|
|
198
226
|
f'F.when(F.col("{src}").isNotNull() & F.col("as_of_date").isNotNull(), '
|
|
199
227
|
f'F.datediff(F.col("as_of_date"), F.to_date(F.col("{src}"))).cast("double"))'
|
|
200
|
-
f'.otherwise(F.lit(None)))'
|
|
228
|
+
f'.otherwise(F.lit(None))) '
|
|
229
|
+
f'if "{src}" in df.columns else df)'
|
|
201
230
|
)
|
|
202
231
|
|
|
203
232
|
|
|
@@ -207,10 +236,11 @@ def _derived_duration(col, p):
|
|
|
207
236
|
return f'df # silver_derived duration {col!r}: source unresolvable'
|
|
208
237
|
a, b = sources[0], sources[1]
|
|
209
238
|
return (
|
|
210
|
-
f'df.withColumn("{col}", '
|
|
239
|
+
f'(df.withColumn("{col}", '
|
|
211
240
|
f'F.when(F.col("{a}").isNotNull() & F.col("{b}").isNotNull(), '
|
|
212
241
|
f'F.datediff(F.to_date(F.col("{b}")), F.to_date(F.col("{a}"))).cast("double"))'
|
|
213
|
-
f'.otherwise(F.lit(None)))'
|
|
242
|
+
f'.otherwise(F.lit(None))) '
|
|
243
|
+
f'if all(c in df.columns for c in ["{a}", "{b}"]) else df)'
|
|
214
244
|
)
|
|
215
245
|
|
|
216
246
|
|
|
@@ -229,12 +259,13 @@ def _derived_cyclical(col, p):
|
|
|
229
259
|
return f'df # silver_derived cyclical {col!r}: source unresolvable'
|
|
230
260
|
src = sources[0]
|
|
231
261
|
return (
|
|
232
|
-
f'df.withColumn("{src}_month_sin", '
|
|
262
|
+
f'(df.withColumn("{src}_month_sin", '
|
|
233
263
|
f'F.when(F.col("{src}").isNotNull(), '
|
|
234
264
|
f'F.sin(2 * 3.141592653589793 * F.month(F.col("{src}")) / 12)).otherwise(F.lit(None)))'
|
|
235
265
|
f'.withColumn("{src}_month_cos", '
|
|
236
266
|
f'F.when(F.col("{src}").isNotNull(), '
|
|
237
|
-
f'F.cos(2 * 3.141592653589793 * F.month(F.col("{src}")) / 12)).otherwise(F.lit(None)))'
|
|
267
|
+
f'F.cos(2 * 3.141592653589793 * F.month(F.col("{src}")) / 12)).otherwise(F.lit(None))) '
|
|
268
|
+
f'if "{src}" in df.columns else df)'
|
|
238
269
|
)
|
|
239
270
|
|
|
240
271
|
|
|
@@ -244,10 +275,11 @@ def _derived_tenure(col, p):
|
|
|
244
275
|
return f'df # silver_derived tenure {col!r}: source unresolvable'
|
|
245
276
|
src = sources[0]
|
|
246
277
|
return (
|
|
247
|
-
f'df.withColumn("{col}", '
|
|
278
|
+
f'(df.withColumn("{col}", '
|
|
248
279
|
f'F.when(F.col("{src}").isNotNull() & F.col("as_of_date").isNotNull(), '
|
|
249
280
|
f'(F.datediff(F.col("as_of_date"), F.to_date(F.col("{src}"))) / 365.25).cast("double"))'
|
|
250
|
-
f'.otherwise(F.lit(None)))'
|
|
281
|
+
f'.otherwise(F.lit(None))) '
|
|
282
|
+
f'if "{src}" in df.columns else df)'
|
|
251
283
|
)
|
|
252
284
|
|
|
253
285
|
|
|
@@ -262,12 +294,16 @@ def _derived_extraction(col, p):
|
|
|
262
294
|
if not sources:
|
|
263
295
|
return f'df # silver_derived extraction {col!r}: source unresolvable'
|
|
264
296
|
src = sources[0]
|
|
297
|
+
# Three-way fall-through: passthrough if `{col}` is already present
|
|
298
|
+
# (landing emitted it), derive from `{src}` when present, otherwise no-op
|
|
299
|
+
# so a missing source from a phantom rec doesn't crash the stage.
|
|
265
300
|
return (
|
|
266
|
-
f'df if "{col}" in df.columns else '
|
|
267
|
-
f'df.withColumn("{col}", '
|
|
301
|
+
f'(df if "{col}" in df.columns else '
|
|
302
|
+
f'(df.withColumn("{col}", '
|
|
268
303
|
f'F.when(F.col("{src}").isNotNull(), '
|
|
269
304
|
f'F.when(F.dayofweek(F.to_date(F.col("{src}"))).isin(1, 7), 1.0).otherwise(0.0))'
|
|
270
|
-
f'.otherwise(F.lit(None)))'
|
|
305
|
+
f'.otherwise(F.lit(None))) '
|
|
306
|
+
f'if "{src}" in df.columns else df))'
|
|
271
307
|
)
|
|
272
308
|
|
|
273
309
|
|
|
@@ -1266,10 +1266,32 @@ class FindingsParser:
|
|
|
1266
1266
|
replay the same logic at runtime via the existing template branches
|
|
1267
1267
|
(`databricks_landing.py.j2` `config.lifecycle_enrichments` /
|
|
1268
1268
|
`config.filters`).
|
|
1269
|
+
|
|
1270
|
+
Idempotency: when a dataset already carries a step of the same kind
|
|
1271
|
+
from the recommendations registry (post-NB00-migration), the override
|
|
1272
|
+
is skipped instead of double-appended. Without this, the generated
|
|
1273
|
+
landing notebook runs `enrich_lifecycle_dataset(...)` twice and the
|
|
1274
|
+
second call crashes with UNRESOLVED_COLUMN because the first already
|
|
1275
|
+
renamed the lifecycle's `valid_from_column`.
|
|
1269
1276
|
"""
|
|
1277
|
+
already_filter = {
|
|
1278
|
+
ds for ds, lc in (config.landing or {}).items()
|
|
1279
|
+
if getattr(lc, "filters", None)
|
|
1280
|
+
}
|
|
1281
|
+
already_lifecycle = {
|
|
1282
|
+
ds for ds, lc in (config.landing or {}).items()
|
|
1283
|
+
if getattr(lc, "lifecycle_enrichments", None)
|
|
1284
|
+
}
|
|
1270
1285
|
for dataset, predicate in self._landing_filter_overrides.items():
|
|
1271
1286
|
if not predicate:
|
|
1272
1287
|
continue
|
|
1288
|
+
if dataset in already_filter:
|
|
1289
|
+
logger.warning(
|
|
1290
|
+
"landing_filter_overrides: dataset %r already has registry-driven "
|
|
1291
|
+
"filter step(s); skipping operator override to avoid double-apply.",
|
|
1292
|
+
dataset,
|
|
1293
|
+
)
|
|
1294
|
+
continue
|
|
1273
1295
|
target = config.landing.get(dataset)
|
|
1274
1296
|
if target is None:
|
|
1275
1297
|
logger.warning(
|
|
@@ -1287,6 +1309,13 @@ class FindingsParser:
|
|
|
1287
1309
|
for dataset, lifecycle_cfg in self._landing_lifecycle_overrides.items():
|
|
1288
1310
|
if not lifecycle_cfg:
|
|
1289
1311
|
continue
|
|
1312
|
+
if dataset in already_lifecycle:
|
|
1313
|
+
logger.warning(
|
|
1314
|
+
"landing_lifecycle_overrides: dataset %r already has registry-driven "
|
|
1315
|
+
"lifecycle step(s); skipping operator override to avoid double-apply.",
|
|
1316
|
+
dataset,
|
|
1317
|
+
)
|
|
1318
|
+
continue
|
|
1290
1319
|
target = config.landing.get(dataset)
|
|
1291
1320
|
if target is None:
|
|
1292
1321
|
logger.warning(
|
|
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
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/01a_a_temporal_text_deep_dive.ipynb
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
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/exploration_notebooks/04a_text_columns_deep_dive.ipynb
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
|
|
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
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/explorer.py
RENAMED
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/findings.py
RENAMED
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/key_resolver.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/run_namespace.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/sampling.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/schema_report.py
RENAMED
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/session.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/skip_logic.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/auto_explorer/snapshot_grid.py
RENAMED
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/ab_test_designer.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/fairness_analyzer.py
RENAMED
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/ratio_features.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/report_generator.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/risk_profile.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/business/roi_analyzer.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/__init__.py
RENAMED
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/cv_analyzer.py
RENAMED
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/error_analyzer.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/noise_tester.py
RENAMED
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/diagnostics/parity_report.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
{churnkit-1.2.8a5 → churnkit-1.2.8a7}/src/customer_retention/analysis/discovery/config_generator.py
RENAMED
|
File without changes
|