⚓ firstmate field guide
Reference

Harness integration

What each supported harness needs, which files wire it in, how it stays supervised, and which harnesses can serve as primary, crewmate, secondmate or scout.

firstmate is vendor-agnostic. .agents/skills/harness-adapters/ routes every harness-specific fact, with per-vendor references under references/harness/. It carries one non-negotiable rule: never dispatch on an unverified adapter. If detection returns unknown, the first mate asks you.

Support matrix#

Harness Primary Crewmate Secondmate Scout
Claude Code (claude) ✓ co-primary ✓ ✓ ✓
Grok (grok) ✓ co-primary ✓ ✓ ✓
Pi (pi, pi-signed) ✓ co-primary ✓ ✓ ✓
Oh My Pi (omp) ✓ ✓ ✓ ✓
Codex (codex) ✓ ✓ ✓ ✓
OpenCode (opencode) ✓ ✓ ✓ ✓
Cursor Agent CLI (cursor) ✓ ✓ ✓ ✓
Kimi (kimi) — ✓ ✓ ✓
Gemini, Muse, Rovo, AGY, Devin — ✓ — ✓

The last row has no primary supervision protocol, so it can't host a secondmate. Kimi is refused on cmux and Orca. Source: docs/configuration.md "Harness support".

Claude Code#

  • Wiring: .claude/settings.json registers these hooks:
    • SessionStart → bin/fm-sessionstart-run.sh
    • PreToolUse seatbelts: fm-arm-pretool-check.sh, fm-cd-pretool-check.sh, fm-subagent-pretool-check.sh
    • UserPromptSubmit → fm-host-mirror.sh
    • Stop → fm-turnend-guard.sh --claude, then fm-claude-stop-autoarm.sh (asyncRewake: true, 28800s timeout)
  • How it stays supervised: on every Stop, the autoarm checks that this is the primary checkout and that it holds state/.lock. It arms the watcher through a single-flight epoch ledger. On an actionable wake it exits 2 with a rewake banner, which Claude delivers as Stop-hook feedback.
  • Model instruction: drain wakes with bin/fm-wake-drain.sh and never re-arm by hand.
  • Workers: config/claude-permission-mode sets bypass (default) or auto. bin/fm-claude-trust.sh pre-registers workspace trust per worktree.
  • /calm needs CLAUDE_CODE_ENABLE_FUNCTION_HOOKS=1.
  • All Claude hooks no-op when GROK_AGENT or GROK_HOOK_EVENT shows that Grok is really driving.

Subscription terms

Kun on running Claude Code under firstmate: "you are still just running the real claude code as-is. zero TOS implication" (2026-08-10 thread). He uses Claude Code for Claude models and Pi for everything else.

Pi / pi-signed#

  • Wiring: tracked .pi/extensions/*.ts auto-load after you approve project trust once per clone:
    • fm-primary-pi-watch.ts — watcher bridge; exposes the fm_watch_arm_pi tool
    • fm-branch-supervision.ts — the in-process supervision branch
    • fm-primary-turnend-guard.ts
    • fm-calm.ts
  • Fallback if the extensions didn't load: restart pi with the extension paths passed via -e.
  • Supervision branch: a second AgentSession in the same process. It absorbs routine wakes and heartbeats and hands outcomes to main. It is on by default once the fleet lock is held. It is Pi-only; it does not run on omp.
  • /supervision-model pins the branch to a cheaper model and effort.
  • FM_PI_HARNESS=pi-signed pi-signed for the signed wrapper.

omp (Oh My Pi)#

  • Wiring: .omp/extensions/ holds fm-primary-omp-watch.ts and the turn-end guard. No trust gate. Start omp with the checkout as cwd. Don't also pass -e, or they load twice.
  • Guard: a blocking session_stop hook compels a continuation, bounded to one per turn by stop_hook_active. This is the strongest guard of any harness.
  • omp needs both extensions trusted; with only one, it fails loudly.

Grok#

  • Wiring: there is no extension. The model arms the watcher itself through Grok's run_terminal_command with background: true. Grok injects a synthetic task_completed message when the arm finishes, and that is the wake.
  • A .grok/hooks/ Stop-hook backstop exists but is not the normal path.
  • Launch with grok --trust once per clone, or run /hooks-trust. Headless grok -p is unsupported as primary.
  • Version trap: Grok 1.0.0 hook processes carry GROK_HOOK_EVENT/GROK_SESSION_ID but not GROK_AGENT. A guard keyed only on the old marker let Claude's auto-arm run synchronously under Grok, and the turn never ended. The docs warn: do not widen the guard to GROK_SESSION_ID, which leaks into child Claude sessions.

Cursor Agent CLI#

  • Wiring: .cursor/hooks.json stop → bin/fm-turnend-guard-cursor.sh.
  • Cursor's stop hook is synchronous, and exit 2 is a silent no-op, so the hook parks: it runs one watcher cycle as its own child and returns a followup_message on an actionable wake. It is bounded by Cursor's loop_limit and by FM_CURSOR_TURNEND_LOOP_CEILING (180).
  • Must launch with --trust, or no project hooks load. Must be interactive: cursor-agent -p has no stop hook.

OpenCode#

  • Wiring: .opencode/plugins/fm-primary-watch-arm.js listens for session.idle, spawns fm-watch-arm.sh --restart, and delivers wakes with client.session.promptAsync. fm-primary-pretool-check.js is the seatbelt.
  • TUI only. opencode run is unsupported as primary.

Codex#

  • There is no background mechanism ("Codex cannot reason while a foreground tool call is running"). The model loops bin/fm-watch-checkpoint.sh --seconds ${FM_CODEX_WATCH_CHECKPOINT:-180}. It exits 124 when quiet.
  • .codex/hooks.json holds the seatbelt and Stop guard.
  • Skills are invoked with $ instead of /: $afk, $bearings.
  • Codex Desktop threads are a companion workflow (firstmate-codexapp skill), not a runtime backend. A thread counts as supervised only once its status-file write is verified.

Kimi#

Kimi has no project-level hooks. A captain-approved global config region in ~/.kimi-code/config.toml (bin/fm-kimi-turnend-hook.sh) gives crew wakes. It is not usable as a primary.

Supervision host (non-Pi primaries)#

The supervision host runs the supervision-branch contract on a headless engine beside your primary (bin/fm-supervision-host.sh). It is on by default for Claude, so no file is needed there. Cursor, OpenCode, omp, Grok and Codex need config/supervision-host. A file saying off disables it on any harness. Each harness's existing arm owner runs the host in place of the raw watcher.

Away Attended
Claude, Cursor ✓ ✓ (via the fm-host-mirror.sh dialog mirror)
OpenCode, omp, Grok, Codex ✓ pass-through

Kun's harness split#

for video generation and real time info, i use grok build. image generation uses codex - this is because of harness capability. for claude models i use claude code - because their TOS does not allow any other harness. everything else is pi. — @kunchenguid, 2026-08-05 thread

Unofficial guide built 2026-09-26 from kunchenguid/firstmate, the AXI repos, and Kun Chen's public posts. The repo moves daily; when this guide and the repo disagree, the repo wins.