mirror of
https://github.com/ChuckBuilds/LEDMatrix.git
synced 2026-10-05 14:55:08 +00:00
feat(ipc)!: remove the cache-key mailboxes (control socket stage 5)
The control socket is now the only way the web interface sends the display a command. The display stops reading display_on_demand_request and plugin_error_clear_request, and the web interface stops writing them. - Display: no mailbox poll (MailboxWatch, the 1 s / 0.25 s cadence, _consume_on_demand_request, the deprecation log) and no persisted display_on_demand_processed_id guard; the error publisher reads no clear request. CacheManager.file_signature and MailboxWatch are removed. - A write to either retired key is dropped by CacheManager.save_cache and logged once per writer, naming the plugin from the call stack (or the request's plugin_id), with the API to move to. - Web: on-demand start with no display listening starts the service (when start_service) and sends the request again once the socket answers (45 s, 10 s for a running service without a socket yet); every other failure is a 503 (400 for invalid_args). Stop answers 503 when no display listens, unless stop_service. errors/clear answers 503 with a reason-specific message instead of writing a request; clear_pending is always false. src.ipc.client.should_fall_back is replaced by display_not_listening. - Kept: display_current_state, display_on_demand_state, plugin_runtime_snapshot and the heartbeat (read whenever the socket cannot answer), and display_on_demand_config (the display's resume record). Tests: mailbox-only tests removed (test_on_demand_mailbox.py, the mailbox cadence, file_signature and MailboxWatch tests); tests that injected requests through the mailbox now use the socket queue or a plugin's in-process request. The run-loop harness sends on-demand requests over its fake control socket, so four golden traces change: on-demand starts and stops land at the request instant instead of the next 0.25 s mailbox look (one frame fewer on the screen they end), and in vegas.json within one frame instead of 263 ms, which shifts the later 1 s-throttled WiFi-notice check by under a second. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -12,8 +12,8 @@ frame, so a command is applied:
|
||||
* at the next frame in Vegas (8 ms here, at 125 fps).
|
||||
|
||||
Each test runs the real run() loop on the fake clock of
|
||||
test/_run_loop_harness.py and compares the socket with the mailbox for the
|
||||
same request. The latencies are the fake clock's, so they are exact.
|
||||
test/_run_loop_harness.py. The latencies are the fake clock's, so they are
|
||||
exact. (The file mailbox these were once compared with is gone: stage 5.)
|
||||
"""
|
||||
|
||||
import os
|
||||
@@ -32,13 +32,10 @@ def _event_time(trace, kind):
|
||||
return next(e[0] for e in trace["events"] if e[1] == kind)
|
||||
|
||||
|
||||
def _on_demand_latency(tmp_path, build, via, horizon=40):
|
||||
def _on_demand_latency(tmp_path, build, horizon=40):
|
||||
h = RunLoopHarness(tmp_path, horizon=horizon)
|
||||
build(h)
|
||||
if via == "socket":
|
||||
h.control_socket().post(POSTED, Command.ON_DEMAND_START, {"plugin_id": "weather"})
|
||||
else:
|
||||
h.on_demand_request(POSTED, "mb1", plugin_id="weather")
|
||||
h.control_socket().post(POSTED, Command.ON_DEMAND_START, {"plugin_id": "weather"})
|
||||
trace = h.run()
|
||||
return round(_event_time(trace, "on-demand-start") - POSTED, 3), trace
|
||||
|
||||
@@ -60,18 +57,12 @@ def _vegas(h):
|
||||
h.enable_vegas(cycle=30)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("build, mailbox_latency", [
|
||||
(_static, 0.7), # the next 1 s frame, at t=11
|
||||
(_dwell, 0.2), # the next 0.25 s tick, at t=10.5
|
||||
(_vegas, 0.02), # the next 10-frame check: 80 ms at 125 fps, ~0.4 s on a Pi 4
|
||||
], ids=["static-screen", "dwell", "vegas"])
|
||||
def test_a_socket_command_lands_at_once(tmp_path, build, mailbox_latency):
|
||||
(tmp_path / "s").mkdir()
|
||||
(tmp_path / "m").mkdir()
|
||||
socket_latency, trace = _on_demand_latency(tmp_path / "s", build, "socket")
|
||||
via_mailbox, _ = _on_demand_latency(tmp_path / "m", build, "mailbox")
|
||||
|
||||
assert via_mailbox == pytest.approx(mailbox_latency, abs=0.002)
|
||||
@pytest.mark.parametrize("build", [_static, _dwell, _vegas],
|
||||
ids=["static-screen", "dwell", "vegas"])
|
||||
def test_a_socket_command_lands_at_once(tmp_path, build):
|
||||
# Before stage 2 these waited for the next 1 s frame, the next 0.25 s
|
||||
# dwell tick, or the next 10-frame Vegas check.
|
||||
socket_latency, trace = _on_demand_latency(tmp_path, build)
|
||||
if build is _vegas:
|
||||
# One 8 ms frame: Vegas checks the queue every frame now.
|
||||
assert socket_latency <= 0.008
|
||||
|
||||
Reference in New Issue
Block a user