refactor(#2290): replace mcp_sockets poll with event-driven register_agent

mara: the background worker is redundant if c0re knows when its own
sockets go missing. damocles: 10s poll latency and redundancy are two
faces of the same issue — poll adds a reconnect window and does
redundant work when c0re could react directly.

design: c0re owns the MCP listener lifecycle, so the only time a
listener disappears without c0re knowing is when c0re itself restarts.

- replace spawn_poll (recurring 10s loop) with sync_on_start (one-shot
  sweep at daemon boot): re-registers all running agents on startup
  after /run/hyperhive/agents/ is cleared by the tmpfs reset.
- run_reconcile (reconcile-start path): add coord.register_agent(name)
  immediately after start_with_fallback — event-driven, no poll delay.
- run_create already calls register_agent eagerly; kill/destroy paths
  already call unregister_agent — no changes needed there.

tracker: #2290
This commit is contained in:
atlas 2026-07-09 00:54:37 +02:00
commit 73f1020a7e
3 changed files with 38 additions and 43 deletions

View file

@ -420,13 +420,13 @@ async fn cmd_serve(
// is one stat per agent per tick.
// See `docs/gateway.md::Per-agent unix-socket upstream`.
agent_sockets::spawn_poll();
// MCP socket listener reconcile loop: every 10s re-registers any
// running agent that lost its host-side MCP listener (e.g. after a
// hive-c0re restart cleared /run/hyperhive/agents/). First tick fires
// immediately so restarts re-register all running agents without delay.
// Decouples listener registration from the start path — start only needs
// lifecycle::ensure_agent_runtime_dir; the supervisor converges the rest.
mcp_sockets::spawn_poll(coord.clone());
// MCP socket listener startup sync: one-shot sweep that re-registers any
// running agent container whose MCP listener was lost when hive-c0re
// restarted (Coordinator starts empty; /run/hyperhive/agents/ is tmpfs).
// After this, listener registration is event-driven: run_create /
// run_reconcile call register_agent on start; kill/destroy call
// unregister_agent. No recurring poll needed — c0re owns the listeners.
mcp_sockets::sync_on_start(coord.clone()).await;
// Reminder scheduler: drains due reminders + handles
// file_path payload persistence. See reminder_scheduler.rs.
reminder_scheduler::spawn(coord.clone());