feat(dm): добавлена эталонная витрина dm.sales_report
- Зачем: - требуется эталонная витрина для обучения паттернам DM-слоя - демонстрация UPSERT-логики с IS DISTINCT FROM для идемпотентности - Что: - DDL: heap-таблица dm.sales_report с 18 полями, DISTRIBUTED BY (flight_date) - Load: UPSERT (UPDATE + INSERT) с JOIN dim_calendar, dim_airports (x2), dim_tariffs, fact_flight_sales - DQ: PL/pgSQL DO $$ с проверками непустоты, уникальности, tickets_sold >= passengers_boarded, boarding_rate BETWEEN 0 AND 1 - DAGs: bookings_dm_ddl (DDL), bookings_to_gp_dm (ETL + DQ с параллельными ветками) - Tests: smoke-тесты для обоих DAG - sql/ddl_gp.sql: добавлен \i dm/sales_report_ddl.sql - Проверка: - make fmt && make lint — passed - make test — 15 passed, 11 skipped - make ddl-gp — DDL applied successfully - airflow dags test bookings_to_gp_dm 2026-02-28T13:00:00 — 4 tasks SUCCESS - 9243 rows loaded, _load_id подставлен корректно (Jinja2 templating works) - DQ checks passed
This commit is contained in:
@@ -382,3 +382,36 @@ def test_bookings_to_gp_dds_dag_structure():
|
||||
|
||||
# Финальная сводка должна ждать DQ факта.
|
||||
_assert_reachable(dag, "dq_dds_fact_flight_sales", "finish_dds_summary")
|
||||
|
||||
|
||||
def test_bookings_dm_ddl_dag_structure():
|
||||
"""Проверка структуры DAG bookings_dm_ddl."""
|
||||
dag = _load_dag("airflow.dags.bookings_dm_ddl")
|
||||
|
||||
expected_tasks = {
|
||||
"apply_dm_sales_report_ddl",
|
||||
}
|
||||
assert expected_tasks.issubset(dag.task_dict.keys())
|
||||
|
||||
# На данном этапе только одна витрина
|
||||
# В будущем: линейная цепочка из 5 задач
|
||||
|
||||
|
||||
def test_bookings_to_gp_dm_dag_structure():
|
||||
"""Проверка структуры DAG bookings_to_gp_dm."""
|
||||
dag = _load_dag("airflow.dags.bookings_to_gp_dm")
|
||||
|
||||
expected_tasks = {
|
||||
"start_dm",
|
||||
"load_dm_sales_report",
|
||||
"dq_dm_sales_report",
|
||||
"finish_dm_summary",
|
||||
}
|
||||
assert expected_tasks.issubset(dag.task_dict.keys())
|
||||
|
||||
# Проверяем зависимости load -> dq
|
||||
_assert_direct_edge(dag, "load_dm_sales_report", "dq_dm_sales_report")
|
||||
|
||||
# Проверяем, что start -> load -> dq -> finish
|
||||
_assert_reachable(dag, "start_dm", "load_dm_sales_report")
|
||||
_assert_reachable(dag, "dq_dm_sales_report", "finish_dm_summary")
|
||||
|
||||
Reference in New Issue
Block a user