test(generator): вычищены прозаические тесты из контракта DAG

Тесты на дословные фразы документов и комментариев удалены: прозу
сторожит ревью, а не pytest. Оставлены структурные инварианты (порядок
задач, монтирования, версии, живые перекрёстные ссылки). В шапке файла —
критерий «инвариант должен переживать честную переписку текста».

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
2026-07-23 18:41:09 +03:00
co-authored by Claude Fable 5
parent 4861d20313
commit 271f1afdb3
+21 -17
View File
@@ -1,4 +1,16 @@
"""Контракты DAG world_init и world_next_day без запуска Airflow."""
"""Контракты DAG world_init и world_next_day без запуска Airflow.
Что здесь контракт. Проверяем только структурные и поведенческие инварианты
стенда: идентификаторы DAG и задач, порядок задач, пути монтирования, синхронность
версий, живые перекрёстные ссылки между документами и реальные идентификаторы
(имена дашбордов, профилей, make-целей). Критерий: инвариант должен переживать
честную переписку текста — краснеть, только когда ломается само поведение или
структура, а не формулировка.
Чего сюда не добавлять: дословные цитаты прозы из документов и комментариев
(«в README есть слово X», «в комментарии написано Y»). Прозу сторожит ревью, а не
pytest — такой тест зелёный до первой честной переписки и краснеет без дефекта.
"""
import ast
from pathlib import Path
@@ -142,7 +154,6 @@ def test_world_dags_precheck_etl_dag_not_paused_before_waiting():
assert "session.query(DagModel)" in shared_tasks
assert "DagModel.dag_id == dag_id" in shared_tasks
assert "target_dag_trigger_error" in shared_tasks
assert "Airflow 2.10.5" in shared_tasks
assert "fail_when_dag_is_paused" in shared_tasks
assert 'return "check_etl_not_paused_before_backfill"' in text
assert 'return "check_etl_not_paused_before_import"' in text
@@ -175,22 +186,14 @@ def test_readme_quick_start_creates_schema_via_ddl_init_before_world_init():
"""Быстрый старт: терминал — только make up, схему создаёт ddl_init до world_init."""
text = (REPO_ROOT / "README.md").read_text(encoding="utf-8")
assert "uv" in text
assert "Docker" in text
assert "docker compose" in text
# Ручного шага создания схемы в быстром старте быть не должно — её создаёт
# DAG ddl_init. Проверяем этот структурный факт и порядок ddl_init→world_init,
# а не наличие слов «uv»/«Docker» в тексте.
assert "make ddl" not in text
quick_start = text.split("## Быстрый старт", maxsplit=1)[1]
assert quick_start.index("ddl_init") < quick_start.index("world_init")
def test_course_readme_lists_uv_before_first_command():
"""Курс называет uv до первой команды."""
text = (REPO_ROOT / "docs" / "course" / "README.md").read_text(encoding="utf-8")
assert "uv" in text
assert text.index("uv") < text.index("make clean")
def test_course_canonical_setup_unpauses_dags_before_world_init():
"""Канонический блок называет три DAG, снятие паузы и порядок etl→world_init."""
# Прозаические формулировки не проверяем — их сторожит ревью, не pytest.
@@ -229,15 +232,16 @@ def test_monitoring_lesson_links_to_canonical_reset():
assert "../README.md#подготовка-и-канонический-сброс" in text
def test_startup_history_runbook_warns_about_daily_wave_idle_gap():
"""Runbook предупреждает о дыре модельного времени при простое daily-wave."""
def test_startup_history_runbook_references_daily_wave_reset_and_import():
"""Runbook ссылается на реальные идентификаторы восстановления стенда."""
# Не пиним формулировку предупреждения о дыре модельного времени — её
# сторожит ревью. Держим ссылки на реальные идентификаторы: профиль,
# make-цель сброса и якорь импорта.
text = (REPO_ROOT / "docs" / "runbooks" / "startup-history.md").read_text(
encoding="utf-8"
)
assert "daily-wave" in text
assert "прост" in text
assert "дыр" in text
assert "make generator-reset" in text
assert "startup-history-import" in text