test: Fix app.py integration tests to prevent pygame window launch and mock display properly

This commit is contained in:
2026-03-16 20:25:58 -07:00
parent 952b73cdf0
commit 28203bac4b

View File

@@ -29,7 +29,9 @@ class TestMain:
patch("engine.app.config") as mock_config, patch("engine.app.config") as mock_config,
patch("engine.app.run_pipeline_mode") as mock_run, patch("engine.app.run_pipeline_mode") as mock_run,
): ):
mock_config.PIPELINE_DIAGRAM = False
mock_config.PRESET = "border-test" mock_config.PRESET = "border-test"
mock_config.PIPELINE_MODE = False
sys.argv = ["mainline.py"] sys.argv = ["mainline.py"]
main() main()
mock_run.assert_called_once_with("border-test") mock_run.assert_called_once_with("border-test")
@@ -40,7 +42,9 @@ class TestMain:
patch("engine.app.config") as mock_config, patch("engine.app.config") as mock_config,
patch("engine.app.list_presets", return_value=["demo", "poetry"]), patch("engine.app.list_presets", return_value=["demo", "poetry"]),
): ):
mock_config.PIPELINE_DIAGRAM = False
mock_config.PRESET = "nonexistent" mock_config.PRESET = "nonexistent"
mock_config.PIPELINE_MODE = False
sys.argv = ["mainline.py"] sys.argv = ["mainline.py"]
with pytest.raises(SystemExit) as exc_info: with pytest.raises(SystemExit) as exc_info:
main() main()
@@ -78,59 +82,49 @@ class TestRunPipelineMode:
"""run_pipeline_mode() uses cached content if available.""" """run_pipeline_mode() uses cached content if available."""
cached = ["cached_item"] cached = ["cached_item"]
with ( with (
patch("engine.app.load_cache", return_value=cached), patch("engine.app.load_cache", return_value=cached) as mock_load,
patch("engine.app.fetch_all") as mock_fetch, patch("engine.app.fetch_all") as mock_fetch,
patch("engine.app.DisplayRegistry.create") as mock_create, patch("engine.app.DisplayRegistry.create") as mock_create,
patch("engine.app.Pipeline") as mock_pipeline_class,
patch("engine.app.effects_plugins"),
patch("engine.app.get_registry"),
patch("engine.app.PerformanceMonitor"),
patch("engine.app.set_monitor"),
patch("engine.app.time.sleep"),
): ):
# Setup mocks to return early
mock_display = Mock() mock_display = Mock()
mock_display.init = Mock()
mock_display.get_dimensions = Mock(return_value=(80, 24)) mock_display.get_dimensions = Mock(return_value=(80, 24))
mock_display.is_quit_requested = Mock(return_value=True)
mock_display.clear_quit_request = Mock()
mock_display.show = Mock()
mock_display.cleanup = Mock()
mock_create.return_value = mock_display mock_create.return_value = mock_display
mock_pipeline = Mock() try:
mock_pipeline.context = Mock()
mock_pipeline.context.params = None
mock_pipeline.execute = Mock(side_effect=KeyboardInterrupt)
mock_pipeline_class.return_value = mock_pipeline
with pytest.raises(KeyboardInterrupt):
run_pipeline_mode("demo") run_pipeline_mode("demo")
except (KeyboardInterrupt, SystemExit):
pass
# Verify fetch_all was NOT called (cache was used) # Verify fetch_all was NOT called (cache was used)
mock_fetch.assert_not_called() mock_fetch.assert_not_called()
mock_load.assert_called_once()
def test_run_pipeline_mode_creates_display(self): def test_run_pipeline_mode_creates_display(self):
"""run_pipeline_mode() creates a display backend.""" """run_pipeline_mode() creates a display backend."""
with ( with (
patch("engine.app.load_cache", return_value=["item"]), patch("engine.app.load_cache", return_value=["item"]),
patch("engine.app.DisplayRegistry.create") as mock_create, patch("engine.app.DisplayRegistry.create") as mock_create,
patch("engine.app.Pipeline") as mock_pipeline_class,
patch("engine.app.effects_plugins"),
patch("engine.app.get_registry"),
patch("engine.app.PerformanceMonitor"),
patch("engine.app.set_monitor"),
patch("engine.app.time.sleep"),
): ):
mock_display = Mock() mock_display = Mock()
mock_display.init = Mock()
mock_display.get_dimensions = Mock(return_value=(80, 24)) mock_display.get_dimensions = Mock(return_value=(80, 24))
mock_display.is_quit_requested = Mock(return_value=True)
mock_display.clear_quit_request = Mock()
mock_display.show = Mock()
mock_display.cleanup = Mock()
mock_create.return_value = mock_display mock_create.return_value = mock_display
mock_pipeline = Mock() try:
mock_pipeline.context = Mock() run_pipeline_mode("border-test")
mock_pipeline.context.params = None except (KeyboardInterrupt, SystemExit):
mock_pipeline.execute = Mock(side_effect=KeyboardInterrupt) pass
mock_pipeline_class.return_value = mock_pipeline
with pytest.raises(KeyboardInterrupt): # Verify display was created with 'terminal' (preset display for border-test)
run_pipeline_mode("demo")
# Verify display was created with 'terminal' (preset display)
mock_create.assert_called_once_with("terminal") mock_create.assert_called_once_with("terminal")
def test_run_pipeline_mode_respects_display_cli_flag(self): def test_run_pipeline_mode_respects_display_cli_flag(self):
@@ -140,25 +134,20 @@ class TestRunPipelineMode:
with ( with (
patch("engine.app.load_cache", return_value=["item"]), patch("engine.app.load_cache", return_value=["item"]),
patch("engine.app.DisplayRegistry.create") as mock_create, patch("engine.app.DisplayRegistry.create") as mock_create,
patch("engine.app.Pipeline") as mock_pipeline_class,
patch("engine.app.effects_plugins"),
patch("engine.app.get_registry"),
patch("engine.app.PerformanceMonitor"),
patch("engine.app.set_monitor"),
patch("engine.app.time.sleep"),
): ):
mock_display = Mock() mock_display = Mock()
mock_display.init = Mock()
mock_display.get_dimensions = Mock(return_value=(80, 24)) mock_display.get_dimensions = Mock(return_value=(80, 24))
mock_display.is_quit_requested = Mock(return_value=True)
mock_display.clear_quit_request = Mock()
mock_display.show = Mock()
mock_display.cleanup = Mock()
mock_create.return_value = mock_display mock_create.return_value = mock_display
mock_pipeline = Mock() try:
mock_pipeline.context = Mock()
mock_pipeline.context.params = None
mock_pipeline.execute = Mock(side_effect=KeyboardInterrupt)
mock_pipeline_class.return_value = mock_pipeline
with pytest.raises(KeyboardInterrupt):
run_pipeline_mode("demo") run_pipeline_mode("demo")
except (KeyboardInterrupt, SystemExit):
pass
# Verify display was created with CLI override # Verify display was created with CLI override
mock_create.assert_called_once_with("websocket") mock_create.assert_called_once_with("websocket")
@@ -172,25 +161,20 @@ class TestRunPipelineMode:
) as mock_fetch_poetry, ) as mock_fetch_poetry,
patch("engine.app.fetch_all") as mock_fetch_all, patch("engine.app.fetch_all") as mock_fetch_all,
patch("engine.app.DisplayRegistry.create") as mock_create, patch("engine.app.DisplayRegistry.create") as mock_create,
patch("engine.app.Pipeline") as mock_pipeline_class,
patch("engine.app.effects_plugins"),
patch("engine.app.get_registry"),
patch("engine.app.PerformanceMonitor"),
patch("engine.app.set_monitor"),
patch("engine.app.time.sleep"),
): ):
mock_display = Mock() mock_display = Mock()
mock_display.init = Mock()
mock_display.get_dimensions = Mock(return_value=(80, 24)) mock_display.get_dimensions = Mock(return_value=(80, 24))
mock_display.is_quit_requested = Mock(return_value=True)
mock_display.clear_quit_request = Mock()
mock_display.show = Mock()
mock_display.cleanup = Mock()
mock_create.return_value = mock_display mock_create.return_value = mock_display
mock_pipeline = Mock() try:
mock_pipeline.context = Mock()
mock_pipeline.context.params = None
mock_pipeline.execute = Mock(side_effect=KeyboardInterrupt)
mock_pipeline_class.return_value = mock_pipeline
with pytest.raises(KeyboardInterrupt):
run_pipeline_mode("poetry") run_pipeline_mode("poetry")
except (KeyboardInterrupt, SystemExit):
pass
# Verify fetch_poetry was called, not fetch_all # Verify fetch_poetry was called, not fetch_all
mock_fetch_poetry.assert_called_once() mock_fetch_poetry.assert_called_once()
@@ -202,24 +186,20 @@ class TestRunPipelineMode:
patch("engine.app.load_cache", return_value=["item"]), patch("engine.app.load_cache", return_value=["item"]),
patch("engine.app.effects_plugins") as mock_effects, patch("engine.app.effects_plugins") as mock_effects,
patch("engine.app.DisplayRegistry.create") as mock_create, patch("engine.app.DisplayRegistry.create") as mock_create,
patch("engine.app.Pipeline") as mock_pipeline_class,
patch("engine.app.get_registry"),
patch("engine.app.PerformanceMonitor"),
patch("engine.app.set_monitor"),
patch("engine.app.time.sleep"),
): ):
mock_display = Mock() mock_display = Mock()
mock_display.init = Mock()
mock_display.get_dimensions = Mock(return_value=(80, 24)) mock_display.get_dimensions = Mock(return_value=(80, 24))
mock_display.is_quit_requested = Mock(return_value=True)
mock_display.clear_quit_request = Mock()
mock_display.show = Mock()
mock_display.cleanup = Mock()
mock_create.return_value = mock_display mock_create.return_value = mock_display
mock_pipeline = Mock() try:
mock_pipeline.context = Mock()
mock_pipeline.context.params = None
mock_pipeline.execute = Mock(side_effect=KeyboardInterrupt)
mock_pipeline_class.return_value = mock_pipeline
with pytest.raises(KeyboardInterrupt):
run_pipeline_mode("demo") run_pipeline_mode("demo")
except (KeyboardInterrupt, SystemExit):
pass
# Verify effects_plugins.discover_plugins was called # Verify effects_plugins.discover_plugins was called
mock_effects.discover_plugins.assert_called_once() mock_effects.discover_plugins.assert_called_once()