Skip to content

Add Muse support as a native harness - #891

Open
vierja wants to merge 2 commits into
zeronsh:mainfrom
vierja:feat/muse-harness
Open

vierja wants to merge 2 commits into
zeronsh:mainfrom
vierja:feat/muse-harness

Conversation

@vierja

@vierja vierja commented Oct 13, 2026 •

Copy link
Copy Markdown

What

Adds Muse (Meta's muse CLI) as a ninth native harness in Zeron, driven through its own wire — the MSP session-host protocol (muse serve, JSON-RPC 2.0 over stdio) — the same way Codex is driven through its app-server. No ACP adapter in between.

  • HarnessId::Muse (wire name "muse") in zeron-proto.
  • New zeron-harness::MuseHarness (crates/harness/src/muse/):
    • Persistent muse serve host per session: initialize handshake, session/start / session/resume (with fresh-start fallback + notice when a session is gone), turn/start per prompt.
    • Streaming: item/delta / item/completed, session/todoListChanged, session/tokenUsage, session/contextUsage normalized into AgentEvents; completed text is reconciled against streamed deltas so nothing duplicates. turn/completed is the authoritative turn end (deterministic_turn_end).
    • Steering: turn/steer mid-turn (a steer that loses the race with turn end becomes the next turn/start), turn/interrupt on stop, model changes via session/setModel on the live host.
    • Server→client requests: approval/request and userInput/request are receipted immediately, then decided via approval/decide / userInput/answer after round-tripping Zeron's question panel. Unattended sessions (auto-approve / danger sandbox) start with approvalMode: allowAll so no approval ever blocks the queue; DangerFullAccess also launches the host with --disable-sandbox (sandbox posture is fixed at host start on this wire).
    • A leading /skill invocation the host advertises becomes a native MSP skill input part; image attachments are inlined as base64 parts; Zeron's MCP server is injected via session/start config. Command ids are UUIDv7, as the host requires.
    • Catalogs: model/list and skill/list probed over short-lived hosts; skills also surface as slash commands.
  • Registration and naming everywhere a harness appears: engine default_registry (lazy slot mirroring the harness descriptor), harness-update provider table, agent-account slugs/CLI names, install tables (no script installer is known for Muse, so it is manual-only), skill discovery (.agents/skills), UI picker brand mark (new muse-mark.svg), Providers/settings rows, and the README agent list. The workspace uuid dependency gains the v7 feature for MSP command ids.

Deliberate v1 limits

  • Titles: Muse has no tools-off title mode, so it does not claim supports_titles; title generation keeps falling back to the existing title-capable harnesses.
  • Accounts: sign-in stays with muse login; Muse is not added to the Accounts providers until the engine can detect/swap its credentials.
  • Subagent/workflow/reminder items render as spawn chips / are skipped where Zeron has no generic rendering; nested child transcripts are not subscribed yet.

Testing

  • Unit: MSP normalizer (delta/completion reconciliation, tool open/settle, failed turns, todos) and model catalog parsing.
  • Integration (crates/harness/tests/muse.rs, fake muse serve in tests/fixtures/fake-muse.py): echo turn, typed tool calls, failed turn error, native skill part, user-input round-trip, resume fallback notice, live catalog/skills, wire-name round-trip — 8 passed.
  • Ignored live smokes against the real binary (run locally, all passing): model/list catalog and a full echo-provider turn end-to-end through MuseHarness.
  • cargo check --workspace --all-targets clean; clippy clean in the new module; proto (76), engine registry (18), harness lib, and UI settings/pickers suites pass. Two timing tests in unrelated subsystems (executable version probe, harness-update installer) flake under full parallel load on this machine and pass in isolation.

View with [code]smith Autofix with [code]smith
Need help on this PR? Tag @codesmith-bot with what you need.

Javier Rey and others added 2 commits October 13, 2026 09:27
Drive Meta's Muse CLI through its MSP session-host protocol
(`muse serve`, JSON-RPC 2.0 over stdio), the same way Codex uses its
app-server: persistent host per session, `session/start`/`session/resume`,
`turn/start`/`turn/steer`/`turn/interrupt`, streamed transcript items
normalized into AgentEvents, and approval/user-input server requests
round-tripped through Zeron's question panel. Unattended sessions start
with approvalMode allowAll; model changes ride `session/setModel` on the
live host; a leading /skill invocation becomes a native MSP skill part;
Zeron's MCP server is injected via session config.

Registers HarnessId::Muse (wire: "muse") in the engine's default
registry, harness-update/account naming, install and skill-discovery
tables, and the UI picker/settings surfaces with a Muse brand mark.
Titles stay on the existing title-capable harnesses (Muse has no
tools-off title mode), and account sign-in stays with `muse login`.

Tests: MSP normalize/catalog units, a fake-`muse serve` integration
suite (echo, tools, failure, skill parts, user input, resume fallback,
live catalog), plus ignored live smokes against the real binary.
The engine injects Zeron's MCP server into every real run, and the
host rejects session/start with capabilityRequired unless the
sessionMcp capability was requested at initialize — the handshake
sent none, so every real run failed during setup. Worse, the runner
only emitted an error Done for an already-active turn, so setup
failures closed the stream silently and the engine reported
'harness stream ended without Done'.

- Request sessionMcp in the initialize capabilities.
- If a host still refuses the MCP config, retry session/start
  without it and note the degraded session in the transcript.
- Track done_pending from run start (not from turn start) so any
  failure before the first turn still terminates with an error
  Done; parked sessions that end between turns stay silent.
- The fake host now enforces the capability, and both the fake and
  live suites run with an injected MCP server like the engine.
- Replace the placeholder spark icon with the Meta mark, tinted
  Meta blue like Claude's brand-orange treatment.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant