jarvis / tests /test_runtime_entrypoint.py
Jonathan Haas
refactor: extract cli entrypoint orchestration helpers
61cd78a
Raw
History Blame Contribute Delete
3.41 kB
from __future__ import annotations
from types import SimpleNamespace
from unittest.mock import patch
import pytest
from jarvis.runtime_entrypoint import (
maybe_run_backup_or_restore,
run_jarvis_event_loop,
)
def test_maybe_run_backup_or_restore_returns_false_when_no_maintenance_args() -> None:
args = SimpleNamespace(backup=None, restore=None, force=False)
ran = maybe_run_backup_or_restore(
args,
config_class=lambda: object(),
create_backup_bundle_fn=lambda config, path: {},
restore_backup_bundle_fn=lambda config, path, overwrite=False: {},
)
assert ran is False
def test_maybe_run_backup_or_restore_backup_prints_result(capsys) -> None:
args = SimpleNamespace(backup="/tmp/backup.zip", restore=None, force=False)
ran = maybe_run_backup_or_restore(
args,
config_class=lambda: object(),
create_backup_bundle_fn=lambda config, path: {"ok": True, "path": path},
restore_backup_bundle_fn=lambda config, path, overwrite=False: {},
)
captured = capsys.readouterr()
assert ran is True
assert '"ok": true' in captured.out.lower()
assert "/tmp/backup.zip" in captured.out
def test_maybe_run_backup_or_restore_failure_raises_system_exit(capsys) -> None:
args = SimpleNamespace(backup="/tmp/backup.zip", restore=None, force=False)
with pytest.raises(SystemExit) as exc_info:
maybe_run_backup_or_restore(
args,
config_class=lambda: object(),
create_backup_bundle_fn=lambda config, path: (_ for _ in ()).throw(RuntimeError("boom")),
restore_backup_bundle_fn=lambda config, path, overwrite=False: {},
)
captured = capsys.readouterr()
assert exc_info.value.code == 1
assert '"ok": false' in captured.out.lower()
assert "boom" in captured.out
def test_run_jarvis_event_loop_bootstraps_and_cleans_up() -> None:
class _FakeTask:
def __init__(self) -> None:
self.cancelled = False
def cancel(self) -> None:
self.cancelled = True
class _FakeLoop:
def __init__(self) -> None:
self.calls: list[object] = []
self.task = _FakeTask()
self.closed = False
def create_task(self, coro):
self.calls.append(("create_task", coro))
return self.task
def run_until_complete(self, awaitable):
self.calls.append(("run_until_complete", awaitable))
return None
def shutdown_asyncgens(self):
return "shutdown_asyncgens"
def shutdown_default_executor(self):
return "shutdown_default_executor"
def close(self):
self.closed = True
fake_loop = _FakeLoop()
jarvis = SimpleNamespace(run=lambda: "run-coro")
signal_calls: list[tuple[object, object]] = []
with patch("jarvis.runtime_entrypoint.asyncio.new_event_loop", return_value=fake_loop), \
patch("jarvis.runtime_entrypoint.asyncio.set_event_loop") as set_event_loop, \
patch("jarvis.runtime_entrypoint.signal.signal", side_effect=lambda sig, handler: signal_calls.append((sig, handler))):
run_jarvis_event_loop(jarvis)
set_event_loop.assert_called_once_with(fake_loop)
assert fake_loop.closed is True
assert any(call[0] == "create_task" for call in fake_loop.calls)
assert len(signal_calls) >= 1