from __future__ import annotations import unittest from contextlib import contextmanager from types import SimpleNamespace from unittest.mock import patch from govoplan_core.celery_app import ( celery, dispatch_mail_outbox, purge_mail_outbox, ) class _Provider: def dispatch_due(self, session, **kwargs): return {"session": session, **kwargs} def purge_expired(self, session, **kwargs): return {"session": session, **kwargs} class MailDeliveryWorkerTests(unittest.TestCase): def test_dispatch_uses_optional_provider_boundary(self) -> None: session = object() @contextmanager def session_scope(): yield session database = SimpleNamespace(SessionLocal=session_scope) with ( patch("govoplan_core.db.session.get_database", return_value=database), patch( "govoplan_core.celery_app._mail_delivery_outbox", return_value=_Provider(), ), ): result = dispatch_mail_outbox.run("tenant-1", 7) self.assertIs(result["session"], session) self.assertEqual(result["tenant_id"], "tenant-1") self.assertEqual(result["limit"], 7) def test_purge_uses_optional_provider_boundary(self) -> None: session = object() @contextmanager def session_scope(): yield session database = SimpleNamespace(SessionLocal=session_scope) with ( patch("govoplan_core.db.session.get_database", return_value=database), patch( "govoplan_core.celery_app._mail_delivery_outbox", return_value=_Provider(), ), ): result = purge_mail_outbox.run(19) self.assertIs(result["session"], session) self.assertEqual(result["limit"], 19) def test_worker_routes_and_schedules_are_declared(self) -> None: self.assertEqual( celery.conf.task_routes["govoplan.mail.dispatch_outbox"], {"queue": "mail"}, ) self.assertEqual( celery.conf.task_routes["govoplan.mail.purge_outbox"], {"queue": "mail"}, ) self.assertEqual( celery.conf.beat_schedule["mail-outbox-every-five-seconds"]["task"], "govoplan.mail.dispatch_outbox", ) self.assertEqual( celery.conf.beat_schedule["mail-outbox-retention-daily"]["task"], "govoplan.mail.purge_outbox", ) if __name__ == "__main__": unittest.main()