gendesign/backend/tests/workers/tasks/test_gas_outlet_sync.py
bot-backend 15757685c9
All checks were successful
Deploy / changes (push) Successful in 7s
Deploy / build-backend (push) Successful in 2m17s
Deploy / build-worker (push) Successful in 3m19s
Deploy / build-frontend (push) Successful in 3m54s
Deploy / deploy (push) Successful in 1m34s
feat(site-finder): Celery + §3 точки выхода газосети (#2119 B2, PR-4/4 — финал формы-6) (#2251)
2026-07-03 04:26:41 +00:00

106 lines
4.5 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

"""Smoke-тесты Celery-обвязки точек выхода газосети (#2119 Фаза B2, PR-4).
- sync_gas_outlet_points зарегистрирована (module в include-списке celery_app);
- beat содержит gas-outlet-points-sync-weekly (еженедельно, вторник);
- таск дважды дёргает лоадер: load_gas_outlet_points → geocode_gas_outlets(apply=True),
каждый шаг graceful (сбой одного не роняет второй) — mock без сети/БД.
"""
from __future__ import annotations
from unittest.mock import patch
def test_task_registered_in_celery_include() -> None:
"""Модуль connection_capacity_sync в include-списке celery_app."""
from app.workers.celery_app import celery_app
assert "app.workers.tasks.connection_capacity_sync" in celery_app.conf.include
def test_beat_schedule_includes_gas_outlet_sync_weekly_tuesday() -> None:
"""gas-outlet-points-sync-weekly зарегистрирована еженедельно во вторник."""
from app.workers import beat_schedule
# build_beat_schedule читает DB → мокаем _build_beat_schedule_from_db,
# чтобы тест не зависел от живого Postgres.
with patch.object(beat_schedule, "_build_beat_schedule_from_db", return_value={}):
schedule = beat_schedule.build_beat_schedule()
assert (
"gas-outlet-points-sync-weekly" in schedule
), f"gas-outlet-points-sync-weekly отсутствует в beat: {sorted(schedule.keys())}"
entry = schedule["gas-outlet-points-sync-weekly"]
assert entry["task"] == "tasks.connection_capacity_sync.sync_gas_outlet_points"
# crontab day_of_week = вторник (2).
assert 2 in entry["schedule"].day_of_week
def test_sync_gas_outlet_points_load_then_geocode() -> None:
"""Таск: load_gas_outlet_points → geocode_gas_outlets(apply=True), оба результата в ответе."""
from app.workers.tasks import connection_capacity_sync as ccs
load_result = {"rows": 1037, "inserted": 10, "updated": 1027}
geo_result = {"candidates": 5, "geocoded": 3, "applied": True}
with (
patch(
"app.services.site_finder.ekgas_outlet_loader.load_gas_outlet_points",
return_value=load_result,
),
patch(
"app.services.site_finder.ekgas_outlet_loader.geocode_gas_outlets",
return_value=geo_result,
) as mock_geo,
patch.object(ccs, "_log_breadcrumb"),
):
out = ccs.sync_gas_outlet_points()
assert out["load"] == load_result
assert out["geocode"] == geo_result
# геокод вызван С apply=True (реальная запись geom на проде).
assert mock_geo.call_args.kwargs.get("apply") is True
def test_sync_gas_outlet_points_geocode_failure_graceful() -> None:
"""Сбой geocode-шага не роняет таск: load-результат сохраняется, geocode → error-словарь."""
from app.workers.tasks import connection_capacity_sync as ccs
load_result = {"rows": 1037, "inserted": 0, "updated": 1037}
with (
patch(
"app.services.site_finder.ekgas_outlet_loader.load_gas_outlet_points",
return_value=load_result,
),
patch(
"app.services.site_finder.ekgas_outlet_loader.geocode_gas_outlets",
side_effect=RuntimeError("DaData quota exhausted"),
),
patch.object(ccs, "_log_breadcrumb"),
):
out = ccs.sync_gas_outlet_points()
assert out["load"] == load_result # шаг 1 не откатывается сбоем шага 2
assert "error" in out["geocode"]
assert "DaData" in out["geocode"]["error"]
def test_sync_gas_outlet_points_load_failure_still_attempts_geocode() -> None:
"""Сбой load-шага не мешает попытке geocode (шаги независимы, каждый graceful)."""
from app.workers.tasks import connection_capacity_sync as ccs
geo_result = {"candidates": 0, "geocoded": 0, "applied": True}
with (
patch(
"app.services.site_finder.ekgas_outlet_loader.load_gas_outlet_points",
side_effect=RuntimeError("ekgas catalog 503"),
),
patch(
"app.services.site_finder.ekgas_outlet_loader.geocode_gas_outlets",
return_value=geo_result,
),
patch.object(ccs, "_log_breadcrumb"),
):
out = ccs.sync_gas_outlet_points()
assert "error" in out["load"]
assert out["geocode"] == geo_result