Download
Docs/More/Examples

Examples

Worked transcripts of every flow — cold start, the orchestrator loop, the worker side, fan-out, and the rails you will hit.

Raw markdown

Every flow below ran against a real deck (2026-09-01, v0.1.3 tree) and behaved exactly as shown. Routes and params are canonical in AGENTS.md; this file is the doing companion. $M is the CLI (mandeck on PATH, or fetch it: curl -so /tmp/mandeck http://127.0.0.1:7717/cli/mandeck && chmod +x /tmp/mandeck).

0. Cold start — you know only a port

curl -s http://127.0.0.1:7717/v1/health
# {"ok":true,"app":"mandeck","docs":"/agents.md","state":"dev.mandeck.native", ...}
#                                  └── read this      └── token lives at
#                                                        ~/Library/Application Support/<state>/cli-token
curl -s http://127.0.0.1:7717/agents.md          # the full contract, port-corrected
TOKEN=$(cat "$HOME/Library/Application Support/dev.mandeck.native/cli-token")

1. The orchestrator loop — spawn, wait, report

JOB=$(mandeck job spawn claude-code --dir ~/myrepo -p "fix the failing test" \
        --check-after 30 | cut -f1)         # job-id \t session \t pane
mandeck job wait "$JOB" --timeout 1200      # blocks; exit 0=done 2=failed 3=waiting-you 4=timeout
case $? in
  0) mandeck job report "$JOB" ;;           # transcript + screen — summarize this to your user
  3) mandeck screen "$JOB" 30               # it asked a question — read it,
     mandeck job send "$JOB" "yes, use bun" ;;  # answer it, wait again
  4) mandeck screen "$JOB" 30 ;;            # still running — honest timeout, look before deciding
esac

Rules that make this work (all enforced, all verified):

  • done/failed come ONLY from explicit signals. Silence, an idle prompt, live:false, unfocus, pane close — none of them finish a job.
  • Mentioning [mandeck job-done] mid-sentence does NOT finish a job; the token must start its own line.
  • Set --check-after longer than your wait timeout, or the follow-up contract reminds you mid-wait (by design; job report settles it).

2. The worker side — you are the spawned agent

Every API-spawned pane exports MANDECK_PANE (your identity) and MANDECK_JOB (the job you owe). Finish honestly:

mandeck job done          # no id needed — $MANDECK_JOB is read
mandeck job fail          # the work errored; say so, don't fake done
echo "[mandeck job-done]" # equivalent: the token alone on its own line

Hand work onward and the follow-up contract makes you own it: spawn with --spawner "$MANDECK_PANE" (the CLI sends it automatically) and the deck will type a [mandeck follow-up] reminder into YOUR pane if you never check the result.

3. Fan out — one task, every repo

mandeck fanout claude-code "bump deps and run tests" ~/api ~/web ~/cli
# one pane per repo, all in one tab, each with the follow-up contract
mandeck waiting            # which panes need an answer

--force spawns even where a live pane already holds that agent+cwd; without it you get already live plus the existing session to reuse (409).

4. MCP instead of shell

{ "mcpServers": { "mandeck": { "command": "node",
    "args": ["/path/to/mandeck-mcp.mjs"] } } }

Fetch the server from a running deck: GET /cli/mandeck-mcp.mjs. 23 tools, 1:1 with the routes — deck_spawn, deck_job_wait, deck_job_report, deck_screen, deck_send, deck_key, deck_events, … Same token file, same loopback-only reach.

5. Safety rails you will hit (by design)

mandeck job spawn shell                    # ✗ job spawn requires --dir (no default $HOME/$PWD)
mandeck job spawn shell --dir ~/x          # second time: ✗ 409 "already live" + existing session
mandeck job done                           # outside a tasked pane: ✗ usage (no $MANDECK_JOB)
curl -X POST .../v1/jobs/<done-job> -d '{"state":"failed"}'   # ✗ 409 "job already done"

6. Testing without touching the live deck

./scripts/devtest.sh up      # own state dir, own port (7729), own ~/.mandeck
MANDECK_API_PORT=7729 MANDECK_STATE_DIR=dev.mandeck.native.devtest mandeck ps
./scripts/devtest.sh down    # quits and wipes its state

The served /agents.md on a test instance rewrites its examples to the test port, so nothing you copy-paste from it reaches the live deck.