You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
A slow-but-alive CLI backend was mistaken for a failure: the orchestrator
backgrounded run.mjs and gave up on a ~15s blind poll, even though the CLI
answered seconds later within run.mjs's own (generous) timeout. The fix adds
liveness signalling and corrects how the relay waits.
- run.mjs: wrap each backend invoke() with a heartbeat — emit a
"[mmt] backend '<be>' still running (Ns)…" stderr line every 10s and
maintain a status file ({state:"running"|"done"|"failed", backend,
elapsed_ms, …}) at a PREDICTABLE path: "<call-file>.status.json" when
--call-file is used, else .mmt/calls/<callId>.status.json. stopHeartbeat is
called on every terminal branch (quota / fail / success). All best-effort:
the tick is fully try/catch-guarded (incl. an EPIPE-safe stderr write) so it
can never throw out of the interval or affect the dispatch; the timer is
unref'd so it never keeps the process alive. Generous timeouts unchanged —
observability added, not shortened.
- Relay guidance (workflows/team.mjs + reasoning.mjs, commands/team.md +
reasoning.md, generated agents/*.md): instruct the relay to run run.mjs
FOREGROUND and WAIT — no backgrounding, no self-imposed sleep/timeout/tail -f,
re-run and keep waiting on the relay shell's own time limit, and poll the
status file to confirm liveness. A slow response is explicitly NOT a failure.
- Tests: 93/93 offline (was 91) — a failed-call status:"failed" assertion on
the existing fake-CLI harness, a --call-file success status:"done" test, and
foreground-wait + status-file markers in workflows.test.mjs. Docs/badge -> 93.
Codex-verified: live heartbeat fires at 10s on a 12s fake CLI; codex
code-reviewed the diff, flagged one [Medium] (unguarded stderr write in the
tick), which was fixed, and a focused re-review returned PASS.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
"description": "Delegates token-heavy, self-contained tasks to local CLI backends chosen by task size and type, with credit-exhaustion fallback through the backend chain to native Claude and a glanceable statusline HUD. Routing and shipped backend behavior are configured in config/roster.json; adding a new backend kind requires invoker and health support in code. /team runs a decompose → dispatch → verify → fix → synthesize pipeline; an optional config-gated UserPromptSubmit hook can proactively nudge delegation.",
Copy file name to clipboardExpand all lines: agents/agy.md
+7Lines changed: 7 additions & 0 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -47,6 +47,13 @@ You are the **agy** dispatcher for the multi-model-team plugin. You do **not** s
47
47
- If the task references a local file/dir the backend should read itself, add
48
48
`--add-dir "<dir>"` so the backend reads it on its own quota instead of through Claude.
49
49
- Do NOT inline the task on the command line and do NOT add commentary to the prompt.
50
+
-**Run it in the FOREGROUND and WAIT.** The agy CLI can take several minutes on a
51
+
hard task; run.mjs blocks until it finishes (it has its own generous timeout). Do NOT
52
+
background it (no `&`, no `run_in_background`), do NOT wrap it in your own
53
+
`sleep`/`timeout`/`tail -f`, and do NOT give up early — a slow response is NOT a failure.
54
+
If your shell hits its own time limit, run the SAME command again and keep waiting; run.mjs
55
+
emits a `[mmt] backend still running (Ns)…` heartbeat to stderr and writes a
56
+
`<call-file>.status.json` ({state:"running"|"done"|"failed"}) you can read to confirm it's alive.
50
57
4. Interpret the output:
51
58
- If stdout begins with `MMT_NATIVE_HANDOFF`, the **agy** CLI was unavailable/exhausted (it fell through the fallback chain) — return that sentinel verbatim so the orchestrator (Opus/Sonnet) handles it in-context.
52
59
- Otherwise stdout **is** the delegated result. Return it **verbatim** — no analysis, no
Copy file name to clipboardExpand all lines: agents/codex.md
+7Lines changed: 7 additions & 0 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -47,6 +47,13 @@ You are the **codex** dispatcher for the multi-model-team plugin. You do **not**
47
47
- If the task references a local file/dir the backend should read itself, add
48
48
`--add-dir "<dir>"` so the backend reads it on its own quota instead of through Claude.
49
49
- Do NOT inline the task on the command line and do NOT add commentary to the prompt.
50
+
-**Run it in the FOREGROUND and WAIT.** The codex CLI can take several minutes on a
51
+
hard task; run.mjs blocks until it finishes (it has its own generous timeout). Do NOT
52
+
background it (no `&`, no `run_in_background`), do NOT wrap it in your own
53
+
`sleep`/`timeout`/`tail -f`, and do NOT give up early — a slow response is NOT a failure.
54
+
If your shell hits its own time limit, run the SAME command again and keep waiting; run.mjs
55
+
emits a `[mmt] backend still running (Ns)…` heartbeat to stderr and writes a
56
+
`<call-file>.status.json` ({state:"running"|"done"|"failed"}) you can read to confirm it's alive.
50
57
4. Interpret the output:
51
58
- If stdout begins with `MMT_NATIVE_HANDOFF`, the **codex** CLI was unavailable/exhausted (it fell through the fallback chain) — return that sentinel verbatim so the orchestrator (Opus/Sonnet) handles it in-context.
52
59
- Otherwise stdout **is** the delegated result. Return it **verbatim** — no analysis, no
Copy file name to clipboardExpand all lines: package.json
+1-1Lines changed: 1 addition & 1 deletion
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,6 @@
1
1
{
2
2
"name": "multi-model-team",
3
-
"version": "0.7.4",
3
+
"version": "0.7.5",
4
4
"type": "module",
5
5
"private": true,
6
6
"description": "Delegates token-heavy, self-contained tasks to local CLI backends (agy/Gemini, codex) chosen by task size and type, with credit-exhaustion fallback to native Claude and a statusline HUD. Node ESM, zero-build, cross-platform (Windows/Linux/macOS).",
0 commit comments