@mu-crew/mu 3.9.0 → 3.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/chunk-4PACTXAB.js +17 -0
- package/dist/chunk-4PACTXAB.js.map +1 -0
- package/dist/chunk-77GBZ2KR.js +85 -0
- package/dist/chunk-77GBZ2KR.js.map +1 -0
- package/dist/chunk-7OQNJWBY.js +391 -0
- package/dist/chunk-7OQNJWBY.js.map +1 -0
- package/dist/chunk-PZ5AY32C.js +10 -0
- package/dist/chunk-PZ5AY32C.js.map +1 -0
- package/dist/chunk-WT7IN2OD.js +9887 -0
- package/dist/chunk-WT7IN2OD.js.map +1 -0
- package/dist/chunk-XXK7FR37.js +640 -0
- package/dist/chunk-XXK7FR37.js.map +1 -0
- package/dist/chunk-YIF3X32A.js +2792 -0
- package/dist/chunk-YIF3X32A.js.map +1 -0
- package/dist/cli-UZEMPIPW.js +6266 -0
- package/dist/cli-UZEMPIPW.js.map +1 -0
- package/dist/cli.js +37 -26127
- package/dist/cli.js.map +1 -1
- package/dist/extension/mu-pi.js +129 -103
- package/dist/extension/mu-pi.js.map +1 -1
- package/dist/index.d.ts +108 -53
- package/dist/index.js +324 -11728
- package/dist/index.js.map +1 -1
- package/dist/tui-X2XICJTN.js +6452 -0
- package/dist/tui-X2XICJTN.js.map +1 -0
- package/dist/tui-sync-worker.js +16 -0
- package/dist/tui-sync-worker.js.map +1 -0
- package/dist/yank-T3AYQTVR.js +12 -0
- package/dist/yank-T3AYQTVR.js.map +1 -0
- package/docs/ARCHITECTURE.md +9 -3
- package/docs/architecture/control-socket.md +5 -1
- package/docs/architecture/sync.md +18 -4
- package/docs/guide/dispatch.md +4 -0
- package/docs/guide/sql.md +1 -1
- package/docs/reference/env.md +2 -1
- package/package.json +1 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/cli.ts","../src/cli/agents.ts","../src/shell-quote.ts","../src/cli/dispatch-hints.ts","../src/cli/staleness.ts","../src/cli/handle.ts","../src/cli/stdin.ts","../src/cli/agents-remote.ts","../src/cli/tasks/edit.ts","../src/cli/tasks/queries.ts","../src/cli/tasks/claim.ts","../src/cli/tasks/edges.ts","../src/cli/tasks/lifecycle.ts","../src/cli/tasks/tree.ts","../src/cli/tasks/wire.ts","../src/cli/db.ts","../src/compact.ts","../src/disk-recon.ts","../src/cli/doctor.ts","../src/dormant.ts","../src/cli/link.ts","../src/cli/log.ts","../src/cli/rebuild.ts","../src/cli/sql.ts","../src/cli/tui-launch-focus.ts","../src/project-root.ts","../src/cli/tui-load.ts","../src/cli/state.ts","../src/cli/sync.ts","../src/cli/undo.ts","../src/cli/workspace.ts","../src/cli/workstream.ts"],"sourcesContent":["// mu — command-line interface.\n//\n// One namespace/command per verb group (see `mu --help` for the current\n// list), each registered via commander as a thin wrapper around the\n// corresponding programmatic function in src/. The real work happens in\n// agents.ts, tasks.ts, tracks.ts, db.ts, mux.ts; this file is just\n// argument parsing, output formatting, and error-to-exit-code\n// translation.\n//\n// Layout: cli.ts is the wiring root. Pure rendering helpers live in\n// `src/cli/format.ts`; typed-error → exit-code mapping + the `handle`\n// wrapper live in `src/cli/handle.ts` (extracted by\n// review_cli_ts_past_refactor_signal). cli.ts re-exports their public\n// surface so existing tests + cli/* importers don't need to change\n// import paths. The exit-code catalogue is documented at the top of\n// `src/cli/handle.ts`.\n\nimport { readFileSync } from \"node:fs\";\nimport { dirname, join } from \"node:path\";\nimport { fileURLToPath } from \"node:url\";\nimport { Command, InvalidArgumentError } from \"commander\";\n\nimport { AgentNotInWorkstreamError, type AgentRow, getAgentByPane } from \"./agents.js\";\nimport { wireAgentCommands, wireSelfCommands } from \"./cli/agents.js\";\nimport { wireDbCommands } from \"./cli/db.js\";\nimport { wireDoctorCommand } from \"./cli/doctor.js\";\nimport {\n emitParseError,\n findCommandForArgv,\n handle,\n NameAmbiguousError,\n UsageError,\n} from \"./cli/handle.js\";\nimport { wireLinkCommand } from \"./cli/link.js\";\nimport { wireLogCommand } from \"./cli/log.js\";\nimport { wireRebuildCommand } from \"./cli/rebuild.js\";\nimport { wireSqlCommand } from \"./cli/sql.js\";\nimport { printBareNoWorkstreamsHint, wireStateCommands } from \"./cli/state.js\";\nimport { wireSyncCommand } from \"./cli/sync.js\";\nimport { wireTaskCommands } from \"./cli/tasks.js\";\nimport { resolveInitialTab } from \"./cli/tui-launch-focus.js\";\nimport { importTui } from \"./cli/tui-load.js\";\nimport { wireUndoCommand } from \"./cli/undo.js\";\nimport { wireWorkspaceCommands } from \"./cli/workspace.js\";\nimport { wireWorkstreamCommands } from \"./cli/workstream.js\";\nimport { type Db, WorkstreamNotFoundError } from \"./db.js\";\nimport { isTaskSortKey, TASK_SORT_KEYS, type TaskSortKey } from \"./tasks/sort.js\";\nimport { TASK_SUBSTATES, type TaskSubstate } from \"./tasks/status.js\";\nimport {\n isTaskStatus,\n TASK_STATUS_LIST,\n TaskNotInWorkstreamError,\n type TaskRow,\n type TaskStatus,\n} from \"./tasks.js\";\nimport { listWorkstreams, resolveMuxSessionWorkstreamName } from \"./workstream.js\";\n\n// ─── Re-exports for downstream cli/* modules ──────────────────────────\n//\n// Pure rendering helpers and the typed-error catalogue live in\n// `src/cli/format.ts` and `src/cli/handle.ts`; cli/* modules import\n// them through `cli.ts` for ergonomic single-import lines.\n\nexport {\n colorPair,\n colorStatus,\n formatAgentsTable,\n formatReadyTable,\n formatTaskListTable,\n formatTornDownWorkstreamsTable,\n formatTracks,\n formatWorkspacesTable,\n formatWorkstreamsTable,\n IDLE_GLYPH,\n printLogRow,\n relTime,\n statusIcon,\n truncate,\n truncateFront,\n} from \"./cli/format.js\";\nexport {\n CliExitError,\n classifyError,\n handle,\n NameAmbiguousError,\n UsageError,\n} from \"./cli/handle.js\";\nexport {\n byRoiDesc,\n isTaskSortKey,\n relTimeBasisForSort,\n sortTasks,\n TASK_SORT_KEYS,\n type TaskSortKey,\n} from \"./tasks/sort.js\";\n\n// ─── Workstream resolution ─────────────────────────────────────────────\n\n/**\n * Resolve the active workstream. Order:\n * 1. --workstream <name> flag\n * 2. $MU_SESSION env var\n * 3. Current tmux session name (with `mu-` prefix stripped)\n *\n * Throws UsageError if none of the above produce a name, or if the\n * explicit value is BLANK (whitespace-only). The blank check lives\n * here as well as in parseCsvFlag because the single-value `-w <name>`\n * shape never passes through the CSV helper: without it,\n * `mu task list -w ' '` resolved to the workstream named \" \" and\n * rendered an empty table instead of erroring\n * (bug_whitespace_status_fragment, adjacent hole).\n */\nexport async function resolveWorkstream(explicit?: string): Promise<string> {\n if (explicit !== undefined && explicit.length > 0 && explicit.trim().length === 0) {\n throw new UsageError(\n `-w/--workstream got a blank (whitespace-only) value ${JSON.stringify(explicit)}. Pass a workstream name, or omit the flag to use $MU_SESSION / the current tmux session.`,\n );\n }\n if (explicit) return explicit;\n if (process.env.MU_SESSION) return process.env.MU_SESSION;\n const tmuxWorkstream = await resolveMuxSessionWorkstreamName();\n if (tmuxWorkstream !== null) return tmuxWorkstream;\n throw new UsageError(\n \"workstream required: pass --workstream <name>, set $MU_SESSION, or run inside an mu-<name> tmux session\",\n );\n}\n\n/** Like resolveWorkstream but returns null instead of throwing on miss.\n * Used by read-permissive verbs (mu log, mu state).\n * where 'no workstream' is a legitimate state to render. */\nexport async function resolveOptionalWorkstream(): Promise<string | null> {\n try {\n return await resolveWorkstream(undefined);\n } catch {\n return null;\n }\n}\n\n// ─── Qualified entity refs (cross-workstream verb args) ────────────────\n//\n// Every verb that takes an entity name (mu task show <id>, mu agent\n// send <name>, mu workspace path <agent>) accepts EITHER:\n// - bare `<name>` → resolves via current workstream context\n// - qualified `<ws>/<name>` → resolves directly, no -w needed\n// Implemented as a parse-at-CLI-entry helper so the SDK signatures\n// stay workstream-explicit (no entity ref shape leaks below cli.ts).\n// See verb_arg_qualified_workstream_name and the OUTPUT_LABELS_AUDIT.\n\nexport interface ParsedRef {\n /** Workstream prefix when the input was `<ws>/<name>`; undefined for\n * bare names. */\n workstream?: string;\n /** The bare name (everything after the first '/' if qualified, else\n * the whole input). */\n name: string;\n}\n\n/** Split `<ws>/<name>` on the FIRST '/'. Bare input → workstream=undefined.\n * Names today are restricted to [a-z0-9_-] (slugify / agent name validator)\n * so '/' is unambiguous: no entity name can contain it. */\nexport function parseQualifiedRef(raw: string): ParsedRef {\n const slash = raw.indexOf(\"/\");\n if (slash === -1) return { name: raw };\n return { workstream: raw.slice(0, slash), name: raw.slice(slash + 1) };\n}\n\n/** Sync glue: parse a qualified ref and (if qualified) push the\n * workstream onto opts.workstream. Throws UsageError when the caller\n * passed BOTH `--workstream A` AND `B/<name>` and they disagree.\n * Returns the bare name for downstream use. Mutates opts. */\nexport function applyQualifiedRef(raw: string, opts: { workstream?: string }): string {\n const parsed = parseQualifiedRef(raw);\n if (parsed.workstream === undefined) return raw;\n if (opts.workstream !== undefined && opts.workstream !== parsed.workstream) {\n throw new UsageError(\n `qualified ref ${JSON.stringify(raw)} (workstream=${parsed.workstream}) conflicts with --workstream ${opts.workstream}`,\n );\n }\n opts.workstream = parsed.workstream;\n return parsed.name;\n}\n\n/** Per-entity table+key+error mapping for findEntityWorkstreams /\n * resolveEntityRef. Centralised so adding a new entity is one row. */\nconst ENTITY_TABLES = {\n task: { table: \"tasks\", keyCol: \"local_id\" },\n agent: { table: \"agents\", keyCol: \"name\" },\n // workspace: lookup is by agent name (vcs_workspaces has agent_id\n // FK; the operator-facing key is the agent name in `agents`).\n workspace: { table: \"agents\", keyCol: \"name\" },\n} as const;\n\nexport type EntityKind = keyof typeof ENTITY_TABLES;\n\n/** List the workstream names where `entity` exists. Used for ambiguity\n * detection when the bare-name caller has no resolved -w context. */\nexport function findEntityWorkstreams(db: Db, kind: EntityKind, name: string): string[] {\n const { table, keyCol } = ENTITY_TABLES[kind];\n const rows = db\n .prepare(\n `SELECT ws.name AS workstream FROM ${table} t\n JOIN workstreams ws ON ws.id = t.workstream_id\n WHERE t.${keyCol} = ?\n ORDER BY ws.name`,\n )\n .all(name) as { workstream: string }[];\n return rows.map((r) => r.workstream);\n}\n\n/**\n * One-stop ref resolver for verbs taking an entity name + optional -w.\n *\n * Pipeline:\n * 1. Parse `<ws>/<name>` (qualified form) — sets opts.workstream\n * from the prefix and returns the bare name.\n * 2. Resolve workstream from --workstream / $MU_SESSION / tmux\n * session (the standard chain in resolveWorkstream).\n * 3. When no workstream resolves AND the bare name lives in ≥2\n * workstreams: throw NameAmbiguousError listing the candidates.\n * When it lives in exactly 1: use that workstream (still bare).\n * When it lives in 0: rethrow the original UsageError so the\n * operator sees the canonical 'workstream required' message.\n *\n * Returns `{ name, workstream }`. The verb then uses `name` for the\n * entity lookup and `workstream` for downstream SDK calls; opts.workstream\n * is mutated to match (so existing helpers like assertTaskInWorkstream\n * still work as the second-line check).\n */\nexport async function resolveEntityRef(\n db: Db,\n raw: string,\n opts: { workstream?: string },\n kind: EntityKind,\n): Promise<{ name: string; workstream: string }> {\n const name = applyQualifiedRef(raw, opts);\n try {\n const workstream = await resolveWorkstream(opts.workstream);\n return { name, workstream };\n } catch (err) {\n // Bare-name + no resolved context: try ambiguity disambiguation.\n if (!(err instanceof UsageError)) throw err;\n const matches = findEntityWorkstreams(db, kind, name);\n if (matches.length >= 2) throw new NameAmbiguousError(name, matches, kind);\n if (matches.length === 1) {\n const only = matches[0];\n if (only !== undefined) {\n opts.workstream = only;\n return { name, workstream: only };\n }\n }\n throw err;\n }\n}\n\n/** Standard --status validation: case-insensitive, returns the\n * canonical TaskStatus or throws UsageError naming every legal\n * value. Centralised so adding a status updates every CLI surface\n * at once (the OPEN | IN_PROGRESS | CLOSED list used to drift\n * across `mu task list --status`, `mu task wait --status`, the\n * --help text, and error messages). Source list lives in\n * src/tasks.ts as TASK_STATUS_LIST. */\nexport function parseStatusOption(raw: string, flag = \"--status\"): TaskStatus {\n const upper = raw.toUpperCase();\n if (!isTaskStatus(upper)) {\n throw new UsageError(`${flag} must be one of ${TASK_STATUS_LIST} (got ${JSON.stringify(raw)})`);\n }\n return upper;\n}\n\n/** Multi-status flag parser for the `--status <s...>` shape used by\n * `mu task list / task next / approve list` (per\n * task_list_multi_status_union). Composes parseCsvFlag (repeat OR\n * comma-separated OR mix) with per-element parseStatusOption\n * validation, then dedups case-insensitively (parseStatusOption\n * upper-cases). Returns `undefined` when the flag is absent or\n * resolves to an empty array — semantically \"no filter\", matching\n * today's no-`--status` shape. Throws UsageError naming the offending\n * element on the first invalid value (so the operator sees which one\n * failed, not just \"some value was wrong\"). */\nexport function parseStatusesOption(\n values: readonly string[] | undefined,\n flag = \"--status\",\n): TaskStatus[] | undefined {\n const fragments = parseCsvFlag(values, flag);\n if (fragments.length === 0) return undefined;\n const seen = new Set<TaskStatus>();\n const out: TaskStatus[] = [];\n for (const raw of fragments) {\n const status = parseStatusOption(raw, flag);\n if (seen.has(status)) continue;\n seen.add(status);\n out.push(status);\n }\n return out;\n}\n\n/** Every substate across all statuses, in canonical order. */\nconst ALL_SUBSTATES: readonly TaskSubstate[] = [...new Set(Object.values(TASK_SUBSTATES).flat())];\n\n/** `--substate <s...>` parser: same repeat/comma shape as\n * parseStatusesOption, validated against every status's substates\n * (case-insensitive, deduped). undefined = no filter. */\nexport function parseSubstatesOption(\n values: readonly string[] | undefined,\n flag = \"--substate\",\n): TaskSubstate[] | undefined {\n const fragments = parseCsvFlag(values, flag);\n if (fragments.length === 0) return undefined;\n const out = new Set<TaskSubstate>();\n for (const raw of fragments) {\n const lower = raw.toLowerCase();\n const match = ALL_SUBSTATES.find((s) => s === lower);\n if (match === undefined) {\n throw new UsageError(\n `${flag} must be one of ${ALL_SUBSTATES.join(\" | \")} (got ${JSON.stringify(raw)})`,\n );\n }\n out.add(match);\n }\n return [...out];\n}\n\n// ─── Self-resolution (current pane → AgentRow) ─────────────────────────\n\n/**\n * Resolve \"the agent running this process\" by reading `$TMUX_PANE` and\n * looking up the matching agent row. Returns null when `$TMUX_PANE` is\n * unset or the pane isn't a managed agent — the lenient variant used\n * by verbs that have a sensible fallback (the calling agent name when\n * resolvable, else a generic 'user' / 'orchestrator'). `resolveSelf`\n * wraps this with the strict throwing variant for verbs that genuinely\n * require a managed-pane caller.\n */\nexport function resolveSelfOptional(db: Db): AgentRow | null {\n const paneId = process.env.TMUX_PANE;\n if (!paneId) return null;\n return getAgentByPane(db, paneId) ?? null;\n}\n\n/**\n * Strict variant of `resolveSelfOptional`: throws UsageError with a\n * helpful message if `$TMUX_PANE` is unset or the pane isn't a\n * managed agent. Used by `mu me` / `mu me tasks` / `mu me next` to give\n * an LLM-in-a-pane zero-config self-identification. Lives in cli.ts\n * so cli/agents.ts and cli/tasks.ts can both import it without a\n * lateral cli/* dependency.\n */\nexport function resolveSelf(db: Db): AgentRow {\n const paneId = process.env.TMUX_PANE;\n if (!paneId) {\n throw new UsageError(\n \"$TMUX_PANE is not set; this verb only works inside an mu-spawned tmux pane (or any tmux pane, but the pane has to be a managed agent)\",\n );\n }\n const agent = resolveSelfOptional(db);\n if (!agent) {\n throw new UsageError(\n `pane ${paneId} is not a managed agent. Use \\`mu agent list\\` to see managed panes, or \\`mu agent spawn\\` to register a new one.`,\n );\n }\n return agent;\n}\n\n// ─── Shared SDK-CLI bridge helpers (used by cli/*.ts) ──────────────\n//\n// These were extracted from inline-with-task-verbs in cli.ts; the\n// task verbs moved to src/cli/tasks.ts but the helpers stay here so\n// every cli/*.ts module can import them from one canonical location.\n\nexport function parseSortOption(raw: string, flag = \"--sort\"): TaskSortKey {\n if (!isTaskSortKey(raw)) {\n throw new UsageError(\n `${flag} must be one of ${TASK_SORT_KEYS.join(\" | \")} (got ${JSON.stringify(raw)})`,\n );\n }\n return raw;\n}\n\n/**\n * Decorate a TaskRow (or array of them) with a computed `roi` field for\n * JSON output. ROI is a CLI-rendering concern (the table view computes\n * it inline; see formatTaskListTable) but JSON consumers were getting\n * raw rows with no ROI at all, which broke `mu task next --json | jq\n * 'sort_by(.roi)'` and similar. We keep `TaskRow` itself ROI-free so\n * the SDK contract stays minimal; the decorator lives only in the JSON\n * emit path.\n *\n * `roi` is a plain JSON number when finite; for effortDays=0 the field\n * is omitted (JSON has no Infinity literal and `null` would be a lie).\n * Callers can detect the infinity case via `effortDays === 0`.\n */\nfunction withRoi<T extends TaskRow>(task: T): T & { roi?: number } {\n if (task.effortDays > 0) {\n return { ...task, roi: task.impact / task.effortDays };\n }\n return task;\n}\n\nexport function withRoiAll<T extends TaskRow>(tasks: T[]): (T & { roi?: number })[] {\n return tasks.map(withRoi);\n}\n\n// ─── Workstream-scope assertions ──────────────────────────────────────\n\n/**\n * Generic workstream-scope assertion. The two typed wrappers\n * (`assertAgentInWorkstream`, `assertTaskInWorkstream`) share this\n * shape: SELECT the `workstream` column from `<table>` WHERE\n * `<keyCol>` = key, and if the row exists with a non-matching\n * workstream throw a typed `*NotInWorkstreamError`. No-op when\n * `expectedWs` is undefined or the row doesn't exist (downstream\n * handlers raise the matching `*NotFoundError`).\n *\n * Doing the lookup directly via raw SQL (rather than through the\n * typed `getAgent` / `getTask`) keeps the helper decoupled from\n * each row's full schema — it only ever needs the one column. The\n * typed errors are constructed by `errFactory` so each caller keeps\n * its specific error class and exit-code mapping.\n */\nexport function assertEntityInWorkstream<E extends Error>(\n db: Db,\n table: string,\n keyCol: string,\n keyVal: string,\n expectedWs: string | undefined,\n errFactory: (keyVal: string, expectedWs: string, actualWs: string | null) => E,\n): void {\n if (!expectedWs) return;\n // v5: per-scope unique TEXT names mean a bare\n // `WHERE keyCol = ? LIMIT 1` could pick the wrong workstream's row\n // and falsely raise NotInWorkstreamError when the expected workstream\n // ALSO has a row of this name (bug_v5_name_clash_silent_misroute).\n // Fast path: if a row exists in the expected workstream, we're done.\n const inScope = db\n .prepare(\n `SELECT 1 AS hit FROM ${table} t\n JOIN workstreams ws ON ws.id = t.workstream_id\n WHERE t.${keyCol} = ? AND ws.name = ?\n LIMIT 1`,\n )\n .get(keyVal, expectedWs) as { hit: number } | undefined;\n if (inScope) return;\n // Slow path: name doesn't exist in expected ws — check whether it\n // exists anywhere else so we can raise the typed mismatch error\n // (rather than letting downstream raise the generic NotFoundError).\n // Pick any other workstream's row deterministically.\n const elsewhere = db\n .prepare(\n `SELECT ws.name AS workstream FROM ${table} t\n LEFT JOIN workstreams ws ON ws.id = t.workstream_id\n WHERE t.${keyCol} = ?\n ORDER BY ws.name\n LIMIT 1`,\n )\n .get(keyVal) as { workstream: string | null } | undefined;\n if (elsewhere) {\n throw errFactory(keyVal, expectedWs, elsewhere.workstream);\n }\n}\n\n/**\n * Sister of `assertTaskInWorkstream` for verbs that target an agent\n * by name. Agent names are per-workstream unique\n * (`UNIQUE(workstream_id, name)` in src/db.ts), so the same name can\n * exist in multiple workstreams; `-w` is the scope check that turns a\n * wrong-target verb into a clear `AgentNotInWorkstreamError` (exit 4)\n * instead of silently operating on a same-named agent in another\n * workstream. No-op when `workstream` is undefined or the agent\n * doesn't exist (downstream handler raises `AgentNotFoundError`).\n */\nexport function assertAgentInWorkstream(\n db: Db,\n agentName: string,\n workstream: string | undefined,\n): void {\n // agents.workstream is NOT NULL in the schema, so `actual` is\n // never null in practice; the `?? \"—\"` is defence-in-depth for the\n // typed-error contract (which expects a non-null actual).\n assertEntityInWorkstream(\n db,\n \"agents\",\n \"name\",\n agentName,\n workstream,\n (n, exp, actual) => new AgentNotInWorkstreamError(n, exp, actual ?? \"—\"),\n );\n}\n\n/**\n * Sister of `assertAgentInWorkstream` for verbs that target a single\n * task by ID. Globally-unique task IDs mean these verbs could ignore\n * the flag, but accepting it gives the operator a sanity check (\"yes,\n * I think this task is in that workstream\") and raises a clear\n * `TaskNotInWorkstreamError` instead of silently acting on the task\n * they didn't mean. No-op when `workstream` is undefined or the task\n * doesn't exist (downstream handler raises `TaskNotFoundError`).\n */\nexport function assertTaskInWorkstream(\n db: Db,\n taskId: string,\n workstream: string | undefined,\n): void {\n // tasks.workstream is NOT NULL in the schema; see assertAgentInWorkstream.\n assertEntityInWorkstream(\n db,\n \"tasks\",\n \"local_id\",\n taskId,\n workstream,\n (id, exp, actual) => new TaskNotInWorkstreamError(id, exp, actual ?? \"—\"),\n );\n}\n\n// ─── Numeric arg parsers ─────────────────────────────────────────────\n//\n// All strict: the whole string must be the number. parseInt/parseFloat\n// kept a numeric prefix (\"5.9abc\" -> 5, \"2x\" -> 2) and parseFloat let\n// \"1e999\" through as Infinity, which JSON serialises as null.\n\nconst NON_NEGATIVE_INT_RE = /^\\s*\\d+\\s*$/;\n\nexport function parsePositiveNumber(value: string): number {\n const n = value.trim() === \"\" ? Number.NaN : Number(value);\n if (!Number.isFinite(n) || n <= 0) {\n throw new InvalidArgumentError(`expected a positive number, got ${JSON.stringify(value)}`);\n }\n return n;\n}\n\n// Parses a duration in seconds for --timeout / --stuck-after: any\n// non-negative finite number, fractions included. Strict on purpose:\n// parseInt read \"0.5\" as 0 (wait forever) and \"10m\" as 10, so a\n// suffix or other trailing text is an error, not a prefix to keep.\nexport function parseSeconds(value: string): number {\n const n = value.trim() === \"\" ? Number.NaN : Number(value);\n if (!Number.isFinite(n) || n < 0) {\n throw new InvalidArgumentError(\n `expected a non-negative number of seconds, got ${JSON.stringify(value)}`,\n );\n }\n return n;\n}\n\nexport function parseImpact(value: string): number {\n const n = NON_NEGATIVE_INT_RE.test(value) ? Number(value) : Number.NaN;\n if (Number.isNaN(n) || n < 1 || n > 100) {\n throw new InvalidArgumentError(`expected 1..100, got ${JSON.stringify(value)}`);\n }\n return n;\n}\n\n// Parses a non-negative integer (0 is valid): line counts, --limit,\n// and --since, which uses 0 as the \"replay everything\" cursor.\nexport function parseNonNegativeInt(value: string): number {\n const n = NON_NEGATIVE_INT_RE.test(value) ? Number(value) : Number.NaN;\n if (!Number.isSafeInteger(n)) {\n throw new InvalidArgumentError(`expected a non-negative integer, got ${JSON.stringify(value)}`);\n }\n return n;\n}\n\n// Parses a positive integer (0 is rejected). Used where 0 would mean\n// \"nothing\", e.g. `mu undo -n`, whose empty list reads as an empty log.\nexport function parsePositiveInt(value: string): number {\n // Digits only, no surrounding whitespace.\n const n = /^\\d+$/.test(value) ? Number(value) : Number.NaN;\n if (!Number.isSafeInteger(n) || n < 1) {\n throw new InvalidArgumentError(`expected a positive integer, got ${JSON.stringify(value)}`);\n }\n return n;\n}\n\n/** Line counts (-n/--lines/--events): same rule as parseNonNegativeInt. */\nexport const parseLines = parseNonNegativeInt;\n\n// ─── Program definition ───────────────────────────────────────────────\n//\n// See the `wire*Commands` calls below for the full namespace/utility\n// list (`workstream`, `agent`, `task`, `workspace`, `log`, `state`,\n// `sql`, `sync`, `rebuild`, `db`, `undo`, `doctor`, plus the bare `mu`\n// TTY-aware default) rather than a count here, which drifts.\n//\n// Every flag is declared on the subcommand that consumes it. The one\n// exception is the root `-w`: a preAction hook (forwardRootWorkstream)\n// writes it into the verb's own `-w`, so `mu -w ws <verb>` and\n// `mu --workstream=ws <verb>` scope exactly like `mu <verb> -w ws`.\n// Verbs therefore read `this.opts()` and still see a root `-w`; without\n// the hook, teardown and state silently fell back to $MU_SESSION. The\n// optsWithGlobals() verbs also see the root array and funnel it through\n// normalizeInheritedWorkstream.\n//\n// Bare `mu` takes only the root `-w` / `--json` flags. In a TTY it\n// loads every workstream into the TUI; in non-TTY / --json / MU_NO_TUI\n// paths it prints help for script-friendly behaviour.\n\n// Reusable workstream flag declaration. Each subcommand that needs it\n// gets its own copy via `.option(...WORKSTREAM_OPT)` so there is no\n// cross-command leakage.\nexport const WORKSTREAM_OPT = [\n \"-w, --workstream <name>\",\n \"workstream (defaults to $MU_SESSION or the current tmux session minus mu- prefix)\",\n] as const;\n\n// Reusable --json flag for every read verb. Output shape is documented\n// per-verb but follows a consistent pattern: collections → the\n// `{items, count}` envelope (emitJsonCollection), so an empty one prints\n// `{\"items\":[],\"count\":0}`; single entities → JSON objects (every\n// \"single\" verb errors on a miss rather than printing `null`). Pretty-printing is OFF; one\n// document per line so output is grep/jq friendly.\nexport const JSON_OPT = [\"--json\", \"emit machine-readable JSON instead of a table\"] as const;\n\n/**\n * Canonical multi-value-flag parser. Every commander variadic flag\n * (`--foo <vals...>`) in mu is post-processed through this helper so\n * the operator can use repeated-flag form, comma-separated form, or\n * any mix:\n *\n * --foo a --foo b --foo c → [\"a\", \"b\", \"c\"]\n * --foo a,b,c → [\"a\", \"b\", \"c\"]\n * --foo a,b --foo c → [\"a\", \"b\", \"c\"]\n *\n * Whitespace inside fragments is trimmed. Two kinds of \"empty\" get\n * DIFFERENT treatment, and the distinction is the whole point (see\n * docs/reference/naming.md § Empty and blank list fragments):\n *\n * EMPTY (`\"\"` before trimming) — DROPPED. This is either a\n * structural comma artifact (`\"a,b,\"`, `\"a,,b\"`) or the\n * deliberate clear-everything sentinel that\n * `mu task reparent --blocked-by ''` documents. Both are\n * things an operator means.\n * BLANK (non-empty before trimming, empty after — i.e. entirely\n * whitespace, `\" \"` / `\"\\t\"`) — a UsageError (exit 2). An\n * operator never means \"filter by the space character\";\n * it is a typo or a quoting accident, and silently dropping\n * it produced a silent wrong answer\n * (bug_whitespace_status_fragment): `--status \"OPEN, \"`\n * quietly widened to no-filter-at-all, and `--status \" \"`\n * returned every task as though no filter were given.\n *\n * Trim-then-drop-empty conflated the two. Deciding it HERE rather\n * than per-call-site is deliberate: a per-call-site answer is exactly\n * how the flag-vs-positional inconsistency arose.\n *\n * Idempotent: the helper is safe to apply twice (its output never\n * contains a blank fragment, so a second pass cannot throw).\n *\n * Convention codified by cli_audit_plurality_uniformity (v0.3). See\n * docs/guide/sql.md \"Pass list flags\".\n */\nexport function parseCsvFlag(\n values: readonly string[] | undefined,\n flag = \"a list flag\",\n): string[] {\n if (!values) return [];\n const out: string[] = [];\n for (const value of values) {\n for (const fragment of value.split(\",\")) {\n // Empty BEFORE trimming: comma artifact or clear-all sentinel.\n if (fragment.length === 0) continue;\n const trimmed = fragment.trim();\n // Non-empty before, empty after: entirely whitespace.\n if (trimmed.length === 0) {\n throw new UsageError(\n `${flag} got a blank (whitespace-only) value ${JSON.stringify(fragment)}. Remove it, or pass an empty string ('') if you meant \"none\".`,\n );\n }\n out.push(trimmed);\n }\n }\n return out;\n}\n\n/**\n * Normalize an `optsWithGlobals()` workstream value into a single name.\n *\n * Subcommands that call `optsWithGlobals()` inherit the ROOT\n * `-w, --workstream <names>` flag, which COLLECTS into an array — so a\n * root-position invocation like `mu -w foo task owned-by worker-1`\n * yields `[\"foo\"]` (an array), not `\"foo\"`. The subcommand's own\n * `WORKSTREAM_OPT` is single-value (`<name>`) and yields a string.\n * `optsWithGlobals()` can hand either shape to a single-workstream\n * verb, so callers MUST funnel the merged value through this helper:\n * it accepts string | string[] | undefined, reuses parseCsvFlag's\n * canonicalisation (repeat / comma / mixed forms), returns the single\n * name (or undefined when none was passed), and throws UsageError when\n * more than one workstream is supplied to a verb that scopes to one.\n *\n * Guards finding_optswithglobals_can_pass_root: without this, an array\n * leaks unchanged through resolveWorkstream into DB calls, producing\n * confusing substrate errors instead of the documented scoping.\n */\nexport function normalizeInheritedWorkstream(\n value: string | readonly string[] | undefined,\n): string | undefined {\n if (value === undefined) return undefined;\n const names = parseCsvFlag(typeof value === \"string\" ? [value] : value, \"-w/--workstream\");\n if (names.length === 0) return undefined;\n if (names.length > 1) {\n throw new UsageError(\n `-w/--workstream takes a single workstream here (got ${names.length}: ${names.join(\", \")})`,\n );\n }\n return names[0];\n}\n\n/** Stable JSON output: one line, no trailing newline beyond console.log's.\n * Exported so cli/*.ts modules can use the same single-source-of-truth\n * formatter. */\nexport function emitJson(value: unknown): void {\n console.log(JSON.stringify(value));\n}\n\n/** Wrap a collection in mu's canonical `{items, count}` envelope.\n * audit_json_envelope_uniformity: every collection-read verb (list,\n * next, owned-by, notes, search, orphans, commits, ...) emits this\n * shape so a future sibling field (`baseRef`, `totalAcrossPages`,\n * ...) can be added without breaking every caller. Pre-1.0\n * breaking versus the pre-audit bare-array shape.\n *\n * Carve-out: `mu sql --json` keeps bare-array rows (it's the escape\n * hatch; row shape is per-query, not part of the typed contract).\n * `mu log --tail --json` keeps NDJSON (one object per line) since\n * it's a stream, not a collection. */\nexport function emitJsonCollection<T>(items: readonly T[]): void {\n emitJson({ items, count: items.length });\n}\n\nasync function cmdBareTui(\n db: Db,\n program: Command,\n requestedWorkstreams?: readonly string[],\n): Promise<void> {\n const workstreams = await listWorkstreams(db);\n const requested = parseCsvFlag(requestedWorkstreams, \"-w/--workstream\");\n if (workstreams.length === 0 && requested.length === 0) {\n program.outputHelp();\n printBareNoWorkstreamsHint();\n return;\n }\n\n const allNames = workstreams.map((w) => w.name);\n const names = requested.length > 0 ? Array.from(new Set(requested)) : allNames;\n for (const name of names) {\n if (!allNames.includes(name)) throw new WorkstreamNotFoundError(name);\n }\n const initialActive = await resolveInitialTab(names, db);\n try {\n const { runTui } = await importTui();\n await runTui(db, { workstreams: names, initialActive });\n } catch (err) {\n // If stdout is a TTY but stdin is not, ink can fail before rendering.\n // Degrade to the non-TTY path instead of crashing a piped/scripted call.\n // For an actual interactive stdin, surface the TUI error normally.\n if (process.stdin.isTTY !== true) {\n program.outputHelp();\n return;\n }\n throw err;\n }\n}\n\n/**\n * Read the package version from the shipped package.json. Works for\n * both source mode (src/cli.ts → ../package.json) and bundled mode\n * (dist/cli.js → ../package.json), since both layouts have package.json\n * exactly one directory up. Avoids hand-bumping a string literal in\n * code on every release.\n */\nfunction readPackageVersion(): string {\n try {\n const here = dirname(fileURLToPath(import.meta.url));\n const pkgPath = join(here, \"..\", \"package.json\");\n const raw = readFileSync(pkgPath, \"utf8\");\n const parsed = JSON.parse(raw) as { version?: unknown };\n return typeof parsed.version === \"string\" ? parsed.version : \"unknown\";\n } catch {\n return \"unknown\";\n }\n}\n\nexport function buildProgram(): Command {\n const program = new Command();\n program\n .name(\"mu\")\n .description(\n \"Persistent crew of AI agents in tmux or herdr panes coordinated through a built-in task DAG.\",\n )\n .version(readPackageVersion())\n .helpOption(\"-h, --help\")\n // .showHelpAfterError() removed (audit_cli_validation_uniformity):\n // emitError() in handle.ts now owns help-on-error emission for both\n // commander mistakes and handler-thrown UsageErrors. Without this\n // removal, commander would print its own \"\\n<help>\" appendix to\n // stderr before throwing CommanderError, leaving us with a duplicate\n // help dump (commander's then ours). We suppress commander's stderr\n // entirely in applyExitOverride below; this comment is the load-\n // bearing explanation of why we don't reach for showHelpAfterError().\n // Sort most Commands lists (NOT the Options list) alphabetically.\n // Commander v14 inherits configureHelp via copyInheritedSettings()\n // when subcommands are created with .command(), but we also walk the\n // tree below for certainty — future subcommand groups added via\n // .addCommand() do not inherit.\n .configureHelp({ sortSubcommands: true })\n // Without this, `mu task list --json` would bind --json to the\n // program (where we declare it for the bare `mu --json` help path)\n // instead of the `list` subcommand. With it,\n // options before a subcommand bind to the program; options after\n // bind to the subcommand. Subcommands inherit it automatically.\n .enablePositionalOptions()\n // Default action when no subcommand is given. Human path (stdout\n // attached to a TTY) opens the interactive TUI across every\n // workstream; non-TTY / MU_NO_TUI / --json keeps the CLI-help path\n // so scripts and agents do not accidentally enter ink.\n //\n // NOT variadic (`<names...>`): a variadic root flag swallowed the\n // verb too, so `mu -w ws task list` parsed as workstreams\n // [\"ws\",\"task\",\"list\"] and printed root help with exit 0.\n .option(\n \"-w, --workstream <names>\",\n \"workstream(s) to render (repeat or comma-separate; or both; defaults to $MU_SESSION or current tmux session). Before a verb, it is that verb's -w\",\n (value: string, previous: string[] | undefined) => [...(previous ?? []), value],\n )\n .option(...JSON_OPT)\n .hook(\"preAction\", forwardRootWorkstream)\n .action(function () {\n const command = this as Command;\n const opts = command.opts() as { workstream?: string[]; json?: boolean };\n if (process.stdout.isTTY !== true || process.env.MU_NO_TUI === \"1\" || opts.json === true) {\n program.outputHelp();\n return;\n }\n return handle((db) => cmdBareTui(db, program, opts.workstream), command)();\n });\n\n wireWorkstreamCommands(program);\n wireAgentCommands(program);\n wireSelfCommands(program);\n wireWorkspaceCommands(program);\n wireTaskCommands(program);\n wireLogCommand(program);\n wireStateCommands(program);\n wireSqlCommand(program);\n wireSyncCommand(program);\n wireRebuildCommand(program);\n wireDbCommands(program);\n wireUndoCommand(program);\n wireDoctorCommand(program);\n wireLinkCommand(program);\n applyAlphabeticalHelpSort(program);\n // audit_cli_validation_uniformity: every node in the command tree\n // must call exitOverride() so commander throws CommanderError\n // instead of calling process.exit() itself. Lets the parseAsync()\n // catch route every operator-error through emitError() with the\n // failing subcommand's --help (human) or `usage` JSON (--json).\n applyExitOverride(program);\n return program;\n}\n\n/** preAction hook: hand a root-position `-w` to the verb's own `-w`, so\n * `mu -w ws task list` means `mu task list -w ws`. Fails loud (exit 2)\n * rather than silently ignoring the flag when the verb takes no `-w`,\n * or when `-w` is given on both sides of the verb. */\nfunction forwardRootWorkstream(root: Command, leaf: Command): void {\n if (leaf === root) return;\n const names = root.opts().workstream as string[] | undefined;\n if (names === undefined) return;\n const usage = (message: string): never =>\n leaf.error(message, { exitCode: 2, code: \"commander.usage\" }) as never;\n const opt = leaf.options.find((o) => o.attributeName() === \"workstream\");\n if (opt === undefined) {\n usage(`error: \\`${leaf.name()}\\` takes no -w/--workstream; drop the root -w`);\n return;\n }\n if (leaf.getOptionValue(\"workstream\") !== undefined) {\n usage(\"error: -w/--workstream given both before and after the verb; pass it once\");\n return;\n }\n if (opt.variadic) {\n leaf.setOptionValueWithSource(\"workstream\", names, \"cli\");\n return;\n }\n const parsed = parseCsvFlag(names, \"-w/--workstream\");\n if (parsed.length > 1) {\n usage(\n `error: -w/--workstream takes a single workstream here (got ${parsed.length}: ${parsed.join(\", \")})`,\n );\n return;\n }\n if (parsed[0] !== undefined) leaf.setOptionValueWithSource(\"workstream\", parsed[0], \"cli\");\n}\n\n// Recursively set sortSubcommands on every command in the tree. Belt\n// and braces over the root .configureHelp() call: guarantees the sort\n// holds regardless of how a subcommand was attached (.command() vs\n// .addCommand()) and regardless of inheritance behaviour across\n// commander versions. Preserves any other help-configuration keys\n// already set on a subcommand.\nfunction applyAlphabeticalHelpSort(cmd: Command): void {\n cmd.configureHelp({ ...cmd.configureHelp(), sortSubcommands: true });\n for (const sub of cmd.commands) {\n applyAlphabeticalHelpSort(sub);\n }\n}\n\n/** Recursively call exitOverride() on every command in the tree.\n * Without this, commander writes its error to stderr and calls\n * process.exit() inline — we never see the error and our emitError()\n * contract (--help on usage errors, --json envelopes, exit-2\n * uniformity) doesn't apply.\n *\n * We ALSO swallow commander's writeErr so commander never prints the\n * unformatted \"error: ...\" / help combo before our handler runs. The\n * captured text is discarded; emitError() re-emits message + help in\n * mu's format. Help displays via --help still flow through writeOut\n * (commander.helpDisplayed code, which classifyCommanderError maps to\n * exit 0 with no further output). */\nfunction applyExitOverride(cmd: Command): void {\n cmd.exitOverride();\n cmd.configureOutput({\n writeOut: (s) => process.stdout.write(s),\n writeErr: () => {\n // Swallow commander's pre-throw stderr; emitError re-emits.\n },\n });\n for (const sub of cmd.commands) {\n applyExitOverride(sub);\n }\n}\n\n// ─── Entry point ───────────────────────────────────────────────────────\n\n/** Bare verb-namespace invocations (`mu workspace`, `mu task`, …)\n * used to print nothing and exit 0 because commander, given a parent\n * with subcommands and no .action(), produces an empty render. We\n * fix this BEFORE parseAsync rather than via .action() on each\n * namespace because attaching .action() makes commander treat\n * `mu task bogus` as a positional arg to `task` instead of routing\n * it to the \"unknown subcommand\" lane (which other tests + emitError\n * depend on). Surfaced by `bare_verb_namespaces_mu_workspace_task`.\n *\n * Triggers when:\n * - argv after the program name is exactly one token\n * - that token names a top-level subcommand of `mu`\n * - that subcommand itself has its own subcommands (i.e. it's a\n * namespace, not a leaf verb)\n * In that case we append `--help` so commander routes through its\n * help printer. Bare `mu` is unaffected because\n * the slice has length 0.\n */\nexport function injectBareNamespaceHelp(\n program: Command,\n argv: readonly string[],\n): readonly string[] {\n // argv is the full process.argv shape: [node, mu, ...userArgs].\n if (argv.length !== 3) return argv;\n const token = argv[2];\n if (token === undefined || token.startsWith(\"-\")) return argv;\n const sub = program.commands.find((c) => c.name() === token || c.aliases().includes(token));\n if (!sub) return argv;\n if (sub.commands.length === 0) return argv;\n return [...argv, \"--help\"];\n}\n\n/** Parse and run one `mu` invocation. Called by the bin bootstrap\n * (src/main.ts) after it enables the compile cache; tests use\n * buildProgram() directly. */\nexport async function runCli(rawArgv: readonly string[]): Promise<void> {\n const program = buildProgram();\n const argv = injectBareNamespaceHelp(program, rawArgv);\n try {\n await program.parseAsync(argv);\n } catch (err) {\n // CommanderError (parse-time) lands here because every command in\n // the tree had .exitOverride() applied. Locate the deepest matching\n // subcommand from argv so emitError can render its --help (human)\n // or `usage` JSON (--json).\n const failingCmd = findCommandForArgv(program, argv.slice(2));\n const exitCode = emitParseError(err, failingCmd);\n process.exit(exitCode);\n }\n}\n","// mu — every `mu agent ...` verb + spawn / send / read / list / show /\n// close / adopt + the top-level `mu me` agent-self\n// verb (default + `tasks` / `next` subcommands).\n//\n// Extracted from src/cli.ts as part of refactor_split_large_src_files.\n//\n// `whoami` / `my-tasks` / `my-next` were merged into `mu me` /\n// `mu me tasks` / `mu me next` in audit_merge_self_verbs_into_mu_me\n// (audit_cleanups_post_schema_v5_wave). The three old verbs are\n// gone; the three cmd functions (`cmdMe`, `cmdMyTasks`, `cmdMyNext`)\n// stayed (with `cmdMe` formerly `cmdWhoami`).\n\nimport { dirname } from \"node:path\";\nimport { agentKey, ctlRuntimeState, readAgentStates } from \"../agent-state.js\";\nimport {\n type AdoptAgentOptions,\n type AdoptAgentResult,\n AgentCtlUnreachableError,\n AgentNotFoundError,\n type AgentStatusSnapshot,\n type AgentWatch,\n abortAgent,\n adoptAgent,\n agentCtlSocket,\n closeAgent,\n delegateOutcome,\n expectsCtl,\n getAgent,\n interruptAgent,\n isKickSignal,\n isSlashCommand,\n type KickSignal,\n kickAgent,\n listLiveAgents,\n parseSessionCommand,\n readAgent,\n refreshAgentTitle,\n resolveCliCommand,\n resolveCliCommandWithSource,\n type SpawnedAgent,\n sendToAgent,\n spawnAgent,\n type Transport,\n waitForAgents,\n} from \"../agents.js\";\nimport {\n applyQualifiedRef,\n assertAgentInWorkstream,\n CliExitError,\n classifyError,\n emitJson,\n formatAgentsTable,\n formatTaskListTable,\n resolveEntityRef,\n resolveSelf,\n resolveWorkstream,\n statusIcon,\n UsageError,\n} from \"../cli.js\";\nimport { ctlProbe, ctlRequest } from \"../ctl/client.js\";\nimport type { Db } from \"../db.js\";\nimport { activeMux, type SendWarning } from \"../mux.js\";\nimport { type NextStep, pc, printNextSteps, printNextStepsTo } from \"../output.js\";\nimport { listTasksByOwner } from \"../tasks.js\";\nimport { detectBackend, type VcsBackendName } from \"../vcs.js\";\nimport { getWorkspaceForAgent } from \"../workspace.js\";\nimport { abortHint, dispatchHint, plainSendHints } from \"./dispatch-hints.js\";\nimport { checkWorkspaceStalenessForDispatch } from \"./staleness.js\";\nimport { readStdinText, STDIN_ARG } from \"./stdin.js\";\n\ninterface SpawnOpts {\n cli?: string;\n command?: string;\n tab?: string;\n role?: string;\n cwd?: string;\n workstream?: string;\n workspace?: boolean;\n workspaceBackend?: VcsBackendName;\n workspaceFrom?: string;\n workspaceProjectRoot?: string;\n /** commander's `--no-ctl` negation: false skips the ctl handshake. */\n ctl?: boolean;\n /** Take the next free name when `<name>` is taken. */\n nextFree?: boolean;\n /** Send this text once the agent is up (`-` reads stdin). */\n send?: string;\n json?: boolean;\n}\n// Preflight: when --workspace is set, resolve+announce the backend\n// and projectRoot BEFORE the long-running git-worktree-add /\n// jj-workspace-add / cp -a, so the operator can ctrl-c if the\n// detected backend is wrong (e.g. cp -a falling through to a\n// 60GB project tree because --workspace-project-root pointed at a\n// non-VCS dir; surfaced by bug_agent_spawn_workspace_aborts_without_status).\n// Skipped on --json so machine consumers get a single structured\n// output, not preflight chatter.\nasync function maybePrintWorkspacePreflight(opts: SpawnOpts): Promise<void> {\n if (!opts.workspace || opts.json) return;\n const projectRoot = opts.workspaceProjectRoot ?? process.cwd();\n const backend: VcsBackendName = opts.workspaceBackend ?? (await detectBackend(projectRoot)).name;\n const warn =\n backend === \"none\"\n ? pc.yellow(\n \" — WARNING: 'none' backend will cp -a the entire projectRoot. Verify --workspace-project-root.\",\n )\n : \"\";\n console.log(\n pc.dim(\n `[mu] workspace preflight: backend=${pc.bold(backend)} projectRoot=${pc.bold(projectRoot)}${warn}`,\n ),\n );\n}\n\nexport async function cmdSpawn(db: Db, rawName: string, opts: SpawnOpts): Promise<void> {\n const workstream = await resolveWorkstream(opts.workstream);\n // Read stdin before any side effect: an empty pipe must not leave a pane.\n const sendText =\n opts.send === undefined\n ? undefined\n : opts.send === STDIN_ARG\n ? await readStdinText(\"send text\")\n : opts.send;\n\n await maybePrintWorkspacePreflight(opts);\n\n const agent = await spawnAgent(db, {\n name: rawName,\n workstream,\n ...(opts.cli !== undefined ? { cli: opts.cli } : {}),\n ...(opts.command !== undefined ? { command: opts.command } : {}),\n ...(opts.tab !== undefined ? { tab: opts.tab } : {}),\n ...(opts.role !== undefined ? { role: opts.role } : {}),\n ...(opts.cwd !== undefined ? { cwd: opts.cwd } : {}),\n ...(opts.workspace !== undefined ? { workspace: opts.workspace } : {}),\n ...(opts.workspaceBackend !== undefined ? { workspaceBackend: opts.workspaceBackend } : {}),\n ...(opts.workspaceFrom !== undefined ? { workspaceFrom: opts.workspaceFrom } : {}),\n ...(opts.workspaceProjectRoot !== undefined\n ? { workspaceProjectRoot: opts.workspaceProjectRoot }\n : {}),\n ...(opts.ctl === false ? { ctl: false } : {}),\n ...(opts.nextFree === true ? { nextFree: true } : {}),\n });\n // --next-free may have picked another name than the one asked for.\n const name = agent.name;\n // A pi agent whose control socket never answered still spawned (the\n // pane is usable by hand), but say so loudly on stderr: every exact\n // send / wait on it will fail until the extension answers.\n if (agent.ctl === \"missing\" || agent.ctl === \"refused\") {\n const warn = new AgentCtlUnreachableError(name, workstream, agent.ctlSocket, agent.ctl);\n console.error(pc.yellow(`warning: ${warn.message}`));\n printNextStepsTo(warn.errorNextSteps(), \"stderr\");\n }\n const sent = sendText === undefined ? undefined : await spawnSend(db, agent, sendText);\n const workspace = opts.workspace ? getWorkspaceForAgent(db, name, workstream) : undefined;\n // Resolve the actual command that landed in the pane, so the operator\n // can confirm `--command 'pi-meta --no-solo'` (etc.) took effect.\n // Mirrors the resolution chain in spawnAgent: explicit --command >\n // $MU_<UPPER_CLI>_COMMAND > the cli value itself. Surfaced from\n // mufeedback note #159: 'Spawned ... (pi)' was misleading when\n // --command overrode the binary.\n const resolvedCommand = opts.command ?? resolveCliCommand(agent.cli);\n const commandOverridden = resolvedCommand !== agent.cli;\n // fb_agent_spawn_no_validation part C: when the override came from\n // an env var (no explicit --command), surface the env-var name in\n // the success line so config issues (\"Spawned ... (pi-meta)\" but I\n // never set $MU_PI_META_COMMAND — wait, I did, and it's stale\")\n // are visible without `mu agent show`. Explicit --command takes\n // priority and is shown via the existing `(cmd: ...)` suffix below.\n const envSourced =\n opts.command === undefined ? resolveCliCommandWithSource(agent.cli) : undefined;\n const nextSteps: NextStep[] = [\n // After --send the next step is the wait (or the pane read below).\n ...(!sent?.ok\n ? [dispatchHint(agent)]\n : sent.runs !== undefined\n ? [\n {\n intent: \"Wait for the response (returns its final text)\",\n command: `mu agent wait ${name} --after-runs ${sent.runs} --json -w ${workstream}`,\n },\n ]\n : []),\n { intent: \"Read pane\", command: `mu agent read ${name} -w ${workstream}` },\n { intent: \"Watch live events\", command: `mu log -w ${workstream} --tail` },\n {\n intent: \"Close (drops registry row, kills pane)\",\n command: `mu agent close ${name} -w ${workstream}`,\n },\n ];\n // Best-effort: the pane exists, so a mux is up; the hint is decoration.\n try {\n const mux = await activeMux();\n nextSteps.push({\n intent: \"Attach the pane\",\n command: await mux.attachHint({\n session: `mu-${workstream}`,\n window: agent.tab ?? name,\n inside: Boolean(process.env.TMUX),\n }),\n });\n } catch {\n // no hint\n }\n if (opts.json) {\n emitJson({\n agent,\n workspace: workspace ?? null,\n resolvedCommand,\n commandOverridden,\n // env-var attribution for machine consumers: present iff the\n // resolution came from $MU_<UPPER_CLI>_COMMAND. Mirrors the\n // human `(via $MU_PI_META_COMMAND)` suffix below.\n ...(envSourced?.resolvedFromEnv ? { resolvedFromEnvVar: envSourced.envVar } : {}),\n ctl: agent.ctl,\n ctlSocket: agent.ctlSocket,\n ...(sent !== undefined ? { send: sent } : {}),\n nextSteps,\n });\n if (sent !== undefined && !sent.ok) throw new CliExitError(sent.exitCode);\n return;\n }\n const wsBit = opts.workspace ? pc.dim(\" with auto-workspace\") : \"\";\n // Three display modes (precedence top-down):\n // 1. --command was explicit → 'pi (cmd: pi-meta --no-solo)'\n // 2. resolved via env var override → 'pi (via $MU_PI_COMMAND)'\n // 3. bare CLI name on PATH → 'pi'\n // Env-var attribution is preferred over the generic '(cmd: ...)'\n // suffix because the env-var name is the actionable knob the\n // operator can grep for / unset (fb_agent_spawn_no_validation pt C).\n const cliDisplay =\n opts.command !== undefined\n ? `${agent.cli} ${pc.dim(`(cmd: ${resolvedCommand})`)}`\n : envSourced?.resolvedFromEnv\n ? `${agent.cli} ${pc.dim(`(via $${envSourced.envVar})`)}`\n : agent.cli;\n console.log(\n `Spawned ${pc.bold(agent.name)} (${cliDisplay}) in window ${pc.bold(agent.tab ?? agent.name)} of ${pc.bold(`mu-${workstream}`)}, pane ${pc.dim(agent.paneId)}${wsBit}`,\n );\n if (workspace) console.log(pc.dim(` workspace: ${workspace.path} (${workspace.backend})`));\n console.log(pc.dim(` ctl: ${agent.ctl} (${agent.ctlSocket})`));\n if (sent?.ok) {\n const runs = sent.runs !== undefined ? `, runs ${sent.runs}` : \"\";\n console.log(pc.dim(` sent ${sent.sentBytes} bytes (via ${sent.transport}${runs})`));\n } else if (sent !== undefined) {\n console.error(pc.red(`error: --send failed: ${sent.message}`));\n }\n printNextSteps(nextSteps);\n if (sent !== undefined && !sent.ok) throw new CliExitError(sent.exitCode);\n}\n\n/** `mu agent spawn --send`: the outcome of the send, as `--json` reports it. */\ntype SpawnSend =\n | {\n ok: true;\n sentBytes: number;\n transport: Transport;\n state?: string;\n runs?: number;\n delivered: boolean;\n }\n | { ok: false; error: string; message: string; exitCode: number };\n\n/**\n * Send the first prompt to a just-spawned agent, so a caller that would\n * run spawn then send pays one mu process instead of two. The pane stays\n * up when the send fails: the spawn succeeded, and the caller decides.\n * A pi whose control socket never answered is not sent to (the send\n * could not be confirmed).\n */\nasync function spawnSend(db: Db, agent: SpawnedAgent, text: string): Promise<SpawnSend> {\n const fail = (err: unknown): SpawnSend => ({\n ok: false,\n error: err instanceof Error ? err.name : \"Error\",\n message: err instanceof Error ? err.message : String(err),\n exitCode: classifyError(err).exitCode,\n });\n if (agent.ctl === \"missing\" || agent.ctl === \"refused\")\n return fail(\n new AgentCtlUnreachableError(agent.name, agent.workstreamName, agent.ctlSocket, agent.ctl),\n );\n let undelivered = false;\n try {\n const sent = await sendToAgent(db, agent.name, text, {\n workstream: agent.workstreamName,\n onUndelivered: () => {\n undelivered = true;\n },\n });\n return {\n ok: true,\n sentBytes: Buffer.byteLength(text),\n transport: sent.transport,\n ...(sent.state !== undefined ? { state: sent.state } : {}),\n ...(sent.runs !== undefined ? { runs: sent.runs } : {}),\n delivered: !undelivered,\n };\n } catch (err) {\n return fail(err);\n }\n}\n\nfunction parseVia(raw: string | undefined): Transport | undefined {\n if (raw === undefined || raw === \"ctl\" || raw === \"mux\") return raw;\n throw new UsageError(`--via must be ctl or mux (got ${JSON.stringify(raw)})`);\n}\n\nexport async function cmdSend(\n db: Db,\n rawName: string,\n rawText: string,\n opts: {\n workstream?: string;\n json?: boolean;\n strictStaleness?: boolean;\n steer?: boolean;\n via?: string;\n fresh?: boolean;\n force?: boolean;\n interrupt?: boolean;\n timeout?: number;\n } = {},\n): Promise<void> {\n const via = parseVia(opts.via);\n const text = rawText === STDIN_ARG ? await readStdinText(\"send text\") : rawText;\n if (opts.interrupt) {\n for (const [on, flag] of [\n [opts.fresh, \"--fresh\"],\n [opts.steer, \"--steer\"],\n [via === \"mux\", \"--via mux\"],\n [opts.force, \"--force\"],\n ] as const) {\n if (on) throw new UsageError(`--interrupt and ${flag} are mutually exclusive`);\n }\n if (isSlashCommand(text)) {\n throw new UsageError(\"--interrupt sends a prompt, not a slash command\");\n }\n } else if (opts.timeout !== undefined) {\n throw new UsageError(\"--timeout only applies with --interrupt\");\n }\n if (opts.force && !opts.fresh && parseSessionCommand(text) === undefined) {\n throw new UsageError(\"--force only applies with --fresh or a /new, /reload, /compact\");\n }\n if (opts.fresh && opts.steer) throw new UsageError(\"--fresh and --steer are mutually exclusive\");\n if (opts.interrupt) return cmdSendInterrupt(db, rawName, text, opts);\n const { name } = await resolveEntityRef(db, rawName, opts, \"agent\");\n assertAgentInWorkstream(db, name, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const stalenessCheck = await checkWorkspaceStalenessForDispatch(db, name, ws, {\n strict: opts.strictStaleness === true,\n });\n // dogfood_send_after_new_dropped: capture the undelivered warning\n // rather than letting it print raw, so it lands in the JSON payload\n // too. `exit 0` must not be able to mean \"silently dropped\".\n let undelivered: SendWarning | undefined;\n const agentRow = getAgent(db, name, ws);\n const sent = await sendToAgent(db, name, text, {\n workstream: ws,\n ...(opts.steer ? { mode: \"steer\" as const } : {}),\n ...(via !== undefined ? { via } : {}),\n ...(opts.fresh ? { fresh: true } : {}),\n ...(opts.force ? { force: true } : {}),\n onUndelivered: (w) => {\n undelivered = w;\n },\n });\n // A ctl reply with runs gives the exact wait baseline: the wait\n // returns the run's final text, so no pane read is needed.\n const nextSteps: NextStep[] = [\n sent.transport === \"ctl\" && sent.runs !== undefined\n ? {\n intent: \"Wait for the response (returns its final text)\",\n command: `mu agent wait ${name} --after-runs ${sent.runs} --json -w ${ws}`,\n }\n : { intent: \"Read response\", command: `mu agent read ${name} -n 50 -w ${ws}` },\n { intent: \"Watch live events\", command: `mu log -w ${ws} --tail` },\n ];\n // A plain ctl send: the reply carries pi's status from before the\n // dispatch, so the hints can tell a queued follow-up (busy) from a new\n // task landing in an old context (idle after a settled run). An older\n // extension replies without runs and its state is post-dispatch: no hints.\n const plainCtl = sent.transport === \"ctl\" && !opts.fresh && sent.command === undefined;\n if (agentRow !== undefined && plainCtl && sent.state !== undefined && sent.runs !== undefined) {\n nextSteps.push(\n ...plainSendHints(\n agentRow,\n {\n state: sent.state,\n runs: sent.runs,\n ...(sent.since !== undefined ? { since: sent.since } : {}),\n },\n Date.now(),\n opts.steer ? \"steer\" : \"followUp\",\n ),\n );\n }\n if (stalenessCheck.warned && stalenessCheck.nextStep !== null) {\n nextSteps.push(stalenessCheck.nextStep);\n }\n if (undelivered !== undefined) {\n nextSteps.unshift({\n intent: \"VERIFY the prompt landed before waiting on it\",\n command: `mu agent read ${name} -n 30 -w ${ws}`,\n });\n }\n if (opts.json) {\n emitJson({\n agentName: name,\n sentBytes: Buffer.byteLength(text),\n transport: sent.transport,\n fresh: opts.fresh === true,\n ...(sent.command !== undefined ? { command: sent.command } : {}),\n ...(sent.state !== undefined ? { state: sent.state } : {}),\n ...(sent.runs !== undefined ? { runs: sent.runs } : {}),\n delivered: undelivered === undefined,\n ...(undelivered !== undefined\n ? { undelivered: { reason: undelivered.reason, message: undelivered.message } }\n : {}),\n staleness: stalenessCheck.staleness,\n nextSteps,\n });\n return;\n }\n if (undelivered !== undefined) {\n console.error(pc.yellow(`warning: ${undelivered.message}`));\n } else {\n const how =\n sent.transport === \"mux\"\n ? \"via mux paste\"\n : opts.fresh\n ? \"via ctl, fresh session\"\n : sent.command !== undefined\n ? `via ctl, pi ran /${sent.command}`\n : sent.runs !== undefined\n ? `via ctl, pi was ${sent.state ?? \"?\"}, runs ${sent.runs}`\n : `via ctl, pi ${sent.state ?? \"?\"}`;\n console.log(pc.dim(`sent ${Buffer.byteLength(text)} bytes to ${name} (${how})`));\n }\n printNextSteps(nextSteps);\n}\n\n/** `mu agent send --interrupt`: abort a busy pi, wait for settle, send. */\nasync function cmdSendInterrupt(\n db: Db,\n rawName: string,\n text: string,\n opts: { workstream?: string; json?: boolean; strictStaleness?: boolean; timeout?: number },\n): Promise<void> {\n const { name } = await resolveEntityRef(db, rawName, opts, \"agent\");\n assertAgentInWorkstream(db, name, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const stalenessCheck = await checkWorkspaceStalenessForDispatch(db, name, ws, {\n strict: opts.strictStaleness === true,\n });\n const r = await interruptAgent(db, name, text, {\n workstream: ws,\n ...(opts.timeout === undefined ? {} : { timeoutMs: Math.round(opts.timeout * 1000) }),\n });\n const nextSteps: NextStep[] = [\n r.runs !== undefined\n ? {\n intent: \"Wait for the response (returns its final text)\",\n command: `mu agent wait ${name} --after-runs ${r.runs} --json -w ${ws}`,\n }\n : { intent: \"Read response\", command: `mu agent read ${name} -n 50 -w ${ws}` },\n ];\n if (r.pending) {\n nextSteps.push({\n intent: \"Queued messages went back to the pane's editor unsent: read them there\",\n command: `mu agent read ${name} -n 30 -w ${ws}`,\n });\n }\n if (stalenessCheck.warned && stalenessCheck.nextStep !== null) {\n nextSteps.push(stalenessCheck.nextStep);\n }\n if (opts.json) {\n emitJson({\n agentName: name,\n sentBytes: Buffer.byteLength(text),\n transport: \"ctl\",\n interrupt: true,\n ...r,\n staleness: stalenessCheck.staleness,\n nextSteps,\n });\n return;\n }\n const what = r.wasBusy ? \"interrupted a busy run\" : \"pi was idle\";\n const runs = r.runs !== undefined ? `, runs ${r.runs}` : \"\";\n console.log(pc.dim(`sent ${Buffer.byteLength(text)} bytes to ${name} (via ctl, ${what}${runs})`));\n if (r.pending) console.log(pc.yellow(\"queued messages went back to the pane's editor unsent\"));\n printNextSteps(nextSteps);\n}\n\n/** Lines in captured scrollback: a final newline ends the last line, it\n * does not start an empty one, and empty text has none. `scrollbackLines`\n * in `agent read --json` and `agent show --json` both mean this. */\nfunction countLines(text: string): number {\n if (text === \"\") return 0;\n return text.split(\"\\n\").length - (text.endsWith(\"\\n\") ? 1 : 0);\n}\n\nexport async function cmdRead(\n db: Db,\n rawName: string,\n opts: { lines?: number; workstream?: string; json?: boolean },\n): Promise<void> {\n const { name } = await resolveEntityRef(db, rawName, opts, \"agent\");\n assertAgentInWorkstream(db, name, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const text = await readAgent(db, name, {\n workstream: ws,\n ...(opts.lines !== undefined ? { lines: opts.lines } : {}),\n });\n if (opts.json) {\n emitJson({\n agentName: name,\n lines: opts.lines ?? null,\n scrollback: text,\n scrollbackLines: countLines(text),\n });\n return;\n }\n process.stdout.write(text);\n if (!text.endsWith(\"\\n\")) process.stdout.write(\"\\n\");\n}\n\nexport async function cmdList(\n db: Db,\n opts: { workstream?: string; json?: boolean },\n): Promise<void> {\n const workstream = await resolveWorkstream(opts.workstream);\n const view = await listLiveAgents(db, { workstream });\n if (opts.json) {\n emitJson({ workstreamName: workstream, agents: view.agents, orphans: view.orphans });\n return;\n }\n console.log(pc.bold(`mu-${workstream}`));\n console.log(formatAgentsTable(view.agents));\n if (view.orphans.length > 0) {\n console.log(\"\");\n console.log(pc.yellow(`Orphan panes (${view.orphans.length})`));\n console.log(pc.dim(\" Panes that look like agents but aren't in the registry.\"));\n console.log(\n pc.dim(\n ` Run \\`mu agent adopt <pane-id>\\` to register one as a managed agent (e.g. \\`mu agent adopt ${view.orphans[0]?.paneId ?? \"%15\"}\\`).`,\n ),\n );\n for (const orphan of view.orphans) {\n console.log(\n ` ${pc.dim(orphan.paneId)} title=${pc.bold(orphan.title)} cli=${orphan.command}`,\n );\n }\n }\n}\n\nexport async function cmdAgentShow(\n db: Db,\n rawName: string,\n opts: { lines?: number; json?: boolean; workstream?: string },\n): Promise<void> {\n const { name } = await resolveEntityRef(db, rawName, opts, \"agent\");\n assertAgentInWorkstream(db, name, opts.workstream);\n // v5: agents.name is per-workstream unique. Resolve the operator's\n // workstream up front so the lookup scopes correctly.\n const ws = await resolveWorkstream(opts.workstream);\n const agent = getAgent(db, name, ws);\n if (!agent) throw new AgentNotFoundError(name);\n const lines = opts.lines ?? 20;\n let scrollback: string;\n try {\n // Best-effort: `mu agent show` still has a registry row to print\n // when the mux is unreachable. Empty scrollback degrades the\n // status refresh below, it doesn't fail the verb.\n scrollback = await (await activeMux()).capturePane(agent.paneId, { lines });\n } catch {\n scrollback = \"\";\n }\n\n const reading = (await readAgentStates([agent], { stateDir: dirname(db.name) })).get(\n agentKey(agent),\n );\n const displayed = {\n ...agent,\n state: reading?.state ?? (\"unknown\" as const),\n source: reading?.source ?? (\"none\" as const),\n ctl: reading?.ctl ?? (\"n/a\" as const),\n since:\n reading?.since === null || reading?.since === undefined\n ? null\n : new Date(reading.since).toISOString(),\n ...(reading?.reason !== undefined ? { reason: reading.reason } : {}),\n };\n\n if (opts.json) {\n emitJson({ agent: displayed, scrollback, scrollbackLines: countLines(scrollback) });\n return;\n }\n\n console.log(pc.bold(`${displayed.name} ${statusIcon(displayed.state)} ${displayed.state}`));\n console.log(` workstream : ${agent.workstreamName}`);\n console.log(` cli : ${agent.cli}`);\n console.log(` pane : ${pc.dim(agent.paneId)}`);\n console.log(` window : ${agent.tab ?? agent.name}`);\n console.log(` role : ${agent.role}`);\n console.log(` created : ${pc.dim(agent.createdAt)}`);\n console.log(` updated : ${pc.dim(agent.updatedAt)}`);\n\n console.log(\"\");\n console.log(pc.bold(`Recent scrollback (last ${lines} lines)`));\n if (scrollback.trim() === \"\") {\n console.log(pc.dim(\" (pane gone or empty)\"));\n return;\n }\n for (const line of scrollback.replace(/\\n+$/, \"\").split(\"\\n\")) {\n console.log(` ${line}`);\n }\n}\n\nexport async function cmdMe(\n db: Db,\n opts: { json?: boolean; includeClosed?: boolean } = {},\n): Promise<void> {\n const self = resolveSelf(db);\n const reading = (await readAgentStates([self], { stateDir: dirname(db.name) })).get(\n agentKey(self),\n );\n const displayed = {\n ...self,\n state: reading?.state ?? (\"unknown\" as const),\n source: reading?.source ?? (\"none\" as const),\n ctl: reading?.ctl ?? (\"n/a\" as const),\n since:\n reading?.since === null || reading?.since === undefined\n ? null\n : new Date(reading.since).toISOString(),\n ...(reading?.reason !== undefined ? { reason: reading.reason } : {}),\n };\n const owned = listTasksByOwner(db, self.workstreamName, self.name, {\n includeClosed: opts.includeClosed ?? false,\n });\n\n if (opts.json) {\n emitJson({ agent: displayed, ownedTasks: owned });\n return;\n }\n\n console.log(pc.bold(`${self.name} ${statusIcon(displayed.state)} ${displayed.state}`));\n console.log(` workstream : ${self.workstreamName}`);\n console.log(` cli : ${self.cli}`);\n console.log(` pane : ${pc.dim(self.paneId)}`);\n console.log(` role : ${self.role}`);\n console.log(\"\");\n if (owned.length === 0) {\n console.log(pc.dim(\"Currently owns no tasks. Try `mu me next` for a recommendation.\"));\n return;\n }\n console.log(pc.bold(`Currently owns ${owned.length} task${owned.length === 1 ? \"\" : \"s\"}`));\n console.log(formatTaskListTable(owned));\n}\n\nexport async function cmdClose(\n db: Db,\n rawName: string,\n opts: { workstream?: string; json?: boolean; discardWorkspace?: boolean } = {},\n): Promise<void> {\n const { name } = await resolveEntityRef(db, rawName, opts, \"agent\");\n assertAgentInWorkstream(db, name, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const result = await closeAgent(db, name, {\n workstream: ws,\n ...(opts.discardWorkspace === true ? { discardWorkspace: true } : {}),\n });\n const next: NextStep[] = [];\n if (result.workspaceFreed) {\n next.push({\n intent: result.workspaceAutoFreedClean\n ? \"Workspace was clean (no uncommitted changes, no commits since fork) so it was auto-freed alongside the agent\"\n : \"Workspace was freed alongside the agent (--discard-workspace)\",\n command: \"cd / # the workspace dir is gone\",\n });\n }\n next.push({\n intent: \"Re-spawn under the same name\",\n command: `mu agent spawn ${name} -w <workstream>`,\n });\n if (opts.json) {\n emitJson({ agentName: name, ...result, nextSteps: next });\n return;\n }\n if (!result.killedPane && !result.deletedRow) {\n console.log(pc.dim(`no agent named ${name} (already closed?)`));\n printNextSteps(next);\n return;\n }\n const wsBit = result.workspaceFreed\n ? pc.dim(result.workspaceAutoFreedClean ? \" (workspace auto-freed)\" : \" (workspace discarded)\")\n : \"\";\n console.log(`Closed ${pc.bold(name)}${wsBit}`);\n printNextSteps(next);\n}\n\ninterface AdoptCliOpts {\n workstream?: string;\n name?: string;\n cli?: string;\n role?: string;\n json?: boolean;\n}\n\nexport async function cmdAdopt(db: Db, paneOrTitle: string, opts: AdoptCliOpts): Promise<void> {\n const ws = await resolveWorkstream(opts.workstream);\n\n // Allow `mu agent adopt <pane-id>` (the backend's id form: tmux '%15',\n // herdr 'w1:p2') OR `mu agent adopt <pane-title>` (a string that looks\n // like an agent name; we look it up in the workstream's mux session).\n // Pane-id form is preferred for scripting; pane-title form is the\n // ergonomic form for interactive use.\n // Load-bearing: resolving the pane IS the verb's input.\n const mux = await activeMux();\n let paneId: string;\n if (mux.isValidPaneId(paneOrTitle)) {\n paneId = paneOrTitle;\n } else {\n const session = `mu-${ws}`;\n const panes = await mux.listPanesInSession(session);\n const match = panes.find((p) => p.title === paneOrTitle);\n if (!match) {\n throw new UsageError(\n `no pane with title '${paneOrTitle}' in session ${session} (try \\`mu agent list -w ${ws}\\` and pass the pane id)`,\n );\n }\n paneId = match.paneId;\n }\n\n const adoptOpts: AdoptAgentOptions = {\n paneId,\n workstream: ws,\n name: opts.name,\n cli: opts.cli,\n role: opts.role,\n };\n const result: AdoptAgentResult = await adoptAgent(db, adoptOpts);\n // Refresh title with composed state. Adopt may have set it to just\n // the agent name; this re-renders with status emoji etc.\n await refreshAgentTitle(db, result.agent.name, ws);\n\n // Window-scoped border for the adopted pane's window. (cmdInit set\n // it on _mu but adopted panes can be in any window.) Self-checks\n // MU_BANNER_QUIET; best-effort.\n await mux.enableMuPaneBordersForPane(paneId).catch(() => {});\n\n const nextSteps: NextStep[] = [];\n // An adopted pi pane was started without MU_CTL_SOCK, so sends to it\n // fail loud. Say how to fix that before anything else.\n const ctlDown = result.ctl === \"missing\" || result.ctl === \"refused\";\n if (ctlDown) {\n nextSteps.push(\n {\n intent: \"Restart pi in that pane with the control socket\",\n command: `MU_CTL_SOCK=${result.ctlSocket} pi`,\n },\n {\n intent: \"Or paste into the pane explicitly\",\n command: `mu agent send ${result.agent.name} \"...\" --via mux -w ${ws}`,\n },\n );\n }\n nextSteps.push(\n dispatchHint(result.agent, { plain: ctlDown }),\n { intent: \"Read pane\", command: `mu agent read ${result.agent.name} -w ${ws}` },\n { intent: \"Verify in agent list\", command: `mu agent list -w ${ws}` },\n );\n\n if (opts.json) {\n emitJson({\n adopted: !result.alreadyAdopted,\n alreadyAdopted: result.alreadyAdopted,\n agent: result.agent,\n previousTitle: result.previousTitle,\n paneTitleSetTo: result.paneTitleSetTo,\n ctl: result.ctl,\n ctlSocket: result.ctlSocket,\n nextSteps,\n });\n return;\n }\n if (ctlDown) {\n console.error(\n pc.yellow(\n `warning: adopted pi agent ${result.agent.name} has no control socket (ctl: ${result.ctl}) at ${result.ctlSocket}; \\`mu agent send\\` will fail until pi runs with MU_CTL_SOCK set (or use --via mux)`,\n ),\n );\n }\n\n if (result.alreadyAdopted) {\n console.log(pc.dim(`already adopted: ${result.agent.name} (pane ${result.agent.paneId})`));\n printNextSteps(nextSteps);\n return;\n }\n console.log(\n `Adopted ${pc.bold(result.agent.name)} ${pc.dim(`(pane ${result.agent.paneId}, workstream ${result.agent.workstreamName})`)}`,\n );\n if (result.previousTitle !== null && result.previousTitle !== result.paneTitleSetTo) {\n console.log(pc.dim(` pane title: '${result.previousTitle}' -> '${result.paneTitleSetTo}'`));\n }\n printNextSteps(nextSteps);\n}\n\nexport async function cmdKick(\n db: Db,\n rawName: string,\n opts: { workstream?: string; signal?: string; json?: boolean } = {},\n): Promise<void> {\n const { name } = await resolveEntityRef(db, rawName, opts, \"agent\");\n assertAgentInWorkstream(db, name, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const sigRaw = opts.signal ?? \"SIGINT\";\n if (!isKickSignal(sigRaw)) {\n throw new UsageError(\n `--signal must be one of SIGINT, SIGTERM, SIGKILL (got ${JSON.stringify(sigRaw)})`,\n );\n }\n const signal: KickSignal = sigRaw;\n const result = await kickAgent(db, name, { workstream: ws, signal });\n const agentRow = getAgent(db, name, ws);\n const abort = agentRow === undefined ? null : abortHint(agentRow);\n const nextSteps: NextStep[] = [\n ...(abort === null ? [] : [abort]),\n {\n intent: \"Read the pane to confirm the tool aborted\",\n command: `mu agent read ${name} -n 30 -w ${ws}`,\n },\n {\n intent: \"Send follow-up steering once the prompt returns\",\n command: `mu agent send ${name} '...' -w ${ws}`,\n },\n {\n intent: \"Escalate (graceful → polite → hammer)\",\n command: `mu agent kick ${name} --signal SIGTERM -w ${ws}`,\n },\n ];\n if (opts.json) {\n emitJson({ ...result, nextSteps });\n return;\n }\n console.log(\n `Kicked ${pc.bold(name)} ${pc.dim(`(signal=${result.signal}, pgid=${result.signaledPgid}, comm=${result.foregroundComm}, tty=${result.tty})`)}`,\n );\n printNextSteps(nextSteps);\n}\n\nexport async function cmdAbort(\n db: Db,\n rawName: string,\n opts: { workstream?: string; timeout?: number; json?: boolean } = {},\n): Promise<void> {\n const { name } = await resolveEntityRef(db, rawName, opts, \"agent\");\n assertAgentInWorkstream(db, name, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const result = await abortAgent(db, name, {\n workstream: ws,\n ...(opts.timeout === undefined ? {} : { timeoutMs: Math.round(opts.timeout * 1000) }),\n });\n // An abort that reported idle is the exact after state: no pane read.\n const nextSteps: NextStep[] = [\n {\n intent: \"Steer it with the next instruction\",\n command: `mu agent send ${name} '...' -w ${ws}`,\n },\n ...(result.after === \"idle\"\n ? []\n : [{ intent: \"Read the pane\", command: `mu agent read ${name} -n 30 -w ${ws}` }]),\n ];\n if (opts.json) {\n emitJson({ ...result, nextSteps });\n return;\n }\n console.log(\n result.aborted\n ? `Aborted ${pc.bold(name)} ${pc.dim(`(${result.before} → ${result.after} in ${result.elapsedMs}ms)`)}`\n : `${pc.bold(name)} was ${result.before}; nothing to abort`,\n );\n printNextSteps(nextSteps);\n}\n\n/**\n * `mu agent wait <names...>` — block until agents finish working.\n *\n * The task-less counterpart to `mu task wait`: scratch / off-the-cuff\n * helpers have no task in the DAG, so the only \"done\" signal is the\n * agent's own runtime status. An agent fires when it goes **busy → any\n * other state** (it must be observed busy first, so an already-idle\n * agent doesn't fire instantly — you're waiting for THIS work to end).\n *\n * Mirrors `mu task wait` output/exit shape:\n * exit 0 = condition met; 5 = timeout; 6 = a watched agent's pane died.\n * `--any`/`--first` fire on the first agent; default = all must fire.\n * `--first` additionally prints the firing agent's qualified ref.\n */\nexport async function cmdAgentWait(\n db: Db,\n rawNames: readonly string[],\n opts: {\n any?: boolean;\n first?: boolean;\n timeout?: number;\n afterRuns?: number;\n workstream?: string;\n json?: boolean;\n },\n): Promise<void> {\n if (rawNames.length === 0) {\n throw new UsageError(\"mu agent wait: at least one agent name is required\");\n }\n // --first is a CLI alias for --any with a richer output shape.\n const wantAny = opts.any === true || opts.first === true;\n const wantFirstShape = opts.first === true;\n\n // Resolve each ref — cross-workstream-aware via `<ws>/<name>`; bare\n // names resolve through the standard -w / $MU_SESSION / tmux chain.\n const refs = await Promise.all(\n rawNames.map(async (raw) => {\n const local: { workstream?: string } = { workstream: opts.workstream };\n const name = applyQualifiedRef(raw, local);\n const workstreamName = await resolveWorkstream(local.workstream);\n return { name, workstreamName };\n }),\n );\n\n // --after-runs is a ctl run count: refuse an agent that has none\n // rather than silently polling it with no baseline.\n if (opts.afterRuns !== undefined) {\n for (const ref of refs) {\n const agent = getAgent(db, ref.name, ref.workstreamName);\n if (agent !== undefined && !expectsCtl(agent, agentCtlSocket(db, agent))) {\n throw new UsageError(\n `--after-runs needs a pi agent (control socket); ${ref.workstreamName}/${ref.name} runs ${agent.cli}. Drop --after-runs to wait on its pane state.`,\n );\n }\n }\n }\n\n const readStatuses = async (\n pending: readonly { name: string; workstreamName: string }[],\n ): Promise<\n Map<\n string,\n {\n status: \"busy\" | \"needs_input\" | \"needs_permission\" | \"unknown\" | null;\n unknownReason?: string;\n }\n >\n > => {\n const agents = pending.flatMap((ref) => {\n const agent = getAgent(db, ref.name, ref.workstreamName);\n return agent === undefined ? [] : [agent];\n });\n const readings = await readAgentStates(agents, { stateDir: dirname(db.name) });\n const snapshots = new Map<\n string,\n {\n status: \"busy\" | \"needs_input\" | \"needs_permission\" | \"unknown\" | null;\n unknownReason?: string;\n }\n >();\n for (const ref of pending) {\n const agent = getAgent(db, ref.name, ref.workstreamName);\n const reading = agent === undefined ? undefined : readings.get(agentKey(agent));\n snapshots.set(agentKey(ref), {\n status: reading?.alive === false ? null : (reading?.state ?? \"unknown\"),\n ...(reading?.reason !== undefined ? { unknownReason: reading.reason } : {}),\n });\n }\n return snapshots;\n };\n\n // pi agents: one ctl `wait` per agent, resolved by the extension on\n // agent_settled. `afterRuns` is --after-runs (the `runs` a send\n // replied with, so a run that settled before this wait still counts),\n // else a status read taken BEFORE the wait starts: a followUp queued\n // while busy runs in the same pi run.\n const watch = async (\n ref: { name: string; workstreamName: string },\n signal: AbortSignal,\n ): Promise<AgentWatch | undefined> => {\n const agent = getAgent(db, ref.name, ref.workstreamName);\n if (agent === undefined) return undefined;\n const sock = agentCtlSocket(db, agent);\n if (!expectsCtl(agent, sock)) return undefined;\n // With --after-runs the run past the baseline is the pending work:\n // read as busy until the wait settles; no status probe needed.\n let initial: AgentStatusSnapshot = { status: \"busy\" };\n let afterRuns = opts.afterRuns;\n if (afterRuns === undefined) {\n const probe = await ctlProbe(sock);\n if (probe.kind !== \"ok\") return undefined;\n afterRuns = probe.status.runs;\n initial = { status: ctlRuntimeState(probe.status.state) };\n }\n const settled = ctlRequest(sock, { op: \"wait\", afterRuns }, { signal }).then(\n (reply): AgentStatusSnapshot =>\n reply.ok && reply.state !== undefined\n ? {\n status: ctlRuntimeState(reply.state),\n ...(reply.lastText !== undefined ? { lastText: reply.lastText } : {}),\n ...(reply.lastError !== undefined ? { lastError: reply.lastError } : {}),\n }\n : { status: \"unknown\", unknownReason: reply.ok ? \"ctl wait: no state\" : reply.error },\n // The connection dropped. A socket that still answers (pi's /new\n // restarts the session) hands back to polling; one that does not\n // means the pi that served it is gone.\n async (): Promise<AgentStatusSnapshot> => {\n if (signal.aborted) return { status: \"unknown\" };\n const again = await ctlProbe(sock);\n return again.kind === \"ok\"\n ? { status: \"unknown\", unknownReason: \"ctl wait interrupted\" }\n : { status: null };\n },\n );\n return { initial, settled };\n };\n\n const timeoutMs = (opts.timeout ?? 600) * 1000;\n const result = await waitForAgents(db, refs, {\n any: wantAny,\n timeoutMs,\n readStatuses,\n watch,\n onInitialUnknown: (agents) => {\n const names = agents.map((agent) => `${agent.workstreamName}/${agent.name}`).join(\", \");\n const reasons = [...new Set(agents.map((agent) => agent.unknownReason ?? \"no reason\"))].join(\n \", \",\n );\n process.stderr.write(\n `mu agent wait: state unknown for ${names} (${reasons}); waiting until --timeout\\n`,\n );\n },\n });\n\n const dead = result.agents.filter((a) => a.dead);\n const fired = result.agents.filter((a) => a.fired);\n const firing = wantFirstShape && fired.length > 0 ? fired[0] : null;\n const qualified = (a: { workstreamName: string; name: string }): string =>\n `${a.workstreamName}/${a.name}`;\n // A pi run that settled with its final text already returned it:\n // read the pane only when the text is empty or the run errored.\n const readHint: NextStep[] =\n firing && (!firing.lastText || firing.lastError !== undefined)\n ? [\n {\n intent: \"Read the finished agent\",\n command: `mu agent read ${firing.name} -w ${firing.workstreamName}`,\n },\n ]\n : [];\n\n if (opts.json) {\n emitJson({\n agents: result.agents.map((a) => ({\n ...a,\n outcome: delegateOutcome(a, result.timedOut),\n })),\n timedOut: result.timedOut,\n ...(firing ? { firing: { workstream: firing.workstreamName, name: firing.name } } : {}),\n ...(dead.length > 0 ? { dead: dead.map(qualified) } : {}),\n nextSteps: readHint,\n });\n } else {\n // A dead pane is reported whenever one happened, even beside agents\n // that fired: the wait counts a death as done, so \"All N finished\"\n // would hide a crashed worker.\n if (dead.length > 0) {\n console.log(pc.red(`Agent pane(s) died: ${dead.map(qualified).join(\", \")}`));\n }\n if (result.timedOut) {\n console.log(\n pc.yellow(\n `Timed out after ${opts.timeout ?? 600}s; ${fired.length}/${result.agents.length} finished`,\n ),\n );\n } else if (firing) {\n console.log(`${pc.bold(qualified(firing))} finished`);\n printNextSteps(readHint);\n } else if (fired.length === result.agents.length) {\n console.log(`All ${result.agents.length} agent(s) finished`);\n } else if (fired.length > 0) {\n // --any, or --all where the rest died: name who finished.\n console.log(\n `${fired.map(qualified).join(\", \")} finished (${fired.length}/${result.agents.length})`,\n );\n }\n }\n\n // Exit-code mapping mirrors `mu task wait`: 6 (a watched pane died,\n // even when others finished) wins over 5 (timeout); a clean\n // met-condition is 0.\n if (dead.length > 0) {\n process.exitCode = 6;\n } else if (result.timedOut) {\n process.exitCode = 5;\n }\n}\n\n// ─── commander wiring ──────────────────────────────────────────\n//\n// wireAgentCommands is called by buildProgram() in src/cli.ts. Wired here so\n// every per-namespace builder lives next to its cmd functions.\n\nimport type { Command } from \"commander\";\nimport {\n handle,\n JSON_OPT,\n normalizeInheritedWorkstream,\n parseLines,\n parseNonNegativeInt,\n parsePositiveNumber,\n parseSeconds,\n WORKSTREAM_OPT,\n} from \"../cli.js\";\n// wireSelfCommands needs cmdMyTasks / cmdMyNext which live in cli/tasks.ts\n// (they're task queries scoped to the resolved-self agent). Lateral\n// cluster→cluster import documented as the single intentional edge.\nimport { wireRemoteEnvCommand } from \"./agents-remote.js\";\nimport { cmdMyNext, cmdMyTasks } from \"./tasks.js\";\n\nexport function wireAgentCommands(program: Command): void {\n const agent = program.command(\"agent\").description(\"Agent-level commands\");\n\n agent\n .command(\"spawn <name>\")\n .description(\"Spawn a new agent in a mux pane\")\n .option(\n \"--cli <cli>\",\n \"agent CLI key (default: pi); also used as the lookup key for $MU_<UPPER_CLI>_COMMAND, e.g. --cli pi_big resolves $MU_PI_BIG_COMMAND\",\n \"pi\",\n )\n .option(\n \"--command <cmd>\",\n \"executable to run in the pane (defaults to $MU_<CLI>_COMMAND or the cli value)\",\n )\n .option(\"--tab <tab>\", \"mux window/tab name to group under (defaults to agent name)\")\n .option(\"--role <role>\", \"full-access | read-only\", \"full-access\")\n .option(\"--cwd <cwd>\", \"initial working directory (ignored when --workspace is set)\")\n .option(\"--workspace\", \"auto-create a VCS workspace for this agent and use its path as cwd\")\n .option(\n \"--workspace-backend <name>\",\n \"force a specific VCS backend for --workspace (jj | sl | git | none)\",\n )\n .option(\n \"--workspace-from <ref>\",\n \"base the workspace on a specific commit / branch / changeset\",\n )\n .option(\n \"--workspace-project-root <path>\",\n \"override the project root the workspace branches from (default: cwd)\",\n )\n .option(\"--no-ctl\", \"skip the control-socket handshake with the mu pi extension\")\n .option(\n \"--next-free\",\n \"if <name> is taken, take the next free one (worker-1 → worker-2, review → review-2); --json's agent.name says which\",\n )\n .option(\n \"--send <text>\",\n \"send this text once the agent is up (one mu call for spawn + send; `-` reads stdin). A failed send keeps the pane and exits non-zero; --json still prints the spawn with send.error\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (name: string) {\n const opts = (this as Command).opts() as {\n nextFree?: boolean;\n send?: string;\n cli?: string;\n command?: string;\n tab?: string;\n role?: string;\n cwd?: string;\n workstream?: string;\n workspace?: boolean;\n workspaceBackend?: VcsBackendName;\n workspaceFrom?: string;\n workspaceProjectRoot?: string;\n ctl?: boolean;\n json?: boolean;\n };\n return handle((db) => cmdSpawn(db, name, opts), this as Command)();\n });\n\n agent\n .command(\"send <name> <text>\")\n .description(\n \"Send text to an agent. pi agents: through the control socket (fails loud if it does not answer; no paste fallback); '/new', '/reload' and '/compact [instructions]' run inside pi over the socket (refused while busy unless --force), any other slash command is refused (--via mux types it into the pane). Non-pi CLIs: pasted into the pane (atomic on herdr; bracketed-paste on tmux). --fresh (pi only): start a new session and send the text into it as one operation; returns once the prompt's run has started, so an immediate next send cannot be lost. Use it instead of sending '/new' then the prompt. Text `-` reads stdin: single-quote short text; pipe prose (apostrophes, $, backticks) as a quoted heredoc: mu agent send <name> - <<'EOF'\",\n )\n .option(\n \"--strict-staleness\",\n \"refuse send when the target agent's workspace is stale (default: warn and proceed)\",\n )\n .option(\n \"--steer\",\n \"if pi is busy, deliver after the current tool calls finish, before the next model call (default: after the run ends); does not stop a running tool: use --interrupt\",\n )\n .option(\n \"--interrupt\",\n \"pi only: if busy, abort the current run (kills the running tool; queued messages go back to the editor), wait for pi to settle, then send the text as a new run. Exit 5 if pi does not settle; the text is then not sent\",\n )\n .option(\n \"--timeout <seconds>\",\n \"with --interrupt: max seconds to wait for pi to settle (default 30)\",\n parsePositiveNumber,\n )\n .option(\"--via <transport>\", \"force the transport: ctl or mux (mux = paste into the pane)\")\n .option(\n \"--fresh\",\n \"pi only: new session + this prompt, one operation (refused with exit 4 while pi is busy)\",\n )\n .option(\n \"--force\",\n \"with --fresh or a pi /new, /reload, /compact: abandon a running turn instead of refusing\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (name: string, text: string) {\n const opts = (this as Command).opts() as {\n workstream?: string;\n json?: boolean;\n strictStaleness?: boolean;\n steer?: boolean;\n via?: string;\n fresh?: boolean;\n force?: boolean;\n interrupt?: boolean;\n timeout?: number;\n };\n return handle((db) => cmdSend(db, name, text, opts), this as Command)();\n });\n\n agent\n .command(\"read <name>\")\n .description(\"Read an agent's pane scrollback\")\n .option(\"-n, --lines <n>\", \"show last N lines (default: full scrollback)\", parseLines)\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (name: string) {\n const opts = (this as Command).opts() as {\n lines?: number;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdRead(db, name, opts), this as Command)();\n });\n\n agent\n .command(\"list\")\n .description(\"List agents in the current workstream (reconciled with the active mux)\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as {\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdList(db, opts), this as Command)();\n });\n\n agent\n .command(\"show <name>\")\n .description(\"Show an agent: registry row + recent scrollback (last N lines, default 20)\")\n .option(\"-n, --lines <n>\", \"how many scrollback lines to show (default 20)\", parseLines)\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (name: string) {\n const opts = (this as Command).opts() as {\n lines?: number;\n json?: boolean;\n workstream?: string;\n };\n return handle((db) => cmdAgentShow(db, name, opts), this as Command)();\n });\n\n agent\n .command(\"close <name>\")\n .description(\n \"Kill an agent's pane and remove its registry row. If the agent has a clean workspace (no uncommitted changes AND no commits since fork) it is auto-freed alongside the close; otherwise close refuses (would orphan or lose work) — pass --discard-workspace to free both anyway (lossy), or run `mu workspace free <agent>` first.\",\n )\n .option(\n \"--discard-workspace\",\n \"free the agent's workspace alongside close (lossy: pending changes are gone)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (name: string) {\n const opts = (this as Command).opts() as {\n workstream?: string;\n json?: boolean;\n discardWorkspace?: boolean;\n };\n return handle((db) => cmdClose(db, name, opts), this as Command)();\n });\n\n agent\n .command(\"kick <name>\")\n .description(\n \"Signal the foreground process group of an agent's pane TTY (escape hatch for a worker wedged on an unbounded `find` / busy-wait loop). For a pi agent try `mu agent abort` first: it stops the turn through the control socket. Default --signal SIGINT (graceful, matches Ctrl-C). Refuses when the foreground is the wrapping CLI itself — use `mu agent close` to close the agent.\",\n )\n .option(\n \"--signal <sig>\",\n \"signal to send: SIGINT (default; graceful), SIGTERM (polite), SIGKILL (hammer)\",\n \"SIGINT\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (name: string) {\n const opts = (this as Command).opts() as {\n workstream?: string;\n signal?: string;\n json?: boolean;\n };\n return handle((db) => cmdKick(db, name, opts), this as Command)();\n });\n\n // `mu agent abort` — stop a pi agent's turn through its control socket.\n agent\n .command(\"abort <name>\")\n .description(\n \"Stop a pi agent's current turn through its control socket (what Esc does in the pane), then wait until pi settles. Kills the running tool. A follow-up queued before the abort does not run: pi puts it back into the pane's editor unsent. Idle agents are left alone (exit 0). Exit 5 when still busy after --timeout; then use `mu agent kick`. Works for remote agents through the forwarded socket. Non-pi agents have no socket: use `mu agent kick`.\",\n )\n .option(\n \"--timeout <seconds>\",\n \"max seconds to wait for pi to settle (default 30)\",\n parsePositiveNumber,\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (name: string) {\n const opts = (this as Command).opts() as {\n workstream?: string;\n timeout?: number;\n json?: boolean;\n };\n return handle((db) => cmdAbort(db, name, opts), this as Command)();\n });\n\n wireRemoteEnvCommand(agent);\n\n // `mu agent wait` — the task-less counterpart to `mu task wait`. Block\n // until agents finish (busy → any other state). For scratch /\n // off-the-cuff helpers that own no task to wait on.\n agent\n .command(\"wait <names...>\")\n .description(\n \"Block until agents finish working (busy → any other state). Keys on AGENTS, so it fires on needs_input too — a worker that stopped to ask a question satisfies it. For task-driven work prefer `mu task wait`, which keys on the task reaching CLOSED and has `--stuck-after` / `--on-stall` for the needs_input case; reach for this verb when the agent owns no task to wait on.\",\n )\n .option(\"--any\", \"succeed as soon as ONE listed agent finishes (default: all)\")\n .option(\"--first\", \"alias for --any that also prints the firing agent's ref\")\n .option(\n \"--timeout <seconds>\",\n \"max seconds to wait, fractions allowed (0 = forever, default 600)\",\n parseSeconds,\n )\n .option(\n \"--after-runs <n>\",\n \"pi agents only: fire on the first run settled past N (the `runs` that `mu agent send --json` printed), even one that settled before this wait started\",\n parseNonNegativeInt,\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (names: string[]) {\n const opts = (this as Command).optsWithGlobals() as {\n any?: boolean;\n first?: boolean;\n timeout?: number;\n afterRuns?: number;\n workstream?: string | string[];\n json?: boolean;\n };\n return handle(\n (db) =>\n cmdAgentWait(db, names, {\n ...opts,\n workstream: normalizeInheritedWorkstream(opts.workstream),\n }),\n this as Command,\n )();\n });\n\n // `mu agent adopt` — register an existing mux pane as a managed agent.\n // Lives under `mu agent` like every other agent-lifecycle verb\n // (mu_adopt_should_be_mu_agent_adopt_for).\n agent\n .command(\"adopt <pane-or-title>\")\n .description(\n \"Register an existing mux pane as a managed mu agent (the inverse of `mu agent list`'s 'orphan' state). Pane id form (tmux '%15', herdr 'w1:p2') or pane title form 'worker-2'.\",\n )\n .option(\"--name <name>\", \"agent name (defaults to the pane's current title)\")\n .option(\"--cli <cli>\", \"agent CLI key (default: pi)\")\n .option(\"--role <role>\", \"full-access | read-only\", \"full-access\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (paneOrTitle: string) {\n const opts = (this as Command).optsWithGlobals() as Omit<AdoptCliOpts, \"workstream\"> & {\n workstream?: string | string[];\n };\n return handle(\n (db) =>\n cmdAdopt(db, paneOrTitle, {\n ...opts,\n workstream: normalizeInheritedWorkstream(opts.workstream),\n }),\n this as Command,\n )();\n });\n\n // ─── task ───────────────────────────────────────────────────────────\n}\n\nexport function wireSelfCommands(program: Command): void {\n // `mu me` is the merged self-identity verb (audit_merge_self_verbs_into_mu_me).\n // Default action: identity block + owned tasks (was `mu whoami`).\n // Subcommands:\n // mu me tasks — just the owned-tasks table (was `mu my-tasks`)\n // mu me next [-n K] — top-K ready in self.workstream (was `mu my-next`)\n const me = program\n .command(\"me\")\n .description(\n \"Identify the agent running this process (via $TMUX_PANE) plus its currently-owned tasks (excludes CLOSED by default). Subcommands: `mu me tasks` for just the owned-tasks table; `mu me next [-n K]` for the top-K ready tasks in this agent's workstream.\",\n )\n .option(\"--include-closed\", \"include CLOSED tasks in the owned-tasks list\")\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as { json?: boolean; includeClosed?: boolean };\n return handle((db) => cmdMe(db, opts), this as Command)();\n });\n\n me.command(\"tasks\")\n .description(\n \"List tasks owned by the current agent (the second half of `mu me`'s output). Excludes CLOSED by default.\",\n )\n .option(\"--include-closed\", \"include CLOSED tasks in the list\")\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as { json?: boolean; includeClosed?: boolean };\n return handle((db) => cmdMyTasks(db, opts), this as Command)();\n });\n\n me.command(\"next\")\n .description(\n \"Top-K ready tasks in the current agent's workstream (alias for `task next -w <self.workstream>`)\",\n )\n .option(\n \"-n, --lines <k>\",\n \"how many top-K tasks to return (default 1; 0 = all ready)\",\n parseLines,\n )\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as { lines?: number; json?: boolean };\n return handle((db) => cmdMyNext(db, opts), this as Command)();\n });\n}\n","// mu — shared POSIX single-quote helper.\n//\n// Wrap a token in single quotes for safe interpolation into a /bin/sh\n// command we render for the user to copy-paste (e.g. next-step hints).\n// Embedded single-quotes are escaped via the canonical close-reopen\n// idiom: ' → '\"'\"'.\n\nexport function shellQuote(s: string): string {\n return `'${s.replace(/'/g, `'\"'\"'`)}'`;\n}\n","// mu — the dispatch-time Next: hints for pi agents.\n//\n// One rule, one place: a hint that suggests sending a NEW TASK to an\n// agent that speaks the control socket (expectsCtl) shows `--fresh`, so\n// the task starts in a clean session; a hint that steers or answers a\n// RUNNING agent stays a plain send. Non-pi agents keep the plain send.\n// Models act on the Next: block printed at the moment of decision far\n// more reliably than on skill prose, so this is where --fresh,\n// --interrupt and `mu agent abort` get taught.\n\nimport { type AgentRow, expectsCtl } from \"../agents.js\";\nimport type { CtlStatus } from \"../ctl/protocol.js\";\nimport type { NextStep } from \"../output.js\";\nimport { shellQuote } from \"../shell-quote.js\";\nimport { relTime } from \"./format.js\";\n\nexport type HintAgent = Pick<AgentRow, \"name\" | \"cli\" | \"workstreamName\">;\n\n/** The prompt that hands a claimed task to its owner. */\nfunction dispatchText(task: { id: string; workstream: string }): string {\n return `Claim done: work on ${task.id}. Read: mu task notes ${task.id} -w ${task.workstream}`;\n}\n\n/**\n * \"Send work\" for an agent about to get a new task. pi agents get\n * `--fresh` unless `plain` (e.g. an adopted pane whose socket is down,\n * where the restart / --via mux hints come first).\n */\nexport function dispatchHint(\n agent: HintAgent,\n opts: { task?: { id: string; workstream: string }; plain?: boolean } = {},\n): NextStep {\n const ws = agent.workstreamName;\n const text = opts.task === undefined ? \"'...'\" : shellQuote(dispatchText(opts.task));\n if (opts.plain === true || !expectsCtl(agent)) {\n return { intent: \"Send work\", command: `mu agent send ${agent.name} ${text} -w ${ws}` };\n }\n return {\n intent:\n opts.task === undefined\n ? \"Send the first task (fresh session + prompt in one step)\"\n : `Send the task to ${agent.name} (fresh session + prompt in one step)`,\n command: `mu agent send ${agent.name} --fresh ${text} -w ${ws}`,\n };\n}\n\n/** `mu agent abort` as the first resort for a pi agent; null otherwise. */\nexport function abortHint(agent: HintAgent): NextStep | null {\n if (!expectsCtl(agent)) return null;\n return {\n intent: \"Prefer abort for pi agents (stops the turn through the control socket)\",\n command: `mu agent abort ${agent.name} -w ${agent.workstreamName}`,\n };\n}\n\n/**\n * Hints for a plain or --steer ctl send, from the status read just before\n * it. Busy: the text was queued, so say how long the run has gone and how\n * to make pi act now. Idle after a settled run (plain only): the text\n * probably started a new task in an old context, so nudge toward --fresh.\n */\nexport function plainSendHints(\n agent: HintAgent,\n before: Pick<CtlStatus, \"state\" | \"runs\"> & { since?: number },\n now: number = Date.now(),\n mode: \"followUp\" | \"steer\" = \"followUp\",\n): NextStep[] {\n const { name, workstreamName: ws } = agent;\n if (before.state === \"busy\") {\n const busy = before.since === undefined ? \"busy\" : `busy since ${relTime(now - before.since)}`;\n const lands = mode === \"steer\" ? \"the current tool call\" : \"the current run ends\";\n return [\n {\n intent: `${busy}: sees this after ${lands}; to act now: --interrupt`,\n command: `mu agent send ${name} --interrupt '...' -w ${ws}`,\n },\n ];\n }\n if (mode === \"followUp\" && before.state === \"idle\" && before.runs > 0) {\n return [\n {\n intent: \"Starting unrelated work? Use --fresh next time (new session, no stale context)\",\n command: `mu agent send ${name} --fresh '...' -w ${ws}`,\n },\n ];\n }\n return [];\n}\n\n/** After `mu task wait` fires: hand the owner its next task (in `ws`), fresh. pi only. */\nexport function nextDispatchHint(agent: HintAgent, ws: string): NextStep | null {\n if (!expectsCtl(agent)) return null;\n const forRef = agent.workstreamName === ws ? agent.name : `${agent.workstreamName}/${agent.name}`;\n return {\n intent: `Dispatch the next task to ${agent.name} (pick one with mu task next; fresh session)`,\n command: `mu task claim <id> --for ${forRef} -w ${ws} && mu agent send ${agent.name} --fresh ${shellQuote(dispatchText({ id: \"<id>\", workstream: ws }))} -w ${agent.workstreamName}`,\n };\n}\n","// Shared CLI helper for the two dispatch surfaces that should warn\n// before sending work to a stale workspace:\n// - `mu task claim --for <agent>`\n// - `mu agent send <agent>`\n\nimport type { Db } from \"../db.js\";\nimport { type NextStep, pc } from \"../output.js\";\nimport { TaskClaimStaleWorkspaceError } from \"../tasks.js\";\nimport {\n getWorkspaceStaleness,\n WORKSPACE_STALE_THRESHOLD,\n type WorkspaceStaleness,\n} from \"../workspace.js\";\n\nexport interface StalenessCheckResult {\n staleness: WorkspaceStaleness | null;\n warned: boolean;\n nextStep: NextStep | null;\n}\n\nexport async function checkWorkspaceStalenessForDispatch(\n db: Db,\n agentName: string,\n workstreamName: string,\n opts: { strict?: boolean; warn?: boolean } = {},\n): Promise<StalenessCheckResult> {\n const staleness = await getWorkspaceStaleness(db, agentName, workstreamName);\n if (staleness?.isStale !== true) {\n return { staleness, warned: false, nextStep: null };\n }\n\n const nextStep: NextStep = {\n intent: \"Refresh first\",\n command: `mu workspace refresh ${agentName} -w ${workstreamName}`,\n };\n\n if (opts.strict === true) {\n throw new TaskClaimStaleWorkspaceError(staleness);\n }\n\n if (opts.warn !== false) {\n console.error(formatStaleWorkspaceWarning(staleness));\n }\n\n return { staleness, warned: true, nextStep };\n}\n\nexport function formatStaleWorkspaceWarning(staleness: WorkspaceStaleness): string {\n return pc.yellow(\n `WARN: ${staleness.agentName} workspace is ${staleness.commitsBehindMain} commits behind main (≥${WORKSPACE_STALE_THRESHOLD} = stale)`,\n );\n}\n","// mu — typed-error → exit-code mapping + CLI handler wrapper.\n//\n// Extracted from src/cli.ts (review_cli_ts_past_refactor_signal):\n// classifyError + emitError + handle were ~150 LOC in the middle of\n// cli.ts. They live here so cli.ts is just argument parsing /\n// workstream resolution / program wiring; the typed-error catalogue\n// belongs next to its own helper. cli.ts re-exports `classifyError`\n// and `handle` for back-compat with existing tests + cli/* importers.\n//\n// Exit codes (docs/guide/sql.md § Script with --json):\n// 0 = success\n// 1 = generic error\n// 2 = usage error (validation / missing-flag / type / mutex /\n// unknown subcommand) — commander-detected mistakes AND\n// handler-thrown UsageError. Both surfaces print the failing\n// subcommand's --help (human path) or include a structured\n// `usage` field (--json path). See `audit_cli_validation_uniformity`.\n// 3 = not found (no such agent / task / pane)\n// 4 = conflict (name collision, double-claim, cycle, etc.)\n// 5 = substrate unavailable or unsafe (no multiplexer, DB locked,\n// ops-log drift, a `mu doctor` FAIL row, timeouts)\n// 6 = REAPER_DETECTED — `mu task wait` aborted because the\n// per-poll reconciler flipped a watched task IN_PROGRESS →\n// OPEN (the owning pane was dead). Only fires when the wait\n// target is CLOSED.\n// 7 = STALL_DETECTED — `mu task wait --on-stall exit` aborted\n// because the existing --stuck-after predicate fired on a\n// watched task. Same target=CLOSED carve-out as exit 6; if\n// both fire in the same poll iteration, exit 6 wins.\n\nimport { type Command, CommanderError } from \"commander\";\nimport {\n AgentAbortNeedsCtlError,\n AgentAbortTimeoutError,\n AgentBusyError,\n AgentCtlUnreachableError,\n AgentDiedOnSpawnError,\n AgentExistsError,\n AgentExtensionOutdatedError,\n AgentFreshNeedsCtlError,\n AgentNameExhaustedError,\n AgentNotFoundError,\n AgentNotInWorkstreamError,\n AgentSlashCommandUnsupportedError,\n AgentSpawnCliNotFoundError,\n AgentSpawnStartupError,\n PaneNotInSessionError,\n WorkspacePreservedError,\n} from \"../agents.js\";\nimport {\n type Db,\n openDb,\n SchemaTooNewError,\n SchemaTooOldError,\n WorkstreamNotFoundError,\n} from \"../db.js\";\nimport { DriftDetectedError } from \"../drift.js\";\nimport { HazardFailError } from \"../fleet-hazards.js\";\nimport { LinkConflictError } from \"../link.js\";\nimport { GroupIdAmbiguousError, LogKindReservedError } from \"../logs.js\";\nimport {\n HerdrCommandOverrideError,\n HerdrUnsupportedCliError,\n HerdrWorkspaceGroupCloseError,\n MuxError,\n NoMultiplexerError,\n PaneNotFoundError,\n} from \"../mux.js\";\nimport {\n hasNextSteps,\n isJsonMode,\n type NextStep,\n pc,\n printNextStepsTo,\n printUsageHuman,\n renderUsageJson,\n type UsageJson,\n} from \"../output.js\";\nimport { RebuildTargetExistsError, RebuildTargetIsSourceError } from \"../rebuild.js\";\nimport {\n ambientFlush,\n ambientIngest,\n SyncPeerNotFoundError,\n SyncPeerRefAmbiguousError,\n SyncSourceNotFoundError,\n syncEnabled,\n} from \"../sync.js\";\nimport {\n ClaimerNotRegisteredError,\n CrossWorkstreamEdgeError,\n CycleError,\n InvalidSubstateError,\n ReaperDetectedDuringWaitError,\n StallDetectedDuringWaitError,\n SubstateReasonRequiredError,\n TaskAlreadyOwnedError,\n TaskClaimStaleWorkspaceError,\n TaskExistsError,\n TaskIdInvalidError,\n TaskInTriageError,\n TaskNotFoundError,\n TaskNotInWorkstreamError,\n TaskParkedError,\n TaskParkStateError,\n TaskTitleSlugEmptyError,\n} from \"../tasks.js\";\nimport { NothingToUndoError, UndoGroupNotFoundError, UndoSupersededError } from \"../undo.js\";\nimport { WorkspaceConflictError, WorkspaceDirtyError, WorkspaceVcsRequiredError } from \"../vcs.js\";\nimport {\n HomeDirAsProjectRootError,\n WorkspaceExistsError,\n WorkspaceNotFoundError,\n WorkspacePathNotEmptyError,\n} from \"../workspace.js\";\nimport {\n WorkstreamExistsError,\n WorkstreamNameInvalidError,\n WorkstreamNameReservedError,\n} from \"../workstream.js\";\n\nexport class UsageError extends Error {\n override readonly name = \"UsageError\";\n}\n\n/**\n * Internal CLI-control sentinel for handlers that already rendered their\n * success/partial-success payload and only need `handle()` to exit with a\n * non-zero code AFTER its DB-close finally has run. Unlike `UsageError` it\n * emits no stderr text; it is a return-code mechanism owned by handle().\n */\nexport class CliExitError extends Error {\n override readonly name = \"CliExitError\";\n constructor(public readonly exitCode: number) {\n super(`exit ${exitCode}`);\n }\n}\n\n// ─── Active-command tracking for the validation-error contract ──────\n//\n// `setActiveCommand` is called by `handle()` at the entry of every\n// .action() body. `emitError()` reads it to render the failing\n// subcommand's --help on usage errors. We thread it via module-local\n// state (mirror of `isJsonMode` reading process.argv) instead of\n// constructor-arg-ing every UsageError throw site — there are 27 of\n// them, several inside helpers (resolveWorkstream, parseStatusFilter)\n// that don't know which subcommand called them.\n//\n// Cleared in handle()'s finally so a sequence of test calls (which\n// re-use the process) doesn't bleed state across cases.\n\nlet activeCommand: Command | undefined;\n\n/** Test-only: introspect the current active command. */\nexport function getActiveCommandForTest(): Command | undefined {\n return activeCommand;\n}\n\n/** Test-only: clear stale state between vitest cases. */\nexport function clearActiveCommandForTest(): void {\n activeCommand = undefined;\n}\n\n/** Map a commander.CommanderError to (exitCode, label). The codes that\n * represent successful early-exits (--help, --version) are mapped to\n * exitCode 0 and a sentinel label so emitError can short-circuit\n * without printing anything. All other codes are uniform exit 2 —\n * the documented \"usage error\" lane that handler-thrown UsageError\n * also occupies. */\nfunction classifyCommanderError(err: CommanderError): { label: string; exitCode: number } {\n if (\n err.code === \"commander.helpDisplayed\" ||\n err.code === \"commander.help\" ||\n err.code === \"commander.version\"\n ) {\n return { label: \"help\", exitCode: 0 };\n }\n // Everything else is a usage mistake (missing required option,\n // unknown option, unknown command, missing argument, type-coercion\n // via InvalidArgumentError). Renumber commander's default exit 1\n // to mu's documented exit 2 so the surface is uniform with the\n // handler-thrown UsageError lane.\n return { label: \"error\", exitCode: 2 };\n}\n\n/** Predicate: is this error a usage-class one for which we should\n * render the failing subcommand's --help? Three families:\n * 1. CommanderError (missing required option, unknown option,\n * unknown command, missing argument, type-coercion failure).\n * 2. UsageError (handler-thrown mutex / arity / range checks).\n * 3. Typed *Invalid* domain errors that fault on a value the\n * operator typed at the CLI (workstream name, task id, prune-flag\n * combination). The verb's --help would\n * have explained the constraint; show it.\n *\n */\nfunction isUsageClassError(err: unknown): boolean {\n if (err instanceof CommanderError) return true;\n if (err instanceof UsageError) return true;\n if (\n err instanceof WorkstreamNameInvalidError ||\n err instanceof WorkstreamNameReservedError ||\n err instanceof TaskIdInvalidError ||\n err instanceof TaskTitleSlugEmptyError\n ) {\n return true;\n }\n return false;\n}\n\n/**\n * Raised when a bare entity name is used at the CLI but the resolution\n * context (--workstream / $MU_SESSION / current tmux session) is empty\n * AND the same name lives in two or more workstreams. Exit 4 (conflict)\n * via classifyError. The errorNextSteps lists every candidate as a\n * runnable qualified-form invocation — a one-paste fix.\n *\n * See verb_arg_qualified_workstream_name for the design.\n */\nexport class NameAmbiguousError extends Error {\n override readonly name = \"NameAmbiguousError\";\n constructor(\n public readonly entityName: string,\n public readonly candidates: readonly string[],\n public readonly kind: \"task\" | \"agent\" | \"workspace\",\n ) {\n super(\n `${kind} name \"${entityName}\" exists in ${candidates.length} workstreams (${candidates.join(\", \")}); pass -w <workstream> or use the qualified form <workstream>/${entityName}`,\n );\n }\n errorNextSteps(): NextStep[] {\n return this.candidates.map((ws) => ({\n intent: `Target the ${ws} ${this.kind}`,\n command: `${ws}/${this.entityName}`,\n }));\n }\n}\n\n/**\n * Map a typed error to (label, exitCode). The label is the prefix\n * before the message in human output (e.g. \"conflict\", \"not found\");\n * the exit code is what the process exits with.\n *\n * Order matters: more-specific classes first. The fallthrough at the\n * end is the generic exit-1 catch-all.\n */\nexport function classifyError(err: unknown): { label: string; exitCode: number } {\n if (\n err instanceof UsageError ||\n // `mu log --kind task|note|...`: a tag naming a projectable entity.\n err instanceof LogKindReservedError ||\n // abort on a non-pi agent: the operator picked the wrong verb (kick).\n err instanceof AgentAbortNeedsCtlError ||\n // send --fresh on an agent with no control socket: wrong recipe.\n err instanceof AgentFreshNeedsCtlError ||\n // an unsupported slash command to a pi agent: --via mux is the recipe.\n err instanceof AgentSlashCommandUnsupportedError ||\n err instanceof WorkstreamNameInvalidError ||\n err instanceof WorkstreamNameReservedError ||\n // Same typed-*Invalid* class: a task id or a title the operator\n // typed that cannot become an id. isUsageClassError prints --help.\n err instanceof TaskIdInvalidError ||\n err instanceof TaskTitleSlugEmptyError ||\n // The operator asked the ACTIVE backend for something it cannot do:\n // a `--cli` the mux does not recognise as an agent kind, or a\n // `--command` / `MU_<CLI>_COMMAND` override it cannot honour. The\n // substrate is healthy and answered precisely, so this is the usage\n // lane, not the exit-5 \"mux is down\" lane. Both refuse BEFORE any\n // side effect.\n err instanceof HerdrUnsupportedCliError ||\n err instanceof HerdrCommandOverrideError ||\n // herdr refused to close a workspace with linked worktree\n // workspaces. Same lane: the substrate answered precisely and only\n // the operator can decide whether those siblings may die.\n err instanceof HerdrWorkspaceGroupCloseError\n ) {\n return { label: \"error\", exitCode: 2 };\n }\n if (\n err instanceof AgentNotFoundError ||\n err instanceof TaskNotFoundError ||\n err instanceof WorkstreamNotFoundError ||\n err instanceof WorkspaceNotFoundError\n ) {\n // WorkstreamNotFoundError originates inside resolveWorkstreamId\n // (src/db.ts) — it's the canonical resolve-time miss for the\n // first leg of the SDK boundary (operator-name → surrogate id).\n // Without this entry it fell through to generic exit 1, robbing\n // operators of the same -> exit-3 mapping that AgentNotFoundError /\n // TaskNotFoundError get. (schema_v5_cli_boundary)\n return { label: \"not found\", exitCode: 3 };\n }\n if (\n err instanceof NameAmbiguousError ||\n err instanceof AgentExistsError ||\n err instanceof AgentNameExhaustedError ||\n err instanceof TaskExistsError ||\n err instanceof TaskAlreadyOwnedError ||\n // Substate refusals (ts_4): a missing --why, a park from the wrong\n // phase, a claim on a parked task, a pair outside TASK_SUBSTATES.\n err instanceof SubstateReasonRequiredError ||\n err instanceof TaskParkStateError ||\n err instanceof TaskParkedError ||\n err instanceof TaskInTriageError ||\n err instanceof InvalidSubstateError ||\n err instanceof TaskClaimStaleWorkspaceError ||\n err instanceof TaskNotInWorkstreamError ||\n err instanceof AgentNotInWorkstreamError ||\n err instanceof PaneNotInSessionError ||\n err instanceof CycleError ||\n err instanceof CrossWorkstreamEdgeError ||\n err instanceof WorkspaceExistsError ||\n err instanceof WorkspacePathNotEmptyError ||\n err instanceof WorkspacePreservedError ||\n err instanceof HomeDirAsProjectRootError ||\n err instanceof WorkspaceVcsRequiredError ||\n err instanceof WorkspaceDirtyError ||\n err instanceof ClaimerNotRegisteredError ||\n err instanceof SchemaTooOldError ||\n err instanceof SchemaTooNewError ||\n err instanceof WorkstreamExistsError ||\n // Rebuild refuses to overwrite an existing target or to write onto\n // the source DB: both are name/state collisions, not usage errors.\n err instanceof RebuildTargetExistsError ||\n err instanceof RebuildTargetIsSourceError ||\n // An abbreviated group id matching several groups: the operator must\n // disambiguate. Guessing would be catastrophic for `mu undo`.\n err instanceof GroupIdAmbiguousError ||\n err instanceof LinkConflictError\n ) {\n return { label: \"conflict\", exitCode: 4 };\n }\n if (\n err instanceof UndoGroupNotFoundError ||\n err instanceof NothingToUndoError ||\n // A `--repair <peer>` ref or a `--from <path>` that names nothing:\n // the same resolve-time-miss lane as every other not-found.\n err instanceof SyncPeerNotFoundError ||\n err instanceof SyncSourceNotFoundError\n ) {\n return { label: \"not found\", exitCode: 3 };\n }\n if (err instanceof SyncPeerRefAmbiguousError) {\n // An abbreviated peer id matching several peers. Same rule as an\n // ambiguous group id: the operator disambiguates, mu never guesses.\n return { label: \"conflict\", exitCode: 4 };\n }\n if (err instanceof UndoSupersededError) {\n // A conflict in the precise sense the exit-code map means: the\n // requested change collides with existing state (later work), and the\n // operator must choose (--force) rather than retry.\n return { label: \"conflict\", exitCode: 4 };\n }\n if (err instanceof DriftDetectedError) {\n // 5 = substrate unavailable/inconsistent. Drift means the SQLite\n // substrate is internally inconsistent (the log and the tables\n // disagree), which is exactly that category — not a usage mistake (2)\n // and not a name collision (4).\n return { label: \"drift\", exitCode: 5 };\n }\n if (err instanceof HazardFailError) {\n // Same lane as drift: a doctor `fail` row (the DB inside\n // MU_SYNC_DIR) means the substrate is unsafe to keep writing.\n return { label: \"doctor\", exitCode: 5 };\n }\n if (isSqliteBusy(err)) {\n // Another process held the write lock past busy_timeout (5s, set in\n // openDb). The DB is unavailable, not wrong: retry later.\n return { label: \"db locked\", exitCode: 5 };\n }\n if (err instanceof AgentSpawnCliNotFoundError) {\n // Pre-flight failure: --cli's resolved binary isn't on PATH. We\n // refused before any side effect, so this is the cleanest\n // operator-typo lane there is. Generic exit 1 (substrate-class)\n // matches AgentDiedOnSpawnError / AgentSpawnStartupError below —\n // all three are \"the spawn can't produce a working agent\".\n return { label: \"spawn cli not found\", exitCode: 1 };\n }\n if (err instanceof AgentCtlUnreachableError) {\n // The agent runs, but mu cannot control it: same \"spawn can't\n // produce a working agent\" lane as the spawn failures around it.\n return { label: \"ctl unreachable\", exitCode: 1 };\n }\n if (err instanceof AgentDiedOnSpawnError) {\n // Substrate-level failure (CLI exited at spawn). The message is\n // already rich (includes captured scrollback). Generic exit 1.\n return { label: \"spawn failed\", exitCode: 1 };\n }\n if (err instanceof AgentSpawnStartupError) {\n // Pane is alive but the spawned CLI parked at a known\n // provider-auth-failure prompt. Same generic exit 1 lane as\n // AgentDiedOnSpawnError — both are \"the spawn looked OK to mu but\n // the operator can't actually use this agent\". The error message\n // already carries the matched line + scrollback;\n // errorNextSteps() carries the remediation recipe.\n return { label: \"spawn startup error\", exitCode: 1 };\n }\n if (err instanceof AgentExtensionOutdatedError) {\n // The agent runs, but its extension cannot serve this op yet:\n // a state conflict the operator resolves by /reload or respawn.\n return { label: \"extension outdated\", exitCode: 4 };\n }\n if (err instanceof AgentBusyError) {\n // The agent's state collides with the request; abort or --force.\n return { label: \"conflict\", exitCode: 4 };\n }\n if (err instanceof AgentAbortTimeoutError) {\n // Same lane as the wait verbs' timeout: still busy, try again or kick.\n return { label: \"timeout\", exitCode: 5 };\n }\n if (err instanceof NoMultiplexerError) {\n return { label: \"no multiplexer\", exitCode: 5 };\n }\n if (err instanceof MuxError || err instanceof PaneNotFoundError) {\n // MuxError is the base of the per-backend families (TmuxError, …),\n // so one instanceof covers every multiplexer.\n return { label: \"mux\", exitCode: 5 };\n }\n if (err instanceof WorkspaceConflictError) {\n // Rebase produced conflicts. git/sl aborted it (workspace unchanged);\n // jj kept it with the conflicts committed in place. Either way the\n // operator must step in by hand. Distinct from the typed-conflict-\n // of-state family (exit 4), which refuses before running anything.\n // Same exit-code lane as TmuxError (manual recovery required).\n return { label: \"workspace conflict\", exitCode: 5 };\n }\n if (err instanceof ReaperDetectedDuringWaitError) {\n // task_wait_reconcile_dead_panes: distinct exit code (6) so\n // operator scripts can branch on \"worker died, not a generic\n // failure\" vs the timeout (5) and the typed conflict family (4).\n return { label: \"reaper\", exitCode: 6 };\n }\n if (err instanceof StallDetectedDuringWaitError) {\n // task_wait_stall_action_flag: distinct exit code (7) so\n // operator scripts can branch on \"worker idle, ambiguous\" vs\n // the unambiguous dead-pane (6). Same precedence rule lives at\n // the wait call site: if both fire in one poll, the\n // ReaperDetectedDuringWaitError throw runs first, so exit 6 wins.\n return { label: \"stall\", exitCode: 7 };\n }\n return { label: \"error\", exitCode: 1 };\n}\n\n/** better-sqlite3's SqliteError for a lock it could not get: SQLITE_BUSY\n * ('database is locked') and SQLITE_LOCKED, with their extended codes. */\nfunction isSqliteBusy(err: unknown): boolean {\n if (!(err instanceof Error) || err.name !== \"SqliteError\") return false;\n const code = (err as { code?: unknown }).code;\n return (\n typeof code === \"string\" && (code.startsWith(\"SQLITE_BUSY\") || code.startsWith(\"SQLITE_LOCKED\"))\n );\n}\n\n/** prose-quoting: on the verbs that carry prose, \"too many arguments\"\n * nearly always means an apostrophe ended a single-quoted string and\n * bash split the rest into words. Point at the stdin form. */\nfunction quotingHint(err: unknown, cmd: Command | undefined): NextStep | undefined {\n if (!(err instanceof CommanderError) || err.code !== \"commander.excessArguments\") return;\n const verb = `${cmd?.parent?.name()} ${cmd?.name()}`;\n const first = cmd?.args[0] ?? \"<id>\";\n const command =\n verb === \"task add\"\n ? \"mu task add <id> -t '<title>' -i <n> -e <days> --note - <<'EOF'\"\n : verb === \"task note\"\n ? `mu task note ${first} - <<'EOF'`\n : verb === \"agent send\"\n ? `mu agent send ${first === \"<id>\" ? \"<name>\" : first} - <<'EOF'`\n : undefined;\n if (command === undefined) return;\n return {\n intent:\n \"a quote in the text probably ended the string early (an apostrophe inside '...'); pass long text with a quoted heredoc\",\n command,\n };\n}\n\n/** Render error + nextSteps to stderr and return the resolved exit\n * code. Returning the exitCode lets `handle` reuse it instead of\n * re-classifying the same error twice (review_code_classify_error_called_twice).\n *\n * audit_cli_validation_uniformity: usage-class errors (commander +\n * UsageError + typed *Invalid*) ALSO emit the failing subcommand's\n * --help (human path) or a structured `usage` field (JSON path). */\nfunction emitError(err: unknown): number {\n if (err instanceof CliExitError) return err.exitCode;\n\n // Commander's --help / --version success-exits arrive as CommanderError\n // with exitCode 0. helpInformation() has already been written by\n // commander itself; nothing more to do.\n if (err instanceof CommanderError) {\n const { exitCode } = classifyCommanderError(err);\n if (exitCode === 0) return 0;\n }\n\n const message = err instanceof Error ? err.message : String(err);\n const { label, exitCode } =\n err instanceof CommanderError ? classifyCommanderError(err) : classifyError(err);\n const errClass = err instanceof Error ? err.name : \"Error\";\n const steps: NextStep[] = hasNextSteps(err) ? err.errorNextSteps() : [];\n const quoting = quotingHint(err, activeCommand);\n if (quoting) steps.push(quoting);\n // Strip commander's own \"error: \" prefix — we re-add our own \"error: \"\n // (red, in the human path) and don't want \"error: error: ...\".\n const cleanMessage =\n err instanceof CommanderError && message.startsWith(\"error: \")\n ? message.slice(\"error: \".length)\n : message;\n const usageCmd = isUsageClassError(err) ? activeCommand : undefined;\n const usage: UsageJson | undefined = usageCmd ? renderUsageJson(usageCmd) : undefined;\n\n if (isJsonMode()) {\n const envelope: Record<string, unknown> = {\n error: errClass,\n message: cleanMessage,\n nextSteps: steps,\n exitCode,\n };\n if (usage) envelope.usage = usage;\n process.stderr.write(`${JSON.stringify(envelope)}\\n`);\n return exitCode;\n }\n\n console.error(pc.red(`${label}: ${cleanMessage}`));\n if (steps.length > 0) {\n printNextStepsTo(steps, \"stderr\");\n }\n if (usageCmd) {\n printUsageHuman(usageCmd);\n }\n return exitCode;\n}\n\nexport interface HandleOptions {\n /**\n * Opt OUT of the ambient sync hook. Exactly one verb sets this today:\n * `mu sql`, the escape hatch whose no-surprise-mutations property is\n * load-bearing. An operator running `mu sql \"SELECT ...\"` to inspect\n * state must see the state as it is, not as it becomes once a peer's\n * segment lands mid-query.\n */\n ambientSync?: false;\n}\n\n/** Wrap an async handler so typed errors become specific exit codes.\n *\n * The optional `command` arg is the failing subcommand's `Command`\n * (commander's `this` in a `.action(function () { ... })` body).\n * When supplied, usage-class errors thrown inside `fn` will render\n * that subcommand's --help (human) or `usage` JSON (--json).\n *\n * THE AMBIENT-SYNC SEAM. `handle()` is the one place every verb passes\n * through, and it is ALREADY async while most verb bodies are\n * synchronous — which is exactly why the hook belongs here and nowhere\n * else. `ambientFlush` is async (it takes a cross-process file lock); if the\n * hook lived inside the verbs, ~63 synchronous handlers would have had\n * to become async to await it. Here, one `await` before `fn(db)` and one\n * after covers all of them, and no verb learns that sync exists.\n *\n * Order is load-bearing: INGEST before the body (so the verb reads the\n * freshest state transport has delivered) and FLUSH after (so the ops\n * the verb just wrote are in this machine's segment before the process\n * exits, rather than waiting for the next invocation).\n *\n * Neither half can fail the command — see src/sync.ts. */\nexport function handle(\n fn: (db: Db) => Promise<void>,\n command?: Command,\n opts?: HandleOptions,\n): () => Promise<void> {\n return async () => {\n let db: Db | undefined;\n let exitCode: number | undefined;\n activeCommand = command;\n // The single `if` the unconfigured single-machine case pays: one env\n // var read, no promise allocated, no filesystem touched.\n const ambient = opts?.ambientSync !== false && syncEnabled();\n try {\n db = openDb();\n if (ambient) await ambientIngest(db);\n await fn(db);\n } catch (err) {\n exitCode = emitError(err);\n } finally {\n activeCommand = undefined;\n // Flush even on the error path: the verb may have committed ops\n // before throwing (a cascade that hit a cycle halfway), and those\n // ops are already canonical in `ops`. Withholding them from the\n // segment would make this machine's history depend on whether the\n // command happened to exit 0.\n if (ambient && db !== undefined) {\n try {\n await ambientFlush(db);\n } catch {\n // ambientFlush is already total; belt and braces.\n }\n }\n try {\n db?.close();\n } catch {\n // best effort\n }\n }\n if (exitCode !== undefined) process.exit(exitCode);\n };\n}\n\n/** Translate a commander parse-time error into mu's wire format,\n * then return the exit code. Used by the top-level `parseAsync` catch\n * in cli.ts so commander mistakes go through the same emitError\n * pipeline that handler-thrown errors use. */\nexport function emitParseError(err: unknown, failingCommand: Command | undefined): number {\n activeCommand = failingCommand;\n try {\n return emitError(err);\n } finally {\n activeCommand = undefined;\n }\n}\n\n/** Walk argv tokens against the program tree to find the deepest\n * matching subcommand. Used by parseAsync's catch to identify which\n * subcommand commander was processing when it threw. Skips options the\n * current command declares (and their values) the way commander's\n * parseOptions does, so a leading global (`mu --json task list`,\n * `mu -w x --json task note …`) still resolves the verb. Stops at an\n * unknown option or token. */\nexport function findCommandForArgv(root: Command, argv: readonly string[]): Command {\n let cur: Command = root;\n for (let i = 0; i < argv.length; i++) {\n const t = argv[i] ?? \"\";\n if (t === \"--\") break;\n if (t.length > 1 && t.startsWith(\"-\")) {\n // Inline value: `--flag=value`, or `-wvalue` for a short flag.\n const long = t.startsWith(\"--\");\n const eq = long ? t.indexOf(\"=\") : -1;\n const flag = long ? (eq === -1 ? t : t.slice(0, eq)) : t.slice(0, 2);\n const inline = long ? eq !== -1 : t.length > 2;\n const opt = cur.options.find((o) => o.short === flag || o.long === flag);\n if (!opt || (inline && !opt.required)) break;\n if (inline || !opt.required) continue;\n i++;\n // A variadic option keeps consuming non-option tokens, as in\n // commander: `--substate a b` binds [a, b] to --substate.\n if (opt.variadic) {\n while (i + 1 < argv.length && !(argv[i + 1] ?? \"-\").startsWith(\"-\")) i++;\n }\n continue;\n }\n const next: Command | undefined = cur.commands.find(\n (c) => c.name() === t || (c.aliases().includes(t) ?? false),\n );\n if (!next) break;\n cur = next;\n }\n return cur;\n}\n","// mu — `-` as a text argument: read the text from stdin.\n//\n// Prose (notes, briefs) breaks shell quoting: an apostrophe ends '...',\n// and \"...\" expands $VAR and backticks. A quoted heredoc piped to `-`\n// needs no quoting at all: `mu task note x - <<'EOF' ... EOF`.\n\nimport { UsageError } from \"./handle.js\";\n\n/** The argument value that means \"read the text from stdin\". */\nexport const STDIN_ARG = \"-\";\n\ntype StdinReader = () => Promise<string>;\n\nasync function readProcessStdin(): Promise<string> {\n let text = \"\";\n process.stdin.setEncoding(\"utf8\");\n for await (const chunk of process.stdin) text += chunk;\n return text;\n}\n\nlet reader: StdinReader | null = null;\n\n/** Test seam: replace the stdin reader (null restores process.stdin). */\nexport function setStdinReaderForTests(fn: StdinReader | null): void {\n reader = fn;\n}\n\n/** Read the text verbatim, minus all trailing newlines (as bash\n * `$(...)` strips them); interior newlines are kept.\n * Empty input is a UsageError: `-` with nothing piped is a mistake. */\nexport async function readStdinText(what: string): Promise<string> {\n const text = (await (reader ?? readProcessStdin)()).replace(/\\n+$/, \"\");\n if (text.trim() === \"\") {\n throw new UsageError(`${what} is \"-\" but stdin was empty; pipe the text in: <<'EOF' ... EOF`);\n }\n return text;\n}\n","// mu — `mu agent remote-env`: print the ssh socket-forward args and the\n// identity env a remote pi agent needs. Prints only; mu runs no ssh.\n//\n// The remote pi's extension serves its control socket at the REMOTE\n// path ($MU_CTL_SOCK); `ssh -L <local>:<remote>` makes it answer at the\n// LOCAL derived path, which every mu verb already connects to. One\n// transport for local and remote agents.\n\nimport { dirname } from \"node:path\";\nimport type { Command } from \"commander\";\nimport { isValidAgentName } from \"../agents.js\";\nimport {\n emitJson,\n handle,\n JSON_OPT,\n resolveWorkstream,\n UsageError,\n WORKSTREAM_OPT,\n} from \"../cli.js\";\nimport { CTL_SOCK_ENV, ctlSocketPath, MAX_SOCK_PATH, remoteCtlSocketPath } from \"../ctl/path.js\";\nimport type { Db } from \"../db.js\";\nimport { type NextStep, pc, printNextSteps } from \"../output.js\";\nimport { shellQuote } from \"../shell-quote.js\";\nimport { isValidWorkstreamName } from \"../workstream.js\";\n\nexport interface RemoteEnv {\n agent: string;\n workstream: string;\n /** The derived path mu connects to; ssh binds it. */\n localSock: string;\n /** Where the remote pi's extension listens ($MU_CTL_SOCK there). */\n remoteSock: string;\n /** ssh options, ready to splice into an ssh command line. */\n sshArgs: string;\n /** Identity env as `K=V` words, for the remote side of the command. */\n env: string;\n /** A complete example `--command` value for `mu agent spawn`. */\n command: string;\n}\n\n/** ssh options forcing a direct (non-multiplexed) connection. */\nconst SSH_DIRECT_OPTS = \"-o ControlMaster=no -o ControlPath=none\";\n\n/** Characters that survive unquoted inside a single-quoted remote command. */\nconst SAFE_WORD = /^[A-Za-z0-9_./:@%+-]+$/;\n\n/**\n * Characters allowed in --remote-sock. SAFE_WORD minus ':' (the `-L`\n * field separator) and '%' (ssh percent-expands forward paths, so the\n * forward would point at a different socket than $MU_CTL_SOCK).\n */\nconst REMOTE_SOCK = /^[A-Za-z0-9_./@+-]+$/;\n\nfunction word(s: string): string {\n return SAFE_WORD.test(s) ? s : shellQuote(s);\n}\n\nexport function buildRemoteEnv(\n db: Db,\n agent: string,\n workstream: string,\n remoteSock?: string,\n): RemoteEnv {\n if (!isValidAgentName(agent)) {\n throw new UsageError(`invalid agent name ${JSON.stringify(agent)}`);\n }\n if (!isValidWorkstreamName(workstream)) {\n throw new UsageError(`invalid workstream name ${JSON.stringify(workstream)}`);\n }\n // Same base as spawn (the DB's directory), so the forward lands where\n // spawn's handshake and every later verb look.\n const localSock = ctlSocketPath(workstream, agent, dirname(db.name));\n const remote = remoteSock ?? remoteCtlSocketPath(workstream, agent, process.getuid?.() ?? 0);\n if (!remote.startsWith(\"/\") || !REMOTE_SOCK.test(remote)) {\n throw new UsageError(\n `--remote-sock must be an absolute path of [A-Za-z0-9_./@+-] characters (got ${JSON.stringify(remote)}): it is spliced unquoted into the remote command, and ssh -L treats ':' as a separator and expands '%' tokens`,\n );\n }\n if (Buffer.byteLength(remote) > MAX_SOCK_PATH) {\n throw new UsageError(\n `--remote-sock is ${Buffer.byteLength(remote)} bytes; unix socket paths must stay within ${MAX_SOCK_PATH}`,\n );\n }\n // ControlMaster=no + ControlPath=none: a direct connection per agent.\n // With `ControlMaster auto` in ~/.ssh/config the pane's ssh becomes a\n // mux client of an existing master, and the -L unix forward never binds\n // the local socket (spawn then reports ctl missing). The connection\n // lives and dies with the pane anyway, so sharing a master buys nothing.\n const sshArgs = `${SSH_DIRECT_OPTS} -o StreamLocalBindUnlink=yes -o ExitOnForwardFailure=yes -L ${word(`${localSock}:${remote}`)}`;\n const env = `MU_MANAGED_AGENT=1 MU_AGENT_NAME=${agent} MU_WORKSTREAM=${workstream} ${CTL_SOCK_ENV}=${remote}`;\n // `$SHELL -ilc`: ssh's remote command runs in a non-interactive shell\n // that skips ~/.zshrc / ~/.bashrc, where PATH (mise, nvm) and provider\n // env usually live; pi then dies at startup. The interactive login\n // shell loads them. Single quotes keep $SHELL for the REMOTE side.\n const command = `ssh ${sshArgs} <host> -t 'cd <remote-dir> && ${env} $SHELL -ilc \"pi --approve\"'`;\n return { agent, workstream, localSock, remoteSock: remote, sshArgs, env, command };\n}\n\nexport async function cmdRemoteEnv(\n db: Db,\n agent: string,\n opts: { workstream?: string; remoteSock?: string; shell?: boolean; json?: boolean },\n): Promise<void> {\n const ws = await resolveWorkstream(opts.workstream);\n const r = buildRemoteEnv(db, agent, ws, opts.remoteSock);\n if (opts.shell) {\n // eval-safe: every value single-quoted.\n console.log(`MU_SSH_ARGS=${shellQuote(r.sshArgs)}`);\n console.log(`MU_REMOTE_ENV=${shellQuote(r.env)}`);\n return;\n }\n const nextSteps: NextStep[] = [\n {\n intent: \"Spawn it (replace <host> and <remote-dir>; the host needs `mu link pi`)\",\n command: `mu agent spawn ${agent} -w ${ws} --command ${shellQuote(r.command)}`,\n },\n {\n intent: \"Or set MU_SSH_ARGS / MU_REMOTE_ENV in your shell\",\n command: `eval \"$(mu agent remote-env ${agent} -w ${ws} --shell)\"`,\n },\n ];\n if (opts.json) {\n emitJson({ ...r, nextSteps });\n return;\n }\n console.log(`${pc.bold(\"ssh args\")} ${r.sshArgs}`);\n console.log(`${pc.bold(\"env\")} ${r.env}`);\n console.log(`${pc.bold(\"command\")} ${r.command}`);\n printNextSteps(nextSteps);\n}\n\nexport function wireRemoteEnvCommand(agent: Command): void {\n agent\n .command(\"remote-env <name>\")\n .description(\n \"Print, without running anything, what a remote pi agent's ssh command needs: the socket forward (-o ControlMaster=no -o ControlPath=none -o StreamLocalBindUnlink=yes -o ExitOnForwardFailure=yes -L <local>:<remote>) and the identity env (MU_MANAGED_AGENT, MU_AGENT_NAME, MU_WORKSTREAM, MU_CTL_SOCK). mu then reaches the remote pi through the local socket exactly like a local one. ControlMaster=no / ControlPath=none give each agent a direct connection: a multiplexed ssh (ControlMaster auto in ~/.ssh/config) never binds the local end of the forward. The example command wraps pi in `$SHELL -ilc` because ssh's non-interactive shell skips ~/.zshrc / ~/.bashrc (PATH, provider env); drop the wrapper if your remote env needs no rc file. The host needs the mu extension (`mu link pi` there) and sshd must allow the forward: if spawn reports ctl refused, check AllowStreamLocalForwarding in the host's sshd_config.\",\n )\n .option(\n \"--remote-sock <path>\",\n \"socket path on the remote host (default /tmp/mu-<uid>/<ws>/<name>.sock, uid = local uid)\",\n )\n .option(\"--shell\", \"print eval-able MU_SSH_ARGS=... and MU_REMOTE_ENV=... lines\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (name: string) {\n const opts = (this as Command).opts() as {\n workstream?: string;\n remoteSock?: string;\n shell?: boolean;\n json?: boolean;\n };\n return handle((db) => cmdRemoteEnv(db, name, opts), this as Command)();\n });\n}\n","// mu — `mu task` create/read/edit verbs (add / show / notes / note / update).\n//\n// add → addTask, with auto-id derivation when localId omitted.\n// show → row + edges + notes (+ lastClaimActor when owner=NULL).\n// notes / note → list + append on task_notes.\n// update → scalar edits (title/impact/effortDays).\n//\n// Plus the helpers:\n// unescapeNoteText — \\n / \\t / \\r / \\\\ inside a quoted string body\n// printNote — shared note formatter for show + notes\n//\n// `who claimed this task?` for the owner=NULL --self path comes from\n// the SDK's lastClaimActor (src/logs.ts) directly — the prior CLI-side\n// thin-wrapper was a vestigial re-export from the cluster split, gone\n// in schema_v5_cleanups.\n//\n// Extracted from src/cli/tasks.ts as part of the wire-out follow-up\n// to refactor_split_large_src_files.\n\nimport {\n assertTaskInWorkstream,\n colorPair,\n emitJson,\n emitJsonCollection,\n parseCsvFlag,\n resolveEntityRef,\n resolveWorkstream,\n UsageError,\n withRoiAll,\n} from \"../../cli.js\";\nimport type { Db } from \"../../db.js\";\nimport { lastClaimActor } from \"../../logs.js\";\nimport { type NextStep, pc, printNextSteps } from \"../../output.js\";\nimport {\n addNote,\n addTask,\n getTask,\n getTaskEdgesWithStatus,\n idFromTitleVerbose,\n listNotes,\n resolveActorIdentity,\n type TaskEdgeWithStatus,\n type TaskNoteRow,\n TaskNotFoundError,\n type UpdateTaskOptions,\n updateTask,\n} from \"../../tasks.js\";\nimport { readStdinText, STDIN_ARG } from \"../stdin.js\";\n\n/**\n * Translate the small set of shell-style escapes (\\n, \\t, \\r, \\\\)\n * inside a note body so a heredoc-free shell call can write a\n * multi-line note in one quoted string:\n *\n * mu task note auth \"FILES: a.rs:45\\nDECISION: chose JWT\"\n *\n * Backslashes are protected via a NUL placeholder so `\\\\n` stays as\n * a literal `\\n` in the output rather than being processed twice.\n */\nexport function unescapeNoteText(s: string): string {\n // Single-pass regex: match a backslash followed by one of the four\n // recognised escape characters and decide per-match what to emit.\n // This avoids the in-band-sentinel pattern (where a placeholder string\n // could in principle collide with legitimate note content) and means\n // `\\\\n` correctly yields a literal `\\n` rather than a newline, because\n // the leading `\\\\` consumes the backslash before `\\n` can match.\n return s.replace(/\\\\([\\\\ntr])/g, (_, ch: string) => {\n switch (ch) {\n case \"\\\\\":\n return \"\\\\\";\n case \"n\":\n return \"\\n\";\n case \"t\":\n return \"\\t\";\n case \"r\":\n return \"\\r\";\n default:\n return _;\n }\n });\n}\n\nexport function printNote(n: TaskNoteRow): void {\n const author = n.author ?? \"<orchestrator>\";\n console.log(` ${pc.dim(n.createdAt)} ${pc.bold(author)}`);\n for (const line of n.content.split(\"\\n\")) {\n console.log(` ${line}`);\n }\n}\n\n/** Split a list of edge neighbours into (still-gating, satisfied)\n * buckets. CLOSED is the only status that satisfies a `blocks` edge;\n * OPEN/IN_PROGRESS stay in the still-gating bucket.\n * (task_show_blocked_by_renders_closed.) */\nfunction partitionEdges(edges: readonly TaskEdgeWithStatus[]): {\n stillGating: TaskEdgeWithStatus[];\n satisfied: TaskEdgeWithStatus[];\n} {\n const stillGating: TaskEdgeWithStatus[] = [];\n const satisfied: TaskEdgeWithStatus[] = [];\n for (const e of edges) {\n if (e.status === \"CLOSED\") satisfied.push(e);\n else stillGating.push(e);\n }\n return { stillGating, satisfied };\n}\n\n/** Render one edge bucket as a comma-separated `<name> [<STATUS[/substate]>]`\n * list. The status is colour-coded the same way the task table\n * renders it (src/cli/format.ts colorPair); satisfied buckets are\n * additionally dimmed so they recede visually. An empty bucket\n * renders as an em-dash (—) to match the prior \"no edges\" rendering\n * for back-compat with operator-eyed scripts. */\nfunction formatEdgeList(edges: readonly TaskEdgeWithStatus[], dim: boolean): string {\n if (edges.length === 0) return pc.dim(\"—\");\n const parts = edges.map((e) => {\n const piece = `${e.name} [${colorPair(e)}]`;\n return dim ? pc.dim(piece) : piece;\n });\n return parts.join(\", \");\n}\n\n/** A note whose whole text is empty, whitespace or a bare `-` is almost\n * always a mistake (an older mu stored `-` literally when stdin was\n * meant; a typo or an empty variable gives \"\"). It is still stored,\n * but loudly: the warning goes to stderr and the --json `warnings`. */\nexport function suspiciousNoteWarnings(text: string): string[] {\n const t = text.trim();\n if (t === \"\") return [\"note text is empty or whitespace only; stored anyway\"];\n if (t === STDIN_ARG) {\n return [\n `note text is a bare \"-\"; stored anyway. To read stdin, pass - and pipe the text: <<'EOF' ... EOF`,\n ];\n }\n return [];\n}\n\nfunction emitWarnings(warnings: readonly string[]): void {\n for (const w of warnings) console.error(pc.yellow(`warning: ${w}`));\n}\n\nexport async function cmdTaskAdd(\n db: Db,\n localId: string | undefined,\n opts: {\n title: string;\n impact: number;\n effortDays: number;\n blockedBy?: string[];\n note?: string;\n noteAuthor?: string;\n triage?: boolean;\n workstream?: string;\n json?: boolean;\n },\n): Promise<void> {\n const workstream = await resolveWorkstream(opts.workstream);\n // Derive the id from the title if the user didn't provide one. The\n // CLI's `<id>` positional is now optional; idFromTitleVerbose handles\n // collisions with `_2`, `_3`, … suffixes AND surfaces a `truncated`\n // flag so we can warn the user when the SLUG_SOFT_CAP word-boundary\n // cut dropped clauses (slugifytitle_silently_drops_clauses).\n // `autoDerived` distinguishes the explicit-<id> branch from the\n // auto-derived branch so `--json` can selectively expose the\n // truncation telemetry only when it's meaningful\n // (task_add_slugify_silently_truncates_ids).\n const autoDerived = localId === undefined;\n let derivation: { id: string; truncated: boolean; originalSlug: string };\n if (localId !== undefined) {\n derivation = { id: localId, truncated: false, originalSlug: localId };\n } else {\n derivation = idFromTitleVerbose(db, workstream, opts.title);\n }\n const id = derivation.id;\n const blockedBy = parseCsvFlag(opts.blockedBy, \"-b/--blocked-by\");\n const hasBlockers = blockedBy.length > 0;\n // `--note -` reads stdin verbatim (no \\\\n unescaping: a heredoc has\n // real newlines). Read before the transaction; it is async.\n const noteText =\n opts.note === STDIN_ARG\n ? await readStdinText(\"--note\")\n : opts.note !== undefined\n ? unescapeNoteText(opts.note)\n : undefined;\n const warnings = noteText !== undefined ? suspiciousNoteWarnings(noteText) : [];\n emitWarnings(warnings);\n const initialNoteAuthor =\n noteText !== undefined ? (opts.noteAuthor ?? (await resolveActorIdentity())) : undefined;\n const { task, note } = db\n .transaction(() => {\n const createdTask = addTask(db, {\n localId: id,\n workstream,\n title: opts.title,\n impact: opts.impact,\n effortDays: opts.effortDays,\n ...(hasBlockers ? { blockedBy } : {}),\n ...(opts.triage === true ? { triage: true } : {}),\n });\n const createdNote =\n noteText !== undefined\n ? addNote(db, createdTask.name, noteText, {\n author: initialNoteAuthor,\n workstream,\n })\n : null;\n return { task: createdTask, note: createdNote };\n })\n .immediate();\n const nextSteps: NextStep[] = [\n { intent: \"Show this task\", command: `mu task show ${task.name} -w ${workstream}` },\n ...(note === null\n ? [\n {\n // Single-quoted example: shell metachars (`...`, $VAR, $(...))\n // inside a double-quoted string expand in YOUR shell before mu\n // sees the note (mufeedback note #257). Single quotes defer\n // expansion to the agent.\n intent: \"Add initial context (or use --note next time)\",\n command: `mu task note ${task.name} 'REPRO: ...\\\\nSCOPE: ...' -w ${workstream}`,\n },\n ]\n : [{ intent: \"Show notes\", command: `mu task notes ${task.name} -w ${workstream}` }]),\n {\n intent: \"Add a blocker\",\n command: `mu task block ${task.name} --by <other-id> -w ${workstream}`,\n },\n opts.triage === true\n ? { intent: \"Accept it as work\", command: `mu task accept ${task.name} -w ${workstream}` }\n : {\n intent: \"Claim and start\",\n command: `mu task claim ${task.name} -w ${workstream} --self (or --for <worker>)`,\n },\n ];\n if (opts.json) {\n // JSON callers are scripts: stay machine-readable. The human\n // stderr hint is suppressed under --json (matches every other\n // prose surface in the CLI). The truncation signal still has to\n // reach scripted callers, though — otherwise pipelines that\n // build follow-up commands from the JSON envelope can't tell the\n // id no longer carries the title's full meaning. Surface it as\n // top-level `truncated`/`originalSlug` siblings of `task` (NOT\n // inside `task`, which mirrors the persisted row).\n // Conventions, consistent with the audit_json_envelope_uniformity\n // singleton style: only emit when meaningful. Both fields are\n // omitted when the operator passed an explicit <id> (no\n // auto-derive) and when auto-derivation produced no truncation\n // (task_add_slugify_silently_truncates_ids).\n const truncationFields =\n autoDerived && derivation.truncated\n ? { truncated: true, originalSlug: derivation.originalSlug }\n : {};\n emitJson({\n task: withRoiAll([task])[0],\n blockers: blockedBy ?? [],\n ...(note !== null ? { note } : {}),\n nextSteps,\n ...truncationFields,\n ...(warnings.length > 0 ? { warnings } : {}),\n });\n return;\n }\n // Stderr hint when auto-id derivation truncated the slug. Stderr +\n // exit 0 so scripts that already pipe stdout aren't disturbed; the\n // operator sees the heads-up that the id no longer carries the full\n // title's meaning, with a one-paste fix (pass <id> positional).\n // Suppressed when the operator passed an explicit id (truncated is\n // false in that branch) since they already chose the id by hand.\n if (derivation.truncated) {\n process.stderr.write(\n `hint: id '${task.name}' truncated from a longer slug; pass <id> positional to override (mu task add <id> --title ... ).\\n`,\n );\n }\n const idHint = localId === undefined ? pc.dim(\" (id derived from title)\") : \"\";\n console.log(\n `Added task ${pc.bold(task.name)}${idHint} ${pc.dim(\n `(workstream=${workstream}, impact=${task.impact}, effort=${task.effortDays})`,\n )}`,\n );\n if (note !== null) {\n console.log(\n pc.dim(` initial note: ${note.content.length} chars by ${note.author ?? \"<orchestrator>\"}`),\n );\n }\n if (hasBlockers) console.log(pc.dim(` blocked by: ${blockedBy.join(\", \")}`));\n printNextSteps(nextSteps);\n}\n\n/** Reconcile `mu task note <id> [text]` positional text with the\n * `--text` flag alias.\n *\n * dogfood-note-arg-shape: `mu task add --note <text>` is a FLAG, so\n * one invocation later the flag form is what operators reach for on\n * `mu task note`, which only accepted a positional and dumped help.\n * `--text` is now an additive alias; the positional is unchanged.\n * Exactly one must be supplied. */\nexport function resolveNoteText(positional: string | undefined, flag: string | undefined): string {\n if (positional !== undefined && flag !== undefined) {\n throw new UsageError(\n 'note text given twice: pass it positionally (mu task note <id> \"...\") OR via --text, not both',\n );\n }\n const text = positional ?? flag;\n if (text === undefined) {\n throw new UsageError(\n 'note text required: mu task note <id> \"...\" (or the --text \"...\" flag alias)',\n );\n }\n return text;\n}\n\nexport async function cmdTaskNote(\n db: Db,\n rawId: string,\n content: string,\n opts: { workstream?: string; json?: boolean; author?: string } = {},\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n // Author resolution: explicit --author wins; otherwise consult\n // MU_AGENT_NAME (env var injected at spawn) > pane title > $USER >\n // 'orchestrator'. Surfaced from mufeedback note #176: notes from\n // spawned agents were appearing as <orchestrator> because the CLI\n // wasn't propagating identity. After this fix, mu-spawned workers'\n // notes are correctly attributed to the agent name.\n const author = opts.author ?? (await resolveActorIdentity());\n const text = content === STDIN_ARG ? await readStdinText(\"note text\") : unescapeNoteText(content);\n const warnings = suspiciousNoteWarnings(text);\n emitWarnings(warnings);\n const note = addNote(db, localId, text, { author, workstream: ws });\n const nextSteps: NextStep[] = [\n { intent: \"Show all notes on this task\", command: `mu task notes ${localId} -w ${ws}` },\n { intent: \"Show full task state\", command: `mu task show ${localId} -w ${ws}` },\n ];\n // A worker reads notes at dispatch, not while it runs: a note on its\n // IN_PROGRESS task reaches it only through a send.\n const task = getTask(db, localId, ws);\n const owner = task?.status === \"IN_PROGRESS\" ? task.ownerName : null;\n if (owner !== null && owner !== author) {\n nextSteps.unshift({\n intent: `${owner} will not see this note: send it (--steer, or --interrupt if the note makes the current work wasted)`,\n command: `mu agent send ${owner} -w ${ws} --steer \"...\"`,\n });\n }\n if (opts.json) {\n emitJson({\n taskName: localId,\n note,\n nextSteps,\n ...(warnings.length > 0 ? { warnings } : {}),\n });\n return;\n }\n console.log(pc.dim(`note appended to ${localId}`));\n printNextSteps(nextSteps);\n}\n\nexport async function cmdTaskShow(\n db: Db,\n rawId: string,\n opts: { json?: boolean; workstream?: string } = {},\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n // v5: tasks.local_id is per-workstream unique. Resolve the\n // operator's workstream up front so the lookup scopes correctly.\n const ws = await resolveWorkstream(opts.workstream);\n const task = getTask(db, localId, ws);\n if (!task) throw new TaskNotFoundError(localId);\n const edges = getTaskEdgesWithStatus(db, localId, task.workstreamName);\n const notes = listNotes(db, localId, task.workstreamName);\n\n // When owner IS NULL but the task is IN_PROGRESS (or recently was),\n // the actor is in agent_logs. Surface it so 'who's working on this'\n // is answerable from `mu task show` alone.\n const lastActor =\n task.ownerName === null && task.status !== \"OPEN\"\n ? lastClaimActor(db, task.workstreamName, task.name)\n : null;\n\n if (opts.json) {\n // JSON shape: blockers/dependents are arrays of {name, status}\n // objects so scripts can filter by status without a second query.\n // (task_show_blocked_by_renders_closed: prior shape was bare\n // string[], which discarded the gating-vs-satisfied distinction.)\n emitJson({\n task: withRoiAll([task])[0],\n blockers: edges.blockers,\n dependents: edges.dependents,\n notes,\n lastClaimActor: lastActor,\n });\n return;\n }\n\n const roi = task.effortDays > 0 ? (task.impact / task.effortDays).toFixed(1) : \"∞\";\n console.log(pc.bold(`${task.name} — ${task.title}`));\n console.log(` workstream : ${task.workstreamName}`);\n console.log(` status : ${colorPair(task)}`);\n // owner: registered worker name, or '(self: <actor>)' for an anonymous\n // claim, or '(unowned)' for OPEN tasks.\n const ownerLine =\n task.ownerName !== null\n ? task.ownerName\n : lastActor !== null\n ? pc.dim(`(self: ${lastActor})`)\n : pc.dim(\"(unowned)\");\n console.log(` owner : ${ownerLine}`);\n console.log(` impact : ${task.impact}`);\n console.log(` effort : ${task.effortDays} ${pc.dim(`(ROI ${roi})`)}`);\n console.log(` created : ${pc.dim(task.createdAt)}`);\n console.log(` updated : ${pc.dim(task.updatedAt)}`);\n\n console.log(\"\");\n console.log(pc.bold(\"Edges\"));\n // Group each side of the edge set by status so the operator can\n // tell at a glance which prerequisites still gate the task vs which\n // have already been satisfied. CLOSED is the only status that\n // satisfies a `blocks` edge; OPEN/IN_PROGRESS stay in the\n // still-gating bucket. (task_show_blocked_by_renders_closed.)\n const { stillGating: gatingBlockers, satisfied: satisfiedBlockers } = partitionEdges(\n edges.blockers,\n );\n const { stillGating: openDependents, satisfied: closedDependents } = partitionEdges(\n edges.dependents,\n );\n console.log(` blocked by : ${formatEdgeList(gatingBlockers, false)}`);\n if (satisfiedBlockers.length > 0) {\n console.log(` satisfied : ${formatEdgeList(satisfiedBlockers, true)}`);\n }\n console.log(` blocks : ${formatEdgeList(openDependents, false)}`);\n if (closedDependents.length > 0) {\n console.log(` no longer : ${formatEdgeList(closedDependents, true)}`);\n }\n\n console.log(\"\");\n console.log(pc.bold(`Notes (${notes.length})`));\n if (notes.length === 0) {\n console.log(pc.dim(\" (no notes)\"));\n } else {\n for (const n of notes) printNote(n);\n }\n // Only the non-default substates get a hint: they are the ones whose\n // way out is not obvious from the status alone.\n const ref = `${task.name} -w ${task.workstreamName}`;\n if (task.substate === \"parked\") {\n console.log(\"\");\n printNextSteps([{ intent: \"Return it to next\", command: `mu task unpark ${ref}` }]);\n } else if (task.substate === \"triage\") {\n console.log(\"\");\n printNextSteps([\n { intent: \"Accept it as work\", command: `mu task accept ${ref}` },\n { intent: \"Decline it\", command: `mu task close ${ref} --as rejected --why \"<reason>\"` },\n ]);\n } else if (task.status === \"CLOSED\" && task.substate !== \"done\") {\n console.log(\"\");\n printNextSteps([{ intent: \"Reopen it\", command: `mu task open ${ref}` }]);\n }\n}\n\nexport async function cmdTaskNotes(\n db: Db,\n rawId: string,\n opts: {\n json?: boolean;\n workstream?: string;\n tail?: number;\n since?: string;\n sinceClaim?: boolean;\n } = {},\n): Promise<void> {\n // Mutex: --since and --since-claim both define a cutoff; allowing\n // both would force one to silently win, which is a footgun. The SDK\n // documents \"since wins\" for safety, but the CLI is strict so the\n // user gets feedback at the surface they typed at. (Mirrors the\n // pattern in cmdTaskUpdate where conflicting fields error rather\n // than picking one.)\n if (opts.since !== undefined && opts.sinceClaim === true) {\n throw new UsageError(\n \"--since and --since-claim are mutually exclusive (both define a cutoff); pick one\",\n );\n }\n // --tail must be a positive integer. The commander parser\n // (parsePositiveNumber) already rejects 0 and negatives at the\n // parse layer, but defend here too in case a programmatic caller\n // pokes a bad value through (the SDK accepts >=0 by design).\n if (\n opts.tail !== undefined &&\n (!Number.isFinite(opts.tail) || opts.tail <= 0 || !Number.isInteger(opts.tail))\n ) {\n throw new UsageError(`--tail must be a positive integer (got ${JSON.stringify(opts.tail)})`);\n }\n // --since must parse as ISO 8601. We accept anything Date.parse\n // recognises (so '2025-01-01' and full RFC3339 both work) but\n // reject typos that produce NaN (e.g. 'yesterday', 'last week').\n if (opts.since !== undefined) {\n const parsed = Date.parse(opts.since);\n if (Number.isNaN(parsed)) {\n throw new UsageError(\n `--since must be an ISO 8601 timestamp (got ${JSON.stringify(opts.since)})`,\n );\n }\n }\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const task = getTask(db, localId, ws);\n if (!task) throw new TaskNotFoundError(localId);\n const filterOpts: {\n tail?: number;\n since?: string;\n sinceClaim?: boolean;\n } = {};\n if (opts.tail !== undefined) filterOpts.tail = opts.tail;\n if (opts.since !== undefined) filterOpts.since = opts.since;\n if (opts.sinceClaim === true) filterOpts.sinceClaim = true;\n const notes = listNotes(db, localId, task.workstreamName, filterOpts);\n if (opts.json) {\n emitJsonCollection(notes);\n return;\n }\n if (notes.length === 0) {\n console.log(pc.dim(`(no notes on ${localId})`));\n return;\n }\n for (const n of notes) printNote(n);\n}\n\nexport async function cmdTaskUpdate(\n db: Db,\n rawId: string,\n opts: {\n title?: string;\n impact?: number;\n effortDays?: number;\n workstream?: string;\n json?: boolean;\n },\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const updateOpts: UpdateTaskOptions = {};\n if (opts.title !== undefined) updateOpts.title = opts.title;\n if (opts.impact !== undefined) updateOpts.impact = opts.impact;\n if (opts.effortDays !== undefined) updateOpts.effortDays = opts.effortDays;\n if (Object.keys(updateOpts).length === 0) {\n throw new UsageError(\n \"nothing to update; pass at least one of --title, --impact, --effort-days\",\n );\n }\n const r = updateTask(db, localId, updateOpts, { workstream: ws });\n const nextSteps: NextStep[] = [\n { intent: \"Show updated task\", command: `mu task show ${localId} -w ${ws}` },\n ];\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps });\n return;\n }\n if (!r.updated) {\n console.log(pc.dim(`${localId}: no fields differ from current (no-op)`));\n return;\n }\n console.log(`Updated ${pc.bold(localId)} ${pc.dim(`(${r.changedFields.join(\", \")})`)}`);\n printNextSteps(nextSteps);\n}\n","// mu — `mu task` query verbs (read-only; no DB writes).\n//\n// list, next, owned-by.\n// Plus the `mu me tasks` / `mu me next` agent-self subcommands (also\n// read-only; they query against `resolveSelf(db)` instead of -w —\n// wired in src/cli/agents.ts via `wireSelfCommands`).\n//\n// Extracted from src/cli/tasks.ts as part of refactor_split_large_src_files.\n//\n// Removed in audit_cleanups_post_schema_v5_wave: `task blocked`,\n// `task goals`, `task search`, `task ready` (the latter merged into\n// `task next -n 0`, which now means \"all ready, unlimited\"). The\n// underlying SDK helpers `listBlocked` and `listGoals` survive —\n// `mu state` / `mu tracks` consume them. The audit's SQL recipes for\n// the removed verbs live in docs/guide/sql.md \"Run common queries\".\n\nimport {\n byRoiDesc,\n emitJsonCollection,\n formatTaskListTable,\n parseSortOption,\n parseStatusesOption,\n parseSubstatesOption,\n relTimeBasisForSort,\n resolveSelf,\n resolveWorkstream,\n sortTasks,\n type TaskSortKey,\n withRoiAll,\n} from \"../../cli.js\";\nimport type { Db } from \"../../db.js\";\nimport { pc, printNextSteps } from \"../../output.js\";\nimport {\n listReady,\n listTasks,\n listTasksByOwner,\n listTasksByOwnerCrossWorkstream,\n} from \"../../tasks.js\";\n\nexport async function cmdMyTasks(\n db: Db,\n opts: { json?: boolean; includeClosed?: boolean } = {},\n): Promise<void> {\n const self = resolveSelf(db);\n // Scope by self.workstream so a same-named worker in another\n // workstream can't pollute this list.\n const tasks = listTasksByOwner(db, self.workstreamName, self.name, {\n includeClosed: opts.includeClosed ?? false,\n });\n if (opts.json) {\n emitJsonCollection(withRoiAll(tasks));\n return;\n }\n if (tasks.length === 0) {\n console.log(pc.dim(`(${self.name} owns no tasks)`));\n return;\n }\n console.log(formatTaskListTable(tasks));\n}\n\nexport async function cmdMyNext(db: Db, opts: { lines?: number; json?: boolean }): Promise<void> {\n const self = resolveSelf(db);\n const k = opts.lines ?? 1;\n const sorted = listReady(db, self.workstreamName).sort(byRoiDesc);\n const tasks = k === 0 ? sorted : sorted.slice(0, k);\n if (opts.json) {\n emitJsonCollection(withRoiAll(tasks));\n return;\n }\n if (tasks.length === 0) {\n console.log(pc.dim(`(no ready tasks in ${self.workstreamName})`));\n return;\n }\n console.log(formatTaskListTable(tasks));\n}\n\nexport async function cmdTaskList(\n db: Db,\n opts: {\n workstream?: string;\n json?: boolean;\n status?: string[];\n substate?: string[];\n sort?: string;\n },\n): Promise<void> {\n const workstream = await resolveWorkstream(opts.workstream);\n const listOpts: Parameters<typeof listTasks>[2] = {};\n // --status accepts repeat OR comma-separate OR mix; parseStatusesOption\n // handles parseCsvFlag + per-element validate + dedup. Returns\n // undefined for no filter (matches today's no-flag shape).\n const statuses = parseStatusesOption(opts.status);\n if (statuses !== undefined) {\n listOpts.status = statuses;\n }\n const substates = parseSubstatesOption(opts.substate);\n if (substates !== undefined) listOpts.substate = substates;\n // Default sort for `mu task list` is `id` (preserves prior\n // behaviour: SQL ORDER BY local_id). The other read verbs default\n // to `roi` because their primary use is \"what should I do next\".\n const sortKey: TaskSortKey = opts.sort === undefined ? \"id\" : parseSortOption(opts.sort);\n const tasks = sortTasks(listTasks(db, workstream, listOpts), sortKey);\n if (opts.json) {\n emitJsonCollection(withRoiAll(tasks));\n return;\n }\n console.log(pc.bold(`mu-${workstream}`));\n const tableOpts: Parameters<typeof formatTaskListTable>[1] = {};\n const basis = relTimeBasisForSort(sortKey);\n if (basis !== null) tableOpts.relTimeBasis = basis;\n console.log(formatTaskListTable(tasks, tableOpts));\n // The triage inbox is a to-do list of decisions: say how to make them.\n const first = tasks.find((t) => t.status === \"OPEN\" && t.substate === \"triage\");\n if (first !== undefined) {\n printNextSteps([\n { intent: \"Accept as work\", command: `mu task accept ${first.name} -w ${workstream}` },\n {\n intent: \"Decline\",\n command: `mu task close ${first.name} --as rejected|duplicate --why \"<reason>\" -w ${workstream}`,\n },\n { intent: \"Read the evidence\", command: `mu task notes ${first.name} -w ${workstream}` },\n ]);\n }\n}\n\n// ROI = impact / effort_days. Higher first. Tasks with effortDays=0\n// (would divide by zero) sort to the top by treating their ROI as Infinity.\n//\n// `-n 0` means \"unlimited\" — the merged-in `task ready` semantics\n// from audit_merge_task_ready_into_next. Default K=1 keeps the\n// historical \"what should I do right now?\" shape.\nexport async function cmdTaskNext(\n db: Db,\n opts: {\n workstream?: string;\n lines?: number;\n json?: boolean;\n sort?: string;\n status?: string[];\n substate?: string[];\n },\n): Promise<void> {\n const workstream = await resolveWorkstream(opts.workstream);\n const k = opts.lines ?? 1;\n const sortKey: TaskSortKey = opts.sort === undefined ? \"roi\" : parseSortOption(opts.sort);\n const readyOpts: Parameters<typeof listReady>[2] = {};\n const statuses = parseStatusesOption(opts.status);\n if (statuses !== undefined) {\n readyOpts.status = statuses;\n }\n const substates = parseSubstatesOption(opts.substate);\n if (substates !== undefined) readyOpts.substate = substates;\n const sorted = sortTasks(listReady(db, workstream, readyOpts), sortKey);\n const tasks = k === 0 ? sorted : sorted.slice(0, k);\n if (opts.json) {\n emitJsonCollection(withRoiAll(tasks));\n return;\n }\n if (tasks.length === 0) {\n const parked = listTasks(db, workstream, { substate: \"parked\" }).length;\n const triage = listTasks(db, workstream, { substate: \"triage\" }).length;\n if (parked === 0 && triage === 0) {\n console.log(pc.dim(\"(no ready tasks)\"));\n return;\n }\n const held = [parked > 0 ? `${parked} parked` : \"\", triage > 0 ? `${triage} in triage` : \"\"]\n .filter(Boolean)\n .join(\", \");\n console.log(pc.dim(`(no ready tasks; ${held})`));\n printNextSteps([\n ...(triage > 0\n ? [\n {\n intent: \"Triage findings\",\n command: `mu task list --substate triage -w ${workstream}`,\n },\n ]\n : []),\n ...(parked > 0\n ? [\n {\n intent: \"List parked tasks\",\n command: `mu task list --substate parked -w ${workstream}`,\n },\n ]\n : []),\n ]);\n return;\n }\n const tableOpts: Parameters<typeof formatTaskListTable>[1] = {};\n const basis = relTimeBasisForSort(sortKey);\n if (basis !== null) tableOpts.relTimeBasis = basis;\n console.log(formatTaskListTable(tasks, tableOpts));\n}\n\nexport async function cmdTaskOwnedBy(\n db: Db,\n agent: string,\n opts: { json?: boolean; includeClosed?: boolean; workstream?: string; all?: boolean } = {},\n): Promise<void> {\n // Default behaviour: scope to the resolved workstream (so the common\n // case 'mu task owned-by worker-1' returns only this workstream's\n // worker-1, not every workstream's). --all explicitly opts into the\n // cross-workstream view via listTasksByOwnerCrossWorkstream.\n const includeClosed = opts.includeClosed ?? false;\n const tasks = opts.all\n ? listTasksByOwnerCrossWorkstream(db, agent, { includeClosed })\n : listTasksByOwner(db, await resolveWorkstream(opts.workstream), agent, { includeClosed });\n if (opts.json) {\n emitJsonCollection(withRoiAll(tasks));\n return;\n }\n if (tasks.length === 0) {\n console.log(pc.dim(`(no tasks owned by ${agent})`));\n return;\n }\n // Surface the workstream column when we're showing cross-workstream\n // results (--all); for the scoped (default) case the column would\n // be redundant.\n console.log(formatTaskListTable(tasks, { withWorkstream: opts.all === true }));\n}\n","// mu — `mu task` ownership + synchronisation verbs (claim / release / wait).\n//\n// claim → CAS-style ownership transfer; dispatch via --for or\n// anonymous --self (owner stays NULL, actor in agent_logs).\n// release → clears owner; auto-flips IN_PROGRESS → OPEN; --reopen\n// forces OPEN from CLOSED.\n// wait → polls until the listed tasks reach --status (default\n// CLOSED). Exit 0 = met; exit 5 = timeout.\n//\n// Extracted from src/cli/tasks.ts as part of the wire-out follow-up\n// to refactor_split_large_src_files.\n\nimport { dirname } from \"node:path\";\nimport { agentKey, readAgentStates, type StateReading } from \"../../agent-state.js\";\nimport { AgentNotFoundError } from \"../../agents/errors.js\";\nimport { type AgentRow, getAgent, refreshAgentTitle } from \"../../agents.js\";\nimport {\n assertTaskInWorkstream,\n CliExitError,\n emitJson,\n parseQualifiedRef,\n parseStatusOption,\n resolveEntityRef,\n resolveWorkstream,\n UsageError,\n} from \"../../cli.js\";\nimport { type Db, tryResolveWorkstreamId, WorkstreamNotFoundError } from \"../../db.js\";\nimport { GLYPH } from \"../../glyphs.js\";\nimport { type NextStep, pc, printNextSteps } from \"../../output.js\";\nimport { reconcile } from \"../../reconcile.js\";\nimport { shellQuote } from \"../../shell-quote.js\";\nimport { findRemoteDispatch } from \"../../state.js\";\nimport { stallWaitHint } from \"../../tasks/errors.js\";\nimport {\n claimTask,\n DEFAULT_STUCK_AFTER_MS,\n formatPair,\n getTask,\n getTaskOwner,\n ReaperDetectedDuringWaitError,\n releaseTask,\n resolveActorIdentity,\n TaskNotFoundError,\n type TaskWaitRef,\n type TaskWaitTaskState,\n waitForTasks,\n} from \"../../tasks.js\";\nimport { type CommitSummary, WorkspaceVcsRequiredError } from \"../../vcs.js\";\nimport { listCommitsForWorkspace, WorkspaceNotFoundError } from \"../../workspace.js\";\nimport { dispatchHint, nextDispatchHint } from \"../dispatch-hints.js\";\nimport { checkWorkspaceStalenessForDispatch } from \"../staleness.js\";\n\nexport async function cmdTaskRelease(\n db: Db,\n rawId: string,\n opts: { reopen?: boolean; evidence?: string; workstream?: string; json?: boolean },\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const sdkOpts: Parameters<typeof releaseTask>[2] = {\n reopen: opts.reopen ?? false,\n workstream: ws,\n };\n if (opts.evidence !== undefined) sdkOpts.evidence = opts.evidence;\n if (opts.evidence) sdkOpts.author = await resolveActorIdentity();\n const r = releaseTask(db, localId, sdkOpts);\n // Title push for the agent that just lost the task. Prev-owner could\n // be null (anonymous claim release — nothing to refresh).\n if (r.previousOwnerName) await refreshAgentTitle(db, r.previousOwnerName, ws);\n const nextSteps: NextStep[] = [\n {\n intent: \"Reclaim\",\n command: `mu task claim ${localId} -w ${ws} (--self / --for <worker>)`,\n },\n { intent: \"Show current state\", command: `mu task show ${localId} -w ${ws}` },\n ];\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps });\n return;\n }\n if (!r.changed) {\n console.log(pc.dim(`${localId} already unowned (no-op)`));\n printNextSteps(nextSteps);\n return;\n }\n const ownerBit = r.previousOwnerName ? `was ${pc.bold(r.previousOwnerName)}` : \"was unowned\";\n const statusBit = r.previousStatus !== r.status ? ` (${r.previousStatus} → ${r.status})` : \"\";\n console.log(`Released ${pc.bold(localId)} ${pc.dim(`(${ownerBit})${statusBit}`)}`);\n if (opts.evidence) console.log(pc.dim(` evidence: ${opts.evidence}`));\n printNextSteps(nextSteps);\n}\n\nexport async function cmdClaim(\n db: Db,\n rawId: string,\n opts: {\n for?: string;\n self?: boolean;\n actor?: string;\n evidence?: string;\n workstream?: string;\n json?: boolean;\n strictStaleness?: boolean;\n force?: boolean;\n },\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n if (opts.self === true && opts.for !== undefined) {\n throw new UsageError(\"--self and --for are mutually exclusive\");\n }\n if (opts.actor !== undefined && opts.self !== true) {\n throw new UsageError(\"--actor only meaningful with --self (it overrides the actor name)\");\n }\n // Parse `--for` for an optional qualified ref: bare `<name>`\n // resolves the agent in the task's workstream (today); qualified\n // `<workstream>/<name>` resolves the agent in its own workstream\n // and dispatches across the workstream boundary\n // (task_claim_for_cross_workstream).\n let forName: string | undefined;\n let forWorkstream: string | undefined;\n if (opts.for !== undefined) {\n const parsed = parseQualifiedRef(opts.for);\n forName = parsed.name;\n if (parsed.workstream !== undefined) {\n forWorkstream = parsed.workstream;\n // Pre-flight: workstream must exist (typed error so the operator\n // sees the canonical exit-3 mapping instead of a bare\n // ClaimerNotRegisteredError pointing at the wrong cause).\n if (tryResolveWorkstreamId(db, forWorkstream) === null) {\n throw new WorkstreamNotFoundError(forWorkstream);\n }\n // Pre-flight: agent must exist in that workstream. Without this\n // the SDK surfaces ClaimerNotRegisteredError (the bare-name\n // shape) which doesn't carry the qualifying workstream context\n // — AgentNotFoundError(name, workstream) is the right shape for\n // the cross-ws path.\n const wsId = tryResolveWorkstreamId(db, forWorkstream);\n if (wsId !== null) {\n const row = db\n .prepare(\"SELECT 1 FROM agents WHERE name = ? AND workstream_id = ?\")\n .get(forName, wsId);\n if (!row) throw new AgentNotFoundError(forName, forWorkstream);\n }\n }\n }\n const sdkOpts: Parameters<typeof claimTask>[2] = { workstream: ws };\n if (forName !== undefined) sdkOpts.agentName = forName;\n if (opts.force) sdkOpts.force = true;\n if (forWorkstream !== undefined) sdkOpts.agentWorkstream = forWorkstream;\n if (opts.self) sdkOpts.self = true;\n if (opts.actor !== undefined) sdkOpts.actor = opts.actor;\n if (opts.evidence !== undefined) sdkOpts.evidence = opts.evidence;\n // `--for` dispatch: the CLAIM note is the dispatcher's, not the\n // worker's (the SDK defaults it to the claimer).\n if (opts.evidence && forName !== undefined) sdkOpts.author = await resolveActorIdentity();\n const stalenessCheck =\n forName !== undefined\n ? await checkWorkspaceStalenessForDispatch(db, forName, forWorkstream ?? ws, {\n strict: opts.strictStaleness === true,\n })\n : { staleness: null, warned: false, nextStep: null };\n const result = await claimTask(db, localId, sdkOpts);\n // Title push for the new owner. Anonymous claims (--self) leave\n // owner=null — nothing to refresh. Refresh in the agent's OWN\n // workstream (forWorkstream when the dispatch was cross-ws), not\n // the task's — the agent row only exists in its own workstream.\n if (result.ownerName) {\n await refreshAgentTitle(db, result.ownerName, forWorkstream ?? ws);\n }\n const nextSteps: NextStep[] = [];\n // claim-before-send: a --for claim is the moment of dispatch, so the\n // first hint is the send that hands the task over.\n const owner =\n result.ownerName === null ? undefined : getAgent(db, result.ownerName, forWorkstream ?? ws);\n if (owner !== undefined)\n nextSteps.push(dispatchHint(owner, { task: { id: localId, workstream: ws } }));\n if (result.ownerName !== null) {\n const remote = findRemoteDispatch(db, ws, localId, result.ownerName);\n if (remote !== undefined) {\n const host = shellQuote(remote.host);\n const remoteCommand = shellQuote(\n `cd ${remote.path} && git rev-parse HEAD 2>/dev/null || echo unreadable`,\n );\n const base = shellQuote(remote.baseSha);\n const task = shellQuote(localId);\n const workstream = shellQuote(ws);\n nextSteps.push({\n intent: `Poll ${result.ownerName}'s remote commit once this turn`,\n command: `job=$(mule run --host ${host} --max-secs 30 ${remoteCommand}) && mule wait \"$job\" >/dev/null && sha=$(mule tail \"$job\") && { case \"$sha\" in (*[!0-9a-fA-F]*|'') :;; (*) [ \"$(printf %s \"$sha\" | wc -c)\" -eq 40 ] && { [ \"$sha\" = ${base} ] || mu task close ${task} --evidence \"${result.ownerName} committed $sha\" -w ${workstream}; };; esac; }`,\n });\n }\n }\n nextSteps.push(\n {\n // Single-quoted example: shell metachars (`...`, $VAR, $(...))\n // inside a double-quoted string expand in YOUR shell before mu\n // sees the note (mufeedback note #257). Single quotes defer\n // expansion to the agent.\n intent: \"Drop a note (single-quote to defer shell expansion)\",\n command: `mu task note ${localId} 'FILES: ...\\\\nDECISION: ...' -w ${ws}`,\n },\n {\n intent: \"Close with grounding\",\n command: `mu task close ${localId} --evidence \"...\" -w ${ws}`,\n },\n { intent: \"Release if blocked\", command: `mu task release ${localId} -w ${ws}` },\n );\n if (stalenessCheck.warned && stalenessCheck.nextStep !== null) {\n nextSteps.push(stalenessCheck.nextStep);\n }\n if (opts.json) {\n emitJson({ ...result, staleness: stalenessCheck.staleness, nextSteps });\n return;\n }\n if (result.ownerName === null) {\n console.log(\n `Claimed ${pc.bold(localId)} ${pc.dim(`(--self by ${result.actorName}; ${result.previousStatus} → ${result.status}; owner=NULL)`)}`,\n );\n } else {\n console.log(\n `Claimed ${pc.bold(localId)} for ${pc.bold(result.ownerName)} ${pc.dim(`(${result.previousStatus} → ${result.status})`)}`,\n );\n }\n if (opts.evidence) console.log(pc.dim(` evidence: ${opts.evidence}`));\n printNextSteps(nextSteps);\n}\n\n/** Qualified id `<ws>/<name>` for a watched ref — used in messages,\n * --json output, and stuck-task hints. */\nfunction qualifiedId(ref: { workstreamName: string; name: string }): string {\n return `${ref.workstreamName}/${ref.name}`;\n}\n\n/** A CLOSED ref whose substate says the work was not done. */\nfunction isUndelivered(ref: TaskWaitTaskState): boolean {\n return ref.status === \"CLOSED\" && ref.substate !== \"done\";\n}\n\nfunction cherryPickCommandForCommits(commits: readonly CommitSummary[]): string | null {\n const first = commits[0];\n if (first === undefined) return null;\n const last = commits[commits.length - 1];\n if (last === undefined) return null;\n if (commits.length === 1) return `git cherry-pick ${first.sha}`;\n return `git cherry-pick ${first.sha}^..${last.sha}`;\n}\n\nfunction noCommitsRescueStep(owner: string, workstream: string): NextStep {\n return {\n intent: `Worker ${owner} closed without committing — apply by hand`,\n command: `cd $(mu workspace path ${owner} -w ${workstream}) && git status # rescue diff with git diff / git apply`,\n };\n}\n\nasync function nextStepForFiringOwner(\n db: Db,\n owner: string,\n workstream: string,\n): Promise<NextStep> {\n try {\n const r = await listCommitsForWorkspace(db, owner, { workstream });\n const command = cherryPickCommandForCommits(r.commits);\n if (command === null) return noCommitsRescueStep(owner, workstream);\n return {\n intent:\n r.commits.length === 1\n ? `Cherry-pick ${owner}'s commit onto your branch`\n : `Cherry-pick ${owner}'s ${r.commits.length} commits onto your branch`,\n command,\n };\n } catch (err) {\n if (err instanceof WorkspaceNotFoundError) {\n return noCommitsRescueStep(owner, workstream);\n }\n if (err instanceof WorkspaceVcsRequiredError) {\n return {\n intent: `Worker ${owner} closed in a non-VCS workspace — inspect files by hand`,\n command: `cd $(mu workspace path ${owner} -w ${workstream}) && ls -la # cp -a snapshot; inspect files manually`,\n };\n }\n return {\n intent: `Unable to determine ${owner}'s workspace commits — inspect workspace manually`,\n command: `mu workspace commits ${owner} -w ${workstream} --json # if this fails, inspect $(mu workspace path ${owner} -w ${workstream})`,\n };\n }\n}\n\n/** Resolve a single `<ws>/<name>` or bare id into a TaskWaitRef.\n * - Qualified refs use their prefix; -w is NOT consulted (so a\n * cross-workstream wait can name two different workstreams).\n * - Bare refs fall back to the standard chain via resolveWorkstream.\n * - When neither qualifier nor -w/MU_SESSION/tmux session resolves a\n * workstream for a bare ref, surface the canonical UsageError from\n * resolveWorkstream so the operator gets the same diagnostic as\n * every other task verb.\n * - Existence is asserted up-front: a typo in either half throws\n * TaskNotFoundError listing the qualified form. (waitForTasks\n * repeats this check; we duplicate here so the error names the\n * raw arg the operator typed, not the normalised internal form.)\n */\nasync function resolveWaitRef(\n db: Db,\n raw: string,\n fallbackWs: string | undefined,\n): Promise<TaskWaitRef> {\n const parsed = parseQualifiedRef(raw);\n let workstreamName: string;\n if (parsed.workstream !== undefined) {\n workstreamName = parsed.workstream;\n } else {\n // Bare ref — use the standard chain (--workstream / $MU_SESSION /\n // tmux session). resolveWorkstream throws UsageError if none of\n // those resolve, which is the same error operators see today on\n // every other task verb.\n workstreamName = await resolveWorkstream(fallbackWs);\n }\n if (getTask(db, parsed.name, workstreamName) === undefined) {\n // Use the raw form (qualified or bare) so the error message\n // matches what the operator typed.\n throw new TaskNotFoundError(parsed.workstream !== undefined ? raw : parsed.name);\n }\n return { workstreamName, name: parsed.name };\n}\n\nexport async function cmdTaskWait(\n db: Db,\n ids: readonly string[],\n opts: {\n status?: string;\n any?: boolean;\n /** --first is a CLI alias for --any with a richer return shape\n * (prints the firing ref's qualified id; --json gains a\n * `firing` field). task_wait_cross_workstream. */\n first?: boolean;\n timeout?: number;\n stuckAfter?: number;\n onStall?: \"warn\" | \"exit\";\n workstream?: string;\n json?: boolean;\n },\n): Promise<void> {\n if (ids.length === 0) {\n throw new UsageError(\"mu task wait: at least one task id is required\");\n }\n // task_wait_stall_action_flag: validate --on-stall up-front so a\n // typo errors loud at the verb boundary instead of being silently\n // ignored by the SDK. Default 'exit': an orchestrator that forgets the\n // flag would otherwise poll past a worker that needs it until --timeout.\n const onStallRaw = opts.onStall ?? \"exit\";\n if (onStallRaw !== \"warn\" && onStallRaw !== \"exit\") {\n throw new UsageError(`--on-stall: expected 'warn' or 'exit', got '${onStallRaw}'`);\n }\n // Validate status (default CLOSED). Same parser as mu task list --status.\n const statusOpt = opts.status !== undefined ? parseStatusOption(opts.status) : undefined;\n\n // --first is a CLI alias for --any (same exit-condition; differs\n // only in output shape: --first emphasises WHICH ref fired so the\n // operator can pipe the qualified id into the next step).\n const wantAny = opts.any === true || opts.first === true;\n // emphasise WHICH ref fired in stdout / --json. ONLY --first opts\n // into this richer shape; --any keeps the per-task summary as-is\n // (matches the help text + the --first inline contract). Promoting\n // --any to the --first shape would surprise scripts that pass --any\n // and parse the ordinary summary.\n const wantFirstShape = opts.first === true;\n\n // Resolve every ref — cross-workstream-aware. Each ref carries its\n // own workstream so the wait set can span multiple workstreams.\n // Pre-flight existence check is inside resolveWaitRef; failures\n // throw before any waiting begins.\n const refs: TaskWaitRef[] = [];\n for (const id of ids) {\n refs.push(await resolveWaitRef(db, id, opts.workstream));\n }\n // Workstream set: every workstream we'll reconcile per poll. May be\n // 1 (legacy single-ws wait) or N (cross-ws). Used both for the\n // reconcile-each-poll path and for the human output below.\n const workstreamSet = new Set(refs.map((r) => r.workstreamName));\n\n // --timeout in seconds for shell ergonomics; SDK takes ms.\n // 0 in the SDK = wait forever; same convention here.\n const timeoutMs = opts.timeout !== undefined ? opts.timeout * 1000 : 600_000;\n // --stuck-after also in seconds; 0 disables. Default mirrors the SDK.\n const stuckAfterMs =\n opts.stuckAfter !== undefined ? opts.stuckAfter * 1000 : DEFAULT_STUCK_AFTER_MS;\n\n const sdkOpts: {\n status?: TaskWaitTaskState[\"status\"];\n any?: boolean;\n timeoutMs: number;\n stuckAfterMs: number;\n onStall?: \"warn\" | \"exit\";\n readOwnerState?: (owner: {\n name: string;\n workstreamName: string;\n }) => Promise<StateReading | null>;\n beforePoll?: () => Promise<void>;\n ctlStuckAfterMs?: number;\n } = { timeoutMs, stuckAfterMs };\n // An explicit --stuck-after applies to every owner, ctl ones included.\n if (opts.stuckAfter !== undefined) sdkOpts.ctlStuckAfterMs = stuckAfterMs;\n if (statusOpt !== undefined) sdkOpts.status = statusOpt;\n if (wantAny) sdkOpts.any = true;\n let ownerReadings = new Map<string, StateReading>();\n sdkOpts.readOwnerState = async (owner) => ownerReadings.get(agentKey(owner)) ?? null;\n\n // task_wait_reconcile_dead_panes (extended for cross-workstream by\n // task_wait_cross_workstream): per-poll reconcile + reaper-flip\n // detection. We keep a snapshot of each watched task's prior\n // (status, owner) so that AFTER reconcile (which may have flipped\n // IN_PROGRESS → OPEN for a dead-pane worker) we can spot the\n // transition and abort with exit 6 instead of running out the\n // operator's --timeout.\n //\n // - Reconcile runs on EVERY poll regardless of target, and once\n // per workstream in the wait set (NOT just the resolved -w —\n // cross-ws waits span multiple workstreams). The reaper is\n // exactly what we want to fire, and it only does so during a\n // `\"full\"` reconcile (the prune deletes the agent row which\n // triggers the IN_PROGRESS → OPEN flip).\n // - Exit-6 suppression: only when the wait target is CLOSED.\n // Other targets treat reaper-flip as a legitimate state change\n // (target=OPEN: it's the success; target=IN_PROGRESS: an\n // operator polling for the next worker to claim doesn't want\n // a dead predecessor to abort their wait).\n // - Cross-ws scoping: a reaper-flip in workstream B while we're\n // waiting on A's task does NOT trigger exit 6 — the\n // priorState/check loop runs ONLY over the watched refs. A\n // reconcile of B is harmless to A's wait.\n // - First-iteration coverage: beforePoll runs BEFORE the initial\n // snapshot too (waitForTasks contract), so a worker that died\n // BEFORE the operator typed `mu task wait` still triggers exit\n // 6 on the first tick.\n const target = statusOpt ?? \"CLOSED\";\n const reaperExitEnabled = target === \"CLOSED\";\n // task_wait_stall_action_flag: same target=CLOSED carve-out as\n // exit-6's reaper-flip suppression. With --status OPEN/IN_PROGRESS\n // the worker reaching needs_input might BE the success path —\n // exiting on stall would race the wait-condition check. Operators\n // who pass --on-stall exit + --status OPEN get warn-only behaviour\n // (the SDK still emits the stderr warning + agent_logs event).\n if (onStallRaw === \"exit\" && target === \"CLOSED\") sdkOpts.onStall = \"exit\";\n // The owner is read by owner_id, not by name in the task's\n // workstream: `task claim --for <ws>/<agent>` assigns an owner from\n // another workstream.\n const ownerOf = (ref: TaskWaitRef): AgentRow | undefined => {\n const owner = getTaskOwner(db, ref.name, ref.workstreamName);\n return owner === undefined ? undefined : getAgent(db, owner.name, owner.workstreamName);\n };\n const priorState = new Map<\n string,\n { status: string; owner: { name: string; workstream: string } | null }\n >();\n sdkOpts.beforePoll = async () => {\n // Reconcile each unique workstream in the wait set, plus the\n // workstream of each watched task's current owner: a\n // cross-workstream owner's dead pane is pruned (and its task\n // reaped) only by a reconcile of the owner's own workstream.\n // Each call is a cheap (~few ms) mux pane listing; it captures no\n // pane text. Full mode prunes dead panes, which fires the reaper\n // that flips tasks back to OPEN.\n const reconcileSet = new Set(workstreamSet);\n for (const ref of refs) {\n const owner = getTaskOwner(db, ref.name, ref.workstreamName);\n if (owner !== undefined) reconcileSet.add(owner.workstreamName);\n }\n for (const wsName of reconcileSet) {\n try {\n await reconcile(db, { workstream: wsName, mode: \"full\" });\n } catch {\n // Tmux substrate hiccup mid-wait: don't crash the wait. The\n // next iteration retries; the exit-6 path stays correct\n // because the prior-state map only fires on a real flip we\n // observed.\n }\n }\n const owners = refs.flatMap((ref) => {\n const agent = ownerOf(ref);\n return agent === undefined ? [] : [agent];\n });\n ownerReadings = await readAgentStates(owners, { stateDir: dirname(db.name) });\n if (!reaperExitEnabled) return;\n for (const ref of refs) {\n const key = qualifiedId(ref);\n const row = getTask(db, ref.name, ref.workstreamName);\n const status = row?.status ?? \"OPEN\";\n const ownerRow = ownerOf(ref);\n const owner =\n ownerRow === undefined\n ? null\n : { name: ownerRow.name, workstream: ownerRow.workstreamName };\n const prior = priorState.get(key);\n // Reaper-flip detected on a watched task: IN_PROGRESS → OPEN AND\n // the prior owner's agent row is gone. The reaper is the agent\n // row's delete, so a vanished owner is what tells it apart from\n // a `mu task release` (owner still registered), a `--self` claim\n // (no owner to reap) or a deleted task (no row): those are\n // ordinary state changes, not a dead pane. The FK\n // CASCADE-SET-NULL has already cleared the current row's owner,\n // so the owner comes from the previous tick's snapshot.\n if (\n row !== undefined &&\n prior !== undefined &&\n prior.status === \"IN_PROGRESS\" &&\n status === \"OPEN\" &&\n prior.owner !== null &&\n getAgent(db, prior.owner.name, prior.owner.workstream) === undefined\n ) {\n throw new ReaperDetectedDuringWaitError(ref.name, prior.owner.name, ref.workstreamName);\n }\n priorState.set(key, { status, owner });\n }\n };\n\n const startedAt = Date.now();\n const result = await waitForTasks(db, refs, sdkOpts);\n const elapsedMs = Date.now() - startedAt;\n\n // ─── WHICH-result shaping ────────────────────────────────────────\n // \"firing\" = the first ref that reached the target on the closing\n // snapshot. Set ONLY for --first. NULL for --any (which reports that\n // one ref fired, not which), for --all (every ref reached; no \"first\"\n // to single out), and on timeout (nothing reached).\n //\n // The --any case is the one that reads like a bug and is not: it\n // exits 0 with firing:null, so a consumer doing `.firing.name` after\n // --any crashes on a SUCCESSFUL wait. It was documented as \"--first /\n // --any\" for a while, which is what made that look supported. Use\n // --first when you need to know which.\n //\n // The `?? null` is unreachable, not defensive-for-a-real-case: both\n // of waitForTasks' non-timeout returns are guarded by isDone(), and\n // --first implies any:true, so isDone means at least one ref has\n // reachedTarget and find() cannot miss. Kept because the types\n // cannot express that, and null is the honest fallback if the\n // invariant ever breaks.\n const firingRef: TaskWaitTaskState | null =\n wantFirstShape && !result.timedOut ? (result.refs.find((t) => t.reachedTarget) ?? null) : null;\n const reachedRefs = result.refs.filter((t) => t.reachedTarget);\n const unmetRefs = result.refs.filter((t) => !t.reachedTarget);\n\n // Build nextSteps. The structure differs by exit shape:\n // - --first / --any success: name the firing ref, suggest\n // cherry-pick + verify + refresh (the dispatch-pipeline\n // recipe). The cherry-pick command uses the firing ref's owner\n // as the worker name when known.\n // - --all success: list closed refs, suggest verify.\n // - timeout / partial: list unmet refs, suggest mu task show.\n const nextSteps: NextStep[] = [];\n if (!result.timedOut && firingRef !== null && isUndelivered(firingRef)) {\n // wontfix / duplicate / superseded: nothing to cherry-pick. The\n // reason note says what happened instead.\n nextSteps.push({\n intent: `Read why ${firingRef.name} closed ${formatPair(firingRef)} (no deliverable)`,\n command: `mu task notes ${firingRef.name} -w ${firingRef.workstreamName}`,\n });\n } else if (!result.timedOut && firingRef !== null) {\n const owner = firingRef.owner;\n if (owner !== null) {\n // Best-effort workspace lookup: prefer an inspectable,\n // sha-pinned cherry-pick range over the old deferred\n // `git log -1` shell substitution. If the worker closed without\n // commits (or the workspace can't answer commits-since-fork),\n // surface a manual-rescue hint instead of a silently-empty pick.\n nextSteps.push(await nextStepForFiringOwner(db, owner, firingRef.workstreamName));\n }\n nextSteps.push({\n intent: \"Verify the cherry-pick\",\n command: \"<your project verify command — e.g. npm run test, cargo test, uv run pytest>\",\n });\n if (owner !== null) {\n nextSteps.push({\n intent: `Refresh ${owner}'s workspace onto current main for the next dispatch`,\n command: `mu workspace refresh ${owner} -w ${firingRef.workstreamName}`,\n });\n const ownerRow = getAgent(db, owner, firingRef.workstreamName);\n const dispatch =\n ownerRow === undefined ? null : nextDispatchHint(ownerRow, firingRef.workstreamName);\n if (dispatch !== null) nextSteps.push(dispatch);\n }\n } else if (!result.timedOut && wantFirstShape === false) {\n // --all success path — every ref reached. No single \"firing\"\n // worker to cherry-pick; the operator presumably already\n // picked along the way (or runs a single verify here).\n nextSteps.push({\n intent: \"Verify the merged work\",\n command: \"<your project verify command — e.g. npm run test, cargo test, uv run pytest>\",\n });\n }\n for (const t of unmetRefs) {\n // A task whose owner needs attention (`stuck`) is the one case\n // where `mu task show` is the wrong first step: the task row looks\n // healthy and IN_PROGRESS, while the reason it is not progressing\n // — a question, a prompt, or a finished-but-unclosed worker — is\n // only visible in the pane. Point at the pane instead.\n if (t.stuck && t.owner !== null) {\n // The owner's own workstream: a `--for <ws>/<agent>` owner lives\n // outside the task's workstream.\n const ownerWs =\n getTaskOwner(db, t.name, t.workstreamName)?.workstreamName ?? t.workstreamName;\n const runs = ownerReadings.get(agentKey({ name: t.owner, workstreamName: ownerWs }))?.runs;\n nextSteps.push(...stallWaitHint(t.owner, ownerWs, runs));\n nextSteps.push({\n intent: `Read ${t.owner}'s pane — ${qualifiedId(t)} is IN_PROGRESS but its owner needs attention`,\n command: `mu agent read ${t.owner} -w ${ownerWs} --lines 60`,\n });\n continue;\n }\n nextSteps.push({\n intent: `Investigate ${qualifiedId(t)} (status=${t.status})`,\n command: `mu task show ${t.name} -w ${t.workstreamName}`,\n });\n }\n if (!result.timedOut) {\n // Surface the next-ready hint for each workstream we waited on —\n // a cross-ws operator wants both `mu task next` candidates.\n for (const wsName of workstreamSet) {\n nextSteps.push({\n intent: `Pick the next ready task in ${wsName}`,\n command: `mu task next -w ${wsName}`,\n });\n }\n }\n\n if (opts.json) {\n // JSON envelope (task_wait_cross_workstream). Built explicitly\n // (no spread of the SDK return) so the operator-facing contract\n // stays narrow:\n // firing — the firing ref on --first/--any success, else null\n // all — refs that REACHED target (every ref on --all\n // success; just the firing ref for --first/--any;\n // the partial set on timeout)\n // timedOut — refs that did NOT reach target. ALWAYS [] on a\n // clean exit; populated on actual timeout. Callers\n // branch on `firing === null && timedOut.length > 0`\n // for the partial-progress case.\n // nextSteps— the same hint list printed to stdout.\n const firingJson =\n firingRef === null\n ? null\n : {\n workstreamName: firingRef.workstreamName,\n name: firingRef.name,\n qualifiedId: qualifiedId(firingRef),\n status: firingRef.status,\n substate: firingRef.substate,\n owner: firingRef.owner,\n };\n const timedOutArray = result.timedOut\n ? unmetRefs.map((t) => ({ ...t, qualifiedId: qualifiedId(t) }))\n : [];\n emitJson({\n firing: firingJson,\n all: reachedRefs.map((t) => ({\n ...t,\n qualifiedId: qualifiedId(t),\n })),\n timedOut: timedOutArray,\n nextSteps,\n });\n if (result.timedOut) throw new CliExitError(5);\n return;\n }\n\n // Human output:\n // --first / --any success: print qualified id of firing ref on\n // stdout (so `... | head -1` and `read REF < <(mu task wait\n // ...)` both work), then a dim summary + per-task lines.\n // --all success / timeout: today's summary line + per-task list.\n const targetStatus = statusOpt ?? \"CLOSED\";\n if (firingRef !== null) {\n console.log(qualifiedId(firingRef));\n }\n const summary = result.timedOut\n ? pc.yellow(`Timed out after ${elapsedMs}ms`)\n : pc.green(\n `${wantAny ? \"any-of\" : \"all-of\"} ${refs.length} reached ${targetStatus} in ${elapsedMs}ms`,\n );\n console.log(summary);\n for (const t of result.refs) {\n const marker = t.reachedTarget ? pc.green(GLYPH.ok) : pc.dim(\"•\");\n // Cross-ws: show the qualified id so a mixed list is unambiguous.\n // Single-ws (workstreamSet.size === 1) keeps today's bare-name\n // output to avoid noise.\n const label = workstreamSet.size > 1 ? qualifiedId(t) : t.name;\n console.log(` ${marker} ${pc.bold(label)} ${pc.dim(`(${formatPair(t)})`)}`);\n }\n printNextSteps(nextSteps);\n if (result.timedOut) throw new CliExitError(5);\n}\n","// mu — `mu task` graph-edge verbs (block / unblock / reparent / delete).\n//\n// All four mutate task_edges (block/unblock/reparent) or cascade through\n// it via FK (delete). Each is idempotent and emits typed errors that\n// `handle()` in src/cli.ts maps to exit codes.\n//\n// Extracted from src/cli/tasks.ts as part of the wire-out follow-up\n// to refactor_split_large_src_files.\n\nimport {\n assertTaskInWorkstream,\n emitJson,\n parseCsvFlag,\n resolveEntityRef,\n resolveWorkstream,\n UsageError,\n} from \"../../cli.js\";\nimport type { Db } from \"../../db.js\";\nimport { type NextStep, pc, printNextSteps } from \"../../output.js\";\nimport { addBlockEdge, deleteTask, removeBlockEdge, reparentTask } from \"../../tasks.js\";\n\n/** Canonicalise the `-b/--by` value into a non-empty blocker list.\n *\n * dogfood-block-multi: `--by` used to be single-valued while\n * `mu task add --blocked-by` was variadic + comma-aware, so the\n * natural `mu task block X --by a,b,c` failed with\n * \"no such task: a,b,c\". Both flags now funnel through the SAME\n * canonical helper (parseCsvFlag), so repeat / comma / mixed forms\n * all work and the two verbs can no longer drift apart.\n *\n * Commander hands us `string` for the legacy `<blocker>` shape and\n * `string[]` for the variadic one; accept both so a programmatic\n * caller passing the old single-string shape keeps working. */\nexport function parseByFlag(by: string | readonly string[]): string[] {\n const blockers = parseCsvFlag(typeof by === \"string\" ? [by] : by, \"-b/--by\");\n if (blockers.length === 0) {\n throw new UsageError(\"-b/--by requires at least one blocker task id\");\n }\n // De-dupe so `--by a,a` is a single edge attempt rather than an\n // added-then-no-op pair that would read as a confusing partial.\n return [...new Set(blockers)];\n}\n\nexport async function cmdTaskBlock(\n db: Db,\n rawBlocked: string,\n opts: { by: string | readonly string[]; workstream?: string; json?: boolean },\n): Promise<void> {\n const { name: blocked } = await resolveEntityRef(db, rawBlocked, opts, \"task\");\n assertTaskInWorkstream(db, blocked, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const blockers = parseByFlag(opts.by);\n const byList = blockers.join(\",\");\n // Sequential, fail-fast: the first bad blocker throws its typed\n // error (not-found / cycle / cross-workstream) and earlier edges\n // stay added. Same semantics as running the single-blocker form N\n // times, which is what this replaces.\n const results = blockers.map((blocker) => ({\n blockerName: blocker,\n ...addBlockEdge(db, ws, blocked, blocker),\n }));\n const added = results.filter((r) => r.added).length;\n const nextSteps: NextStep[] = [\n { intent: \"Show the dependency tree\", command: `mu task tree ${blocked} -w ${ws}` },\n { intent: \"Remove these edges\", command: `mu task unblock ${blocked} --by ${byList} -w ${ws}` },\n ];\n if (opts.json) {\n const first = results[0];\n emitJson({\n blockedName: blocked,\n // Single-blocker callers keep the pre-existing scalar shape.\n blockerName: first !== undefined && results.length === 1 ? first.blockerName : undefined,\n blockerNames: blockers,\n results,\n added: added > 0,\n addedEdges: added,\n nextSteps,\n });\n return;\n }\n for (const r of results) {\n if (!r.added) {\n console.log(pc.dim(`${r.blockerName} → ${blocked}: edge already exists (no-op)`));\n continue;\n }\n console.log(`Added edge ${pc.bold(r.blockerName)} → ${pc.bold(blocked)}`);\n }\n printNextSteps(nextSteps);\n}\n\nexport async function cmdTaskUnblock(\n db: Db,\n rawBlocked: string,\n opts: { by: string | readonly string[]; workstream?: string; json?: boolean },\n): Promise<void> {\n const { name: blocked } = await resolveEntityRef(db, rawBlocked, opts, \"task\");\n assertTaskInWorkstream(db, blocked, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n // Symmetric with `block`: same --by parsing on both halves of the\n // same edge operation, so undoing a multi-blocker block is a single\n // invocation too.\n const blockers = parseByFlag(opts.by);\n const byList = blockers.join(\",\");\n const results = blockers.map((blocker) => ({\n blockerName: blocker,\n ...removeBlockEdge(db, ws, blocked, blocker),\n }));\n const removed = results.filter((r) => r.removed).length;\n const nextSteps: NextStep[] = [\n { intent: \"Show what now blocks this task\", command: `mu task tree ${blocked} -w ${ws}` },\n { intent: \"Re-add the edges\", command: `mu task block ${blocked} --by ${byList} -w ${ws}` },\n ];\n if (opts.json) {\n const first = results[0];\n emitJson({\n blockedName: blocked,\n blockerName: first !== undefined && results.length === 1 ? first.blockerName : undefined,\n blockerNames: blockers,\n results,\n removed: removed > 0,\n removedEdges: removed,\n nextSteps,\n });\n return;\n }\n for (const r of results) {\n if (!r.removed) {\n console.log(pc.dim(`${r.blockerName} → ${blocked}: no such edge (no-op)`));\n continue;\n }\n console.log(`Removed edge ${pc.bold(r.blockerName)} → ${pc.bold(blocked)}`);\n }\n printNextSteps(nextSteps);\n}\n\nexport async function cmdTaskReparent(\n db: Db,\n rawId: string,\n opts: { blockedBy: string[]; workstream?: string; json?: boolean },\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n // An all-EMPTY --blocked-by '' is the documented clear-all-blockers\n // sentinel here (unlike --by, where zero blockers is meaningless),\n // so [] stays legal. A BLANK ' ' still throws from parseCsvFlag.\n const blockers = parseCsvFlag(opts.blockedBy, \"-b/--blocked-by\");\n const r = reparentTask(db, localId, blockers, { workstream: ws });\n const nextSteps: NextStep[] = [\n { intent: \"Show the new dependency tree\", command: `mu task tree ${localId} -w ${ws}` },\n { intent: \"Show the task\", command: `mu task show ${localId} -w ${ws}` },\n ];\n if (opts.json) {\n emitJson({ taskName: localId, blockerNames: blockers, ...r, nextSteps });\n return;\n }\n console.log(\n `Reparented ${pc.bold(localId)} ${pc.dim(`(removed ${r.removedEdges} edges, added ${r.addedEdges})`)}`,\n );\n printNextSteps(nextSteps);\n}\n\nexport async function cmdTaskDelete(\n db: Db,\n rawId: string,\n opts: { workstream?: string; json?: boolean; yes?: boolean } = {},\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n // Two-phase: bare = dry-run preview; --yes commits. Mirrors\n // `mu workstream teardown` / `mu undo`. Surfaced by feedback\n // ws task fb_task_delete_no_yes\n // (impact=30): the dogfood report typed `mu task delete X --yes`\n // (mirroring workstream teardown) and got 'unknown option --yes'\n // because the verb took no confirmation flag at all; two failed\n // deletes left long-named tasks lingering until noticed.\n const dryRun = opts.yes !== true;\n const r = deleteTask(db, localId, ws, { dryRun });\n const commitNextSteps: NextStep[] = [\n ...(r.group === null\n ? []\n : [\n {\n intent: \"Undo the delete (restores the task, its edges and notes)\",\n command: `mu undo ${r.group.slice(0, 8)} --yes`,\n },\n ]),\n {\n intent: \"List remaining tasks\",\n command: `mu task list -w ${ws}`,\n },\n ];\n const dryRunNextSteps: NextStep[] = [\n {\n intent: \"Confirm and actually delete (cascades to edges + notes)\",\n command: `mu task delete ${localId} -w ${ws} --yes`,\n },\n {\n intent: \"After deleting, find the delete's group to undo it (DB only)\",\n command: \"mu undo\",\n },\n {\n intent: \"Inspect the task + edges before deciding\",\n command: `mu task show ${localId} -w ${ws}`,\n },\n ];\n\n // Missing row — idempotent no-op (same outcome whether dry-run or\n // --yes). The `present: false` discriminator keeps this distinct\n // from a dry-run that found an existing task with no edges/notes.\n if (!r.present) {\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps: commitNextSteps });\n return;\n }\n console.log(pc.dim(`no task named ${localId} (already deleted?)`));\n return;\n }\n\n // Dry-run: print the cascade preview. The task DOES exist (present\n // checked above); zero edges + zero notes is a real cascade-of-one.\n if (r.dryRun) {\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps: dryRunNextSteps });\n return;\n }\n console.log(\n r.deletedEdges === 0 && r.deletedNotes === 0\n ? `Would delete ${pc.bold(localId)} ${pc.dim(\"(no edges, no notes)\")}`\n : `Would delete ${pc.bold(localId)} ${pc.dim(`(edges: ${r.deletedEdges}, notes: ${r.deletedNotes})`)}`,\n );\n console.log(\"\");\n console.log(pc.dim(\"(dry-run; rerun with --yes to actually delete)\"));\n console.log(\n pc.dim(\"The delete is one op group; `mu undo <group> --yes` reverts it (DB only).\"),\n );\n printNextSteps(dryRunNextSteps);\n return;\n }\n\n // Commit path.\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps: commitNextSteps });\n return;\n }\n console.log(\n `Deleted ${pc.bold(localId)} ${pc.dim(`(edges: ${r.deletedEdges}, notes: ${r.deletedNotes})`)}`,\n );\n printNextSteps(commitNextSteps);\n}\n","// mu — `mu task` lifecycle verbs (status transitions).\n//\n// close / open / park / accept / unpark. Each delegates to the SDK; changes are captured as ops\n// and optionally reported as evidence notes.\n//\n// Extracted from src/cli/tasks.ts as part of refactor_split_large_src_files.\n\nimport { refreshAgentTitle } from \"../../agents.js\";\nimport {\n assertTaskInWorkstream,\n emitJson,\n resolveEntityRef,\n resolveWorkstream,\n} from \"../../cli.js\";\nimport type { Db } from \"../../db.js\";\nimport { type NextStep, pc, printNextSteps, printNextStepsTo } from \"../../output.js\";\nimport { formatPair, type TaskPair } from \"../../tasks/status.js\";\nimport {\n acceptTask,\n type CloseSubstate,\n closeTask,\n getTask,\n openTask,\n parkTask,\n resolveActorIdentity,\n unparkTask,\n weakDecisionWarning,\n} from \"../../tasks.js\";\nimport { backendByName, type VcsBackendName } from \"../../vcs.js\";\nimport { getWorkspaceForAgent } from \"../../workspace.js\";\n\nexport async function cmdTaskClose(\n db: Db,\n rawId: string,\n opts: {\n evidence?: string;\n ifReady?: boolean;\n as?: string;\n why?: string;\n workstream?: string;\n json?: boolean;\n } = {},\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const actor = await resolveActorIdentity();\n const sdkOpts: Parameters<typeof closeTask>[2] = { workstream: ws };\n if (opts.evidence !== undefined) sdkOpts.evidence = opts.evidence;\n if (opts.ifReady) sdkOpts.ifReady = true;\n // closeTask validates the substate (InvalidSubstateError) and the\n // required --why (SubstateReasonRequiredError) before any write; the\n // cast only narrows the type, the SDK owns the check.\n if (opts.as !== undefined) sdkOpts.as = opts.as.toLowerCase() as CloseSubstate;\n if (opts.why !== undefined) sdkOpts.why = opts.why;\n // The reason note is attributed like the evidence note.\n if (opts.why !== undefined && opts.why !== \"\") sdkOpts.author = actor;\n // mufeedback task_close_evidence_does_not_append_the: closeTask\n // auto-inserts a `CLOSE: <evidence>` note when --evidence is\n // non-empty. Resolve the actor identity once per close so the note is\n // attributed to the closing worker (mu-spawned worker via\n // MU_AGENT_NAME, adopted pane via title, otherwise $USER /\n // 'orchestrator') and so the success Next: hints can inspect that\n // actor's workspace without resolving identity a second time.\n if (opts.evidence !== undefined && opts.evidence !== \"\") {\n sdkOpts.author = actor;\n }\n // Capture the owner BEFORE closeTask so we can refresh their title\n // even though closeTask doesn't return owner info. owner won't\n // change as a result of close (FK SET NULL only fires on delete).\n const taskRow = getTask(db, localId, ws);\n // Read before the close: the warning is about the finding as it was.\n const warnings = decisionWarnings(db, localId, ws, sdkOpts.as ?? \"done\", opts.why);\n const r = closeTask(db, localId, sdkOpts);\n // --if-ready can return a CloseSkippedResult (no mutation). Branch\n // first so the typed `skipped` field stays in scope below.\n if (\"skipped\" in r) {\n // A blocker in triage closes only when someone decides it: waiting on\n // it would hang, so lead with the triage inbox.\n const inTriage = r.blockingIds.filter((id) => getTask(db, id, ws)?.substate === \"triage\");\n const blockingNextSteps: NextStep[] = [\n ...(inTriage.length > 0\n ? [\n {\n intent: `Triage ${inTriage.length} blocking finding(s) (accept, or close --as rejected|duplicate)`,\n command: `mu task list --substate triage -w ${ws}`,\n },\n ]\n : []),\n {\n intent: \"Watch the remaining blockers (returns when one closes)\",\n command: `mu task wait ${r.blockingIds.join(\" \")} -w ${ws} --first --any --on-stall exit`,\n },\n { intent: \"Show the umbrella + blockers\", command: `mu task show ${localId} -w ${ws}` },\n {\n intent: \"Close anyway (override --if-ready)\",\n command: `mu task close ${localId} -w ${ws}`,\n },\n ];\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps: blockingNextSteps });\n return;\n }\n const total = r.blockingIds.length;\n const shown = r.blockingIds.slice(0, 8).join(\", \");\n const tail = total > 8 ? \", \\u2026\" : \"\";\n console.log(\n pc.dim(\n `Skipped ${pc.bold(localId)}: blocked by ${total} task(s) (${shown}${tail}); rerun without --if-ready to close anyway`,\n ),\n );\n printNextSteps(blockingNextSteps);\n return;\n }\n if (r.changed && taskRow?.ownerName) await refreshAgentTitle(db, taskRow.ownerName, ws);\n const pickNext: NextStep = {\n intent: r.unblocked.length > 0 ? \"Pick up an unblocked task\" : \"Pick the next ready task\",\n command: `mu task next -w ${ws}`,\n };\n const reopen: NextStep = {\n intent: \"Reopen if needed\",\n command: `mu task open ${localId} -w ${ws}`,\n };\n // A non-done close that released dependents leads with them.\n const nextSteps: NextStep[] = [\n ...(r.unblocked.length > 0 ? [pickNext, reopen] : [reopen, pickNext]),\n { intent: \"See full state\", command: `mu state -w ${ws}` },\n ];\n if (r.changed && r.status === \"CLOSED\") {\n await maybeAppendDirtyWorkspaceCommitHint(db, nextSteps, actor, ws, taskRow?.title ?? localId);\n }\n if (opts.json) {\n emitJson({ taskName: localId, ...r, warnings, nextSteps });\n return;\n }\n printDecisionWarnings(warnings, localId, ws);\n if (!r.changed) {\n console.log(pc.dim(`${localId} already CLOSED (no-op)`));\n printNextSteps(nextSteps);\n return;\n }\n const ev = opts.evidence ? pc.dim(` evidence: ${opts.evidence}`) : \"\";\n console.log(`Closed ${pc.bold(localId)} ${pc.dim(`(${transition(r)})`)}`);\n if (ev) console.log(ev);\n if (r.unblocked.length > 0) console.log(`Unblocked: ${r.unblocked.join(\", \")}`);\n printNextSteps(nextSteps);\n}\n\n/** The weak-decision warning for this accept / close, as a 0-or-1 list\n * (the `warnings` array in --json). Never blocks the verb. */\nfunction decisionWarnings(\n db: Db,\n localId: string,\n ws: string,\n kind: Parameters<typeof weakDecisionWarning>[3],\n reason: string | undefined,\n): string[] {\n const w = weakDecisionWarning(db, localId, ws, kind, reason);\n return w === undefined ? [] : [w];\n}\n\nfunction printDecisionWarnings(warnings: readonly string[], localId: string, ws: string): void {\n if (warnings.length === 0) return;\n for (const w of warnings) console.error(pc.yellow(`warning: ${w}`));\n printNextStepsTo(\n [\n {\n intent: \"Record what confirmed it\",\n command: `mu task note ${localId} -w ${ws} \"EVIDENCE: <command + result>\"`,\n },\n ],\n \"stderr\",\n );\n}\n\n/** \"OPEN → CLOSED/wontfix\": the pair transition a lifecycle verb made. */\nfunction transition(r: {\n previousStatus: TaskPair[\"status\"];\n previousSubstate: TaskPair[\"substate\"];\n status: TaskPair[\"status\"];\n substate: TaskPair[\"substate\"];\n}): string {\n const from = formatPair({ status: r.previousStatus, substate: r.previousSubstate });\n return `${from} → ${formatPair({ status: r.status, substate: r.substate })}`;\n}\n\n/** Commit-everything command per backend, message appended. Every\n * form picks up untracked files, because `isClean` counts them as\n * dirty (`git commit -am` alone would refuse with \"nothing added\"). */\nconst COMMIT_ALL: Record<Exclude<VcsBackendName, \"none\">, string> = {\n git: \"git add -A && git commit -m\",\n jj: \"jj commit -m\",\n sl: \"sl commit --addremove -m\",\n};\n\n/** The \"Don't forget to commit\" command for a dirty workspace. Exported\n * for the fast-tier test that pins every backend's form. */\nexport function commitHintCommand(\n backend: Exclude<VcsBackendName, \"none\">,\n actor: string,\n workstream: string,\n taskTitle: string,\n): string {\n return `cd $(mu workspace path ${actor} -w ${workstream}) && ${COMMIT_ALL[backend]} ${shellSingleQuote(taskTitle)}`;\n}\n\nasync function maybeAppendDirtyWorkspaceCommitHint(\n db: Db,\n nextSteps: NextStep[],\n actor: string,\n workstream: string,\n taskTitle: string,\n): Promise<void> {\n if (actor.length === 0) return;\n try {\n const row = getWorkspaceForAgent(db, actor, workstream);\n if (row === undefined || row.backend === \"none\") return;\n const backend = backendByName(row.backend);\n const clean = await backend.isClean(row.path);\n if (clean) return;\n nextSteps.push({\n intent: \"Don't forget to commit\",\n command: commitHintCommand(row.backend, actor, workstream, taskTitle),\n });\n } catch {\n // Best-effort hint only: a VCS probe failure must never make\n // `mu task close` fail after the task successfully closed.\n }\n}\n\nfunction shellSingleQuote(value: string): string {\n return `'${value.replaceAll(\"'\", \"'\\\\''\")}'`;\n}\n\nexport async function cmdTaskOpen(\n db: Db,\n rawId: string,\n opts: { evidence?: string; workstream?: string; json?: boolean } = {},\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const sdkOpts: Parameters<typeof openTask>[2] = { workstream: ws };\n if (opts.evidence !== undefined) sdkOpts.evidence = opts.evidence;\n if (opts.evidence) sdkOpts.author = await resolveActorIdentity();\n const r = openTask(db, localId, sdkOpts);\n const nextSteps: NextStep[] = [\n {\n intent: \"Claim it\",\n command: `mu task claim ${localId} -w ${ws} (--self / --for <worker>)`,\n },\n { intent: \"Close again\", command: `mu task close ${localId} -w ${ws}` },\n ];\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps });\n return;\n }\n if (!r.changed) {\n console.log(pc.dim(`${localId} already OPEN (no-op)`));\n printNextSteps(nextSteps);\n return;\n }\n const ev = opts.evidence ? pc.dim(` evidence: ${opts.evidence}`) : \"\";\n console.log(`Reopened ${pc.bold(localId)} ${pc.dim(`(${transition(r)})`)}`);\n if (ev) console.log(ev);\n printNextSteps(nextSteps);\n}\n\nexport async function cmdTaskPark(\n db: Db,\n rawId: string,\n opts: { why: string; evidence?: string; workstream?: string; json?: boolean },\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const sdkOpts: Parameters<typeof parkTask>[2] = {\n workstream: ws,\n why: opts.why,\n author: await resolveActorIdentity(),\n };\n if (opts.evidence !== undefined) sdkOpts.evidence = opts.evidence;\n const r = parkTask(db, localId, sdkOpts);\n const nextSteps: NextStep[] = [\n { intent: \"Unpark it later\", command: `mu task unpark ${localId} -w ${ws}` },\n { intent: \"List parked tasks\", command: `mu task list --substate parked -w ${ws}` },\n ];\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps });\n return;\n }\n if (!r.changed) {\n console.log(pc.dim(`${localId} already OPEN/parked (no-op)`));\n } else {\n console.log(`Parked ${pc.bold(localId)} ${pc.dim(`(${transition(r)})`)}`);\n }\n printNextSteps(nextSteps);\n}\n\nexport async function cmdTaskAccept(\n db: Db,\n rawId: string,\n opts: { evidence?: string; workstream?: string; json?: boolean } = {},\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const sdkOpts: Parameters<typeof acceptTask>[2] = { workstream: ws };\n if (opts.evidence !== undefined) sdkOpts.evidence = opts.evidence;\n if (opts.evidence) sdkOpts.author = await resolveActorIdentity();\n const warnings = decisionWarnings(db, localId, ws, \"accept\", opts.evidence);\n const r = acceptTask(db, localId, sdkOpts);\n const nextSteps: NextStep[] = [\n {\n intent: \"Claim it\",\n command: `mu task claim ${localId} -w ${ws} (--self / --for <worker>)`,\n },\n { intent: \"Triage the next one\", command: `mu task list --substate triage -w ${ws}` },\n ];\n if (opts.json) {\n emitJson({ taskName: localId, ...r, warnings, nextSteps });\n return;\n }\n printDecisionWarnings(warnings, localId, ws);\n if (!r.changed) {\n const pair = formatPair({ status: r.status, substate: r.substate });\n console.log(pc.dim(`${localId} is ${pair}, not in triage (no-op)`));\n } else {\n console.log(`Accepted ${pc.bold(localId)} ${pc.dim(`(${transition(r)})`)}`);\n }\n printNextSteps(nextSteps);\n}\n\nexport async function cmdTaskUnpark(\n db: Db,\n rawId: string,\n opts: { evidence?: string; workstream?: string; json?: boolean } = {},\n): Promise<void> {\n const { name: localId } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, localId, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const sdkOpts: Parameters<typeof unparkTask>[2] = { workstream: ws };\n if (opts.evidence !== undefined) sdkOpts.evidence = opts.evidence;\n if (opts.evidence) sdkOpts.author = await resolveActorIdentity();\n const r = unparkTask(db, localId, sdkOpts);\n const nextSteps: NextStep[] = [\n {\n intent: \"Claim it\",\n command: `mu task claim ${localId} -w ${ws} (--self / --for <worker>)`,\n },\n { intent: \"Pick the next ready task\", command: `mu task next -w ${ws}` },\n ];\n if (opts.json) {\n emitJson({ taskName: localId, ...r, nextSteps });\n return;\n }\n if (!r.changed) {\n const pair = formatPair({ status: r.status, substate: r.substate });\n console.log(pc.dim(`${localId} is ${pair}, not parked (no-op)`));\n } else {\n console.log(`Unparked ${pc.bold(localId)} ${pc.dim(`(${transition(r)})`)}`);\n }\n printNextSteps(nextSteps);\n}\n","// mu — `mu task tree` verb (ASCII / JSON dependency rendering).\n//\n// Renders the blocker subtree (default) or dependent subtree (--down)\n// of a task. Diamonds — a node reachable by two parent paths — collapse\n// to one full subtree render plus a one-line \"↻\" recurrence marker\n// at every later occurrence. Schema forbids cycles, so the seen-set\n// only fires on diamonds in practice; double-edged as defence against\n// future bugs.\n//\n// Extracted from src/cli/tasks.ts as part of the wire-out follow-up\n// to refactor_split_large_src_files.\n\nimport { assertTaskInWorkstream, colorPair, emitJson, resolveEntityRef } from \"../../cli.js\";\nimport { renderTaskTree } from \"../../dag.js\";\nimport type { Db } from \"../../db.js\";\nimport { pc } from \"../../output.js\";\nimport { getTask, getTaskEdges, TaskNotFoundError, type TaskRow } from \"../../tasks.js\";\n\ninterface TreeOpts {\n /** Show dependents (what this task blocks) instead of blockers. */\n down?: boolean;\n json?: boolean;\n workstream?: string;\n}\n\n/** JSON shape: each node carries its full TaskRow plus a recursive\n * `children` array (whose contents depend on direction — blockers if\n * --down is omitted, dependents if --down). Diamond-recurrent nodes carry\n * `recurrence: true` and an empty `children` (instead of expanding). */\ninterface TreeJsonNode {\n task: TaskRow;\n recurrence?: true;\n children: TreeJsonNode[];\n}\n\nexport async function cmdTaskTree(db: Db, rawId: string, opts: TreeOpts): Promise<void> {\n // resolveEntityRef parses `<workstream>/<name>` if present, else uses\n // opts.workstream. Returns the resolved (name, workstream) pair so we\n // never re-resolve downstream — the workstream is mandatory on every\n // SDK call that resolves an entity by name.\n const { name: rootId, workstream: ws } = await resolveEntityRef(db, rawId, opts, \"task\");\n assertTaskInWorkstream(db, rootId, ws);\n const root = getTask(db, rootId, ws);\n if (!root) throw new TaskNotFoundError(rootId);\n const down = opts.down ?? false;\n const seen = new Set<string>([rootId]);\n\n if (opts.json) {\n const node: TreeJsonNode = {\n task: root,\n children: buildJsonTree(db, ws, rootId, down, seen),\n };\n emitJson({ direction: down ? \"dependents\" : \"blockers\", root: node });\n return;\n }\n\n const direction = down ? \"dependents\" : \"blockers\";\n const swapHint = down ? \"omit --down for blockers\" : \"--down for dependents\";\n console.log(pc.bold(`Tree of ${rootId} ${pc.dim(`(${direction} below; ${swapHint})`)}`));\n console.log(\n renderTaskTree(db, ws, root, down ? \"dependents\" : \"blockers\", (task) => colorPair(task)),\n );\n}\n\nfunction buildJsonTree(\n db: Db,\n workstream: string,\n taskId: string,\n down: boolean,\n seen: Set<string>,\n): TreeJsonNode[] {\n const edges = getTaskEdges(db, taskId, workstream);\n const childIds = down ? edges.dependents : edges.blockers;\n const out: TreeJsonNode[] = [];\n for (const childId of childIds) {\n const child = getTask(db, childId, workstream);\n if (!child) continue;\n if (seen.has(childId)) {\n out.push({ task: child, recurrence: true, children: [] });\n continue;\n }\n seen.add(childId);\n out.push({ task: child, children: buildJsonTree(db, workstream, childId, down, seen) });\n }\n return out;\n}\n","// mu — `mu task` commander wiring.\n//\n// Pure glue: every `task.command(...)` definition lives here, so the\n// per-verb modules in this cluster stay focused on behaviour. Imported\n// by buildProgram() in src/cli.ts via the re-export hub at\n// src/cli/tasks.ts.\n//\n// Extracted from src/cli/tasks.ts as part of the wire-out follow-up\n// to refactor_split_large_src_files.\n\nimport type { Command } from \"commander\";\nimport {\n handle,\n JSON_OPT,\n normalizeInheritedWorkstream,\n parseImpact,\n parseLines,\n parsePositiveNumber,\n parseSeconds,\n TASK_SORT_KEYS,\n WORKSTREAM_OPT,\n} from \"../../cli.js\";\nimport { TASK_SUBSTATES } from \"../../tasks/status.js\";\nimport { TASK_STATUS_LIST } from \"../../tasks.js\";\nimport { cmdClaim, cmdTaskRelease, cmdTaskWait } from \"./claim.js\";\nimport { cmdTaskBlock, cmdTaskDelete, cmdTaskReparent, cmdTaskUnblock } from \"./edges.js\";\nimport {\n cmdTaskAdd,\n cmdTaskNote,\n cmdTaskNotes,\n cmdTaskShow,\n cmdTaskUpdate,\n resolveNoteText,\n} from \"./edit.js\";\nimport {\n cmdTaskAccept,\n cmdTaskClose,\n cmdTaskOpen,\n cmdTaskPark,\n cmdTaskUnpark,\n} from \"./lifecycle.js\";\nimport { cmdTaskList, cmdTaskNext, cmdTaskOwnedBy } from \"./queries.js\";\nimport { cmdTaskTree } from \"./tree.js\";\n\nexport function wireTaskCommands(program: Command): void {\n const task = program.command(\"task\").description(\"Task graph commands\");\n\n task\n .command(\"add [id]\")\n .description(\n \"Add a task to the graph. The id positional is optional — if omitted, derived from --title via slugify (collisions get _2, _3, … suffixes). Auto-derived ids are capped at ~40 chars with a word-boundary cut, so long titles drop trailing clauses; pass the <id> positional explicitly to override.\",\n )\n .requiredOption(\"-t, --title <title>\", \"task title\")\n .requiredOption(\"-i, --impact <n>\", \"impact 1..100\", parseImpact)\n .requiredOption(\"-e, --effort-days <days>\", \"effort in days (>0)\", parsePositiveNumber)\n .option(\n \"-b, --blocked-by <ids...>\",\n \"task ids that block this one (repeat or comma-separate; or both)\",\n )\n .option(\n \"--note <text>\",\n \"append an initial note after creating the task; `-` reads it from stdin (prose: --note - <<'EOF')\",\n )\n .option(\"--note-author <name>\", \"author label for --note (default: current actor)\")\n .option(\n \"--triage\",\n \"start as OPEN/triage: a proposal (e.g. a review finding) kept out of next/claim until `mu task accept`\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (id: string | undefined) {\n const opts = (this as Command).opts() as {\n title: string;\n impact: number;\n effortDays: number;\n blockedBy?: string[];\n note?: string;\n noteAuthor?: string;\n triage?: boolean;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskAdd(db, id, opts), this as Command)();\n });\n\n // --sort key list shared across list/next. `id` is the historical\n // default for `mu task list`; `roi` is the default for `next` (the\n // \"what should I do\" verb; `next -n 0` replaced `task ready`). The two time-based\n // keys (`recency` = updated_at DESC, `age` = created_at ASC) trigger\n // an extra `updated`/`created` column with relative timestamps so\n // the user sees the dimension they sorted by.\n const SORT_OPT_DESC = `sort key (${TASK_SORT_KEYS.join(\" | \")})`;\n const SUBSTATE_OPT_DESC = `filter by substate (${[...new Set(Object.values(TASK_SUBSTATES).flat())].join(\" | \")}; repeat or comma-separate)`;\n\n task\n .command(\"list\")\n .description(\"List every task in the current workstream (id, status, ROI, owner)\")\n .option(...WORKSTREAM_OPT)\n .option(\n \"--status <status...>\",\n `filter by lifecycle status (${TASK_STATUS_LIST}; case-insensitive; repeat or comma-separate; or both)`,\n )\n .option(\"--substate <substate...>\", SUBSTATE_OPT_DESC)\n .option(\"--sort <key>\", `${SORT_OPT_DESC} (default id)`)\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as {\n workstream?: string;\n json?: boolean;\n status?: string[];\n substate?: string[];\n sort?: string;\n };\n return handle((db) => cmdTaskList(db, opts), this as Command)();\n });\n\n task\n .command(\"next\")\n .description(\n \"Show the next ready task(s) by ROI (impact / effort_days). The 'what should I do?' verb. Pass -n 0 for the unlimited 'what is doable?' shape (merged-in `task ready`).\",\n )\n .option(\n \"-n, --lines <k>\",\n \"how many top-K tasks to return (default 1; 0 = all ready)\",\n parseLines,\n )\n .option(...WORKSTREAM_OPT)\n .option(\"--sort <key>\", `${SORT_OPT_DESC} (default roi)`)\n .option(\n \"--status <status...>\",\n `filter by lifecycle status (${TASK_STATUS_LIST}; case-insensitive; repeat or comma-separate; or both)`,\n )\n .option(\"--substate <substate...>\", SUBSTATE_OPT_DESC)\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as {\n workstream?: string;\n lines?: number;\n json?: boolean;\n sort?: string;\n status?: string[];\n substate?: string[];\n };\n return handle((db) => cmdTaskNext(db, opts), this as Command)();\n });\n\n task\n .command(\"owned-by <agent>\")\n .description(\n \"List tasks owned by an agent. Defaults to the current workstream (v5: agent names are per-workstream unique). Pass --all to surface every workstream's same-named worker. Excludes CLOSED by default — pass --include-closed for the full historical owner list.\",\n )\n .option(\n \"--include-closed\",\n \"include CLOSED tasks (closeTask preserves owner as historical record; default omits them)\",\n )\n .option(\n \"--all\",\n \"surface every workstream's same-named agent (cross-workstream view; default scopes to current workstream)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (agent: string) {\n const opts = (this as Command).optsWithGlobals() as {\n json?: boolean;\n includeClosed?: boolean;\n all?: boolean;\n workstream?: string | string[];\n };\n return handle(\n (db) =>\n cmdTaskOwnedBy(db, agent, {\n ...opts,\n workstream: normalizeInheritedWorkstream(opts.workstream),\n }),\n this as Command,\n )();\n });\n\n task\n .command(\"note <id> [text]\")\n .description(\n \"Append a note to a task. The note text may be given positionally or via --text (dogfood-note-arg-shape: `mu task add --note` is a flag, so the flag form is what you reach for on the follow-up). Author defaults to $MU_AGENT_NAME (env injected at spawn) > pane title > $USER > 'orchestrator'; pass --author to override. Quoting: single quotes for short text; for prose (an apostrophe ends '...', double quotes expand $VAR and `cmd`) pass `-` and pipe a quoted heredoc: mu task note <id> - <<'EOF'. Stdin text is stored verbatim (no \\\\n unescaping); a bare `-` or empty note warns.\",\n )\n .option(\"--author <name>\", \"override the auto-detected author label\")\n .option(\n \"--text <text>\",\n \"the note text (alias for the positional <text> argument; `-` reads stdin)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (id: string, text: string | undefined) {\n const opts = (this as Command).opts() as {\n workstream?: string;\n json?: boolean;\n author?: string;\n text?: string;\n };\n // resolveNoteText throws UsageError; call it INSIDE the handle()\n // callback so the typed-error → exit-code map wraps it. A throw\n // from the .action() body itself escapes to commander's\n // parse-time catch, which is a different (and DB-close-skipping)\n // lane. Same rule every other verb's validation follows.\n return handle(\n (db) => cmdTaskNote(db, id, resolveNoteText(text, opts.text), opts),\n this as Command,\n )();\n });\n\n task\n .command(\"show <id>\")\n .description(\"Show a task: row + edges (blockers/dependents) + notes\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as { json?: boolean; workstream?: string };\n return handle((db) => cmdTaskShow(db, id, opts), this as Command)();\n });\n\n task\n .command(\"tree <id>\")\n .description(\n \"ASCII tree of a task's blockers (default) or dependents (--down). Diamonds collapse to one render with an arrow marker.\",\n )\n .option(\"--down\", \"render dependents (what this task blocks) instead of blockers\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n down?: boolean;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskTree(db, id, opts), this as Command)();\n });\n\n task\n .command(\"notes <id>\")\n .description(\n \"List the notes attached to a task (oldest first). Filters: --tail N (last N), --since <iso> (after timestamp), --since-claim (since most recent claim event).\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .option(\"--tail <n>\", \"print only the last N notes (alias --last)\", parsePositiveNumber)\n .option(\"--last <n>\", \"alias for --tail\", parsePositiveNumber)\n .option(\"--since <iso>\", \"print only notes created after this ISO 8601 timestamp\")\n .option(\n \"--since-claim\",\n \"print only notes since the most recent 'task claim' event (auto-resolved)\",\n )\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n json?: boolean;\n workstream?: string;\n tail?: number;\n last?: number;\n since?: string;\n sinceClaim?: boolean;\n };\n // --last is an alias for --tail; collapse before passing to the verb.\n // If both are provided, prefer the explicit --tail.\n const tail = opts.tail ?? opts.last;\n const merged: {\n json?: boolean;\n workstream?: string;\n tail?: number;\n since?: string;\n sinceClaim?: boolean;\n } = {};\n if (opts.json !== undefined) merged.json = opts.json;\n if (opts.workstream !== undefined) merged.workstream = opts.workstream;\n if (tail !== undefined) merged.tail = tail;\n if (opts.since !== undefined) merged.since = opts.since;\n if (opts.sinceClaim !== undefined) merged.sinceClaim = opts.sinceClaim;\n return handle((db) => cmdTaskNotes(db, id, merged), this as Command)();\n });\n\n // --evidence <text> on the four lifecycle verbs records what the\n // caller relied on (test output, command exit, observed file change)\n // in the auto-emitted event payload. The verb still trusts the\n // caller; the audit trail records what they said. First inch of\n // the \"observed vs claimed state\" distinction.\n const EVIDENCE_OPT = [\n \"--evidence <text>\",\n \"record what the caller observed (e.g. 'tests pass: npm test exit 0'); appears verbatim in the event log\",\n ] as const;\n\n task\n .command(\"close <id>\")\n .description(\n \"Mark a task CLOSED (idempotent). --as records why it closed (not every close is done work); any CLOSED substate satisfies blockers. --if-ready no-ops unless every blocker is CLOSED — the umbrella-on-wave-done pattern.\",\n )\n .option(\n \"--as <substate>\",\n `closing substate (${TASK_SUBSTATES.CLOSED.join(\" | \")}; default done)`,\n )\n .option(\"--why <text>\", \"reason, stored as a note; required unless --as done\")\n .option(\n \"--if-ready\",\n \"only close when every blocker is CLOSED; otherwise no-op + list the still-blocking ids\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...EVIDENCE_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n evidence?: string;\n as?: string;\n why?: string;\n ifReady?: boolean;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskClose(db, id, opts), this as Command)();\n });\n\n task\n .command(\"open <id>\")\n .description(\"Mark a task OPEN — e.g. to reopen something closed by mistake (idempotent)\")\n .option(...WORKSTREAM_OPT)\n .option(...EVIDENCE_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n evidence?: string;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskOpen(db, id, opts), this as Command)();\n });\n\n task\n .command(\"park <id>\")\n .description(\n \"Park an OPEN task (OPEN/parked): it leaves `next` and `claim` refuses it without --force. Dependents stay blocked. Idempotent.\",\n )\n .requiredOption(\"--why <text>\", \"why it is parked; stored as a note\")\n .option(...WORKSTREAM_OPT)\n .option(...EVIDENCE_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n why: string;\n evidence?: string;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskPark(db, id, opts), this as Command)();\n });\n\n task\n .command(\"accept <id>\")\n .description(\n \"Accept an OPEN/triage task (a proposed finding) as work: OPEN/todo, back in `next`. No-op on any other state. Decline with `close --as rejected|duplicate --why`.\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...EVIDENCE_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n evidence?: string;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskAccept(db, id, opts), this as Command)();\n });\n\n task\n .command(\"unpark <id>\")\n .description(\"Return a parked task to OPEN (back in `next`). No-op on any other state.\")\n .option(...WORKSTREAM_OPT)\n .option(...EVIDENCE_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n evidence?: string;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskUnpark(db, id, opts), this as Command)();\n });\n\n task\n .command(\"release <id>\")\n .description(\n \"Clear a task's owner. IN_PROGRESS auto-flips to OPEN so the task re-enters the ready set; other statuses preserved. Use --reopen to force OPEN from CLOSED. Idempotent.\",\n )\n .option(\n \"--reopen\",\n \"force status to OPEN regardless of current status (escape hatch for un-closing a CLOSED owned task in one verb)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...EVIDENCE_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n reopen?: boolean;\n evidence?: string;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskRelease(db, id, opts), this as Command)();\n });\n\n task\n .command(\"claim <id>\")\n .description(\n \"Claim a task. Default: derive agent from $TMUX_PANE's title (must be a registered worker). \" +\n \"Use --for <worker> to dispatch. Use --self for orchestrator-direct work (anonymous claim, owner=NULL, actor recorded in agent_logs).\",\n )\n .option(\n \"-f, --for <agent>\",\n \"claim on behalf of a registered worker (dispatch); accepts bare 'name' (resolves in the task's workstream) or qualified '<workstream>/<name>' for cross-workstream dispatch (e.g. 'roadmap-v0-3/worker-1')\",\n )\n .option(\n \"--self\",\n \"anonymous claim (orchestrator pattern): owner stays NULL; actor recorded in agent_logs.source. Mutually exclusive with --for.\",\n )\n .option(\n \"--actor <name>\",\n \"override the actor name used for the log (only valid with --self; defaults to pane title or $USER)\",\n )\n .option(\"--force\", \"claim even when the task is parked or in triage (OPEN/parked, OPEN/triage)\")\n .option(\n \"--strict-staleness\",\n \"refuse --for dispatch when the target agent's workspace is stale (default: warn and proceed)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...EVIDENCE_OPT)\n .option(...JSON_OPT)\n .action(function (taskId: string) {\n const opts = (this as Command).opts() as {\n for?: string;\n self?: boolean;\n actor?: string;\n evidence?: string;\n workstream?: string;\n json?: boolean;\n strictStaleness?: boolean;\n force?: boolean;\n };\n return handle((db) => cmdClaim(db, taskId, opts), this as Command)();\n });\n\n task\n .command(\"block <blocked>\")\n .description(\n \"Add blocking edges: --by <ids...> blocks <blocked>. Accepts repeat or comma-separated ids (same shape as `mu task add --blocked-by`). Validates same-workstream + cycle.\",\n )\n .requiredOption(\n \"-b, --by <blockers...>\",\n \"the task(s) that should block <blocked> (repeat or comma-separate)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (blocked: string) {\n const opts = (this as Command).opts() as {\n by: string | string[];\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskBlock(db, blocked, opts), this as Command)();\n });\n\n task\n .command(\"unblock <blocked>\")\n .description(\n \"Remove blocking edges (idempotent). --by accepts repeat or comma-separated ids, symmetric with `mu task block`.\",\n )\n .requiredOption(\n \"-b, --by <blockers...>\",\n \"the task(s) whose blocker edge to remove (repeat or comma-separate)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (blocked: string) {\n const opts = (this as Command).opts() as {\n by: string | string[];\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskUnblock(db, blocked, opts), this as Command)();\n });\n\n task\n .command(\"delete <id>\")\n .description(\n \"Delete a task (cascades edges + notes via FK). Two-phase: bare = dry-run preview; --yes commits. Idempotent on missing. The delete is one op group; `mu undo <group> --yes` reverts it (DB only).\",\n )\n .option(\"-y, --yes\", \"actually delete (without --yes prints a dry-run preview)\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n workstream?: string;\n json?: boolean;\n yes?: boolean;\n };\n return handle((db) => cmdTaskDelete(db, id, opts), this as Command)();\n });\n\n task\n .command(\"update <id>\")\n .description(\n \"Update scalar fields on a task. Pass at least one of --title, --impact, --effort-days. Use close/open/release for status/owner changes.\",\n )\n .option(\"-t, --title <title>\", \"new title\")\n .option(\"-i, --impact <n>\", \"new impact 1..100\", parseImpact)\n .option(\"-e, --effort-days <days>\", \"new effort in days (>0)\", parsePositiveNumber)\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n title?: string;\n impact?: number;\n effortDays?: number;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskUpdate(db, id, opts), this as Command)();\n });\n\n task\n .command(\"reparent <id>\")\n .description(\n \"Atomically replace every incoming edge of <id> with the new --blocked-by list. Pass --blocked-by '' to clear all blockers.\",\n )\n .requiredOption(\n \"-b, --blocked-by <ids...>\",\n \"tasks that block <id> (repeat or comma-separate; or both; pass an empty string to clear)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (id: string) {\n const opts = (this as Command).opts() as {\n blockedBy: string[];\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskReparent(db, id, opts), this as Command)();\n });\n\n task\n .command(\"wait <ids...>\")\n .description(\n \"Block until the listed tasks reach --status (default CLOSED). Each <id> may be bare (resolves via -w / $MU_SESSION / tmux) or qualified `<workstream>/<name>` (cross-workstream waits don't need -w). Default: every task must reach the target. --any / --first exit on the first one that does; --first additionally prints the firing ref's qualified id to stdout. A worker needing attention terminates the wait with exit 7 (--on-stall exit, the default). Exit 0 = condition met; 5 = timeout; 6 = a watched task was reaper-flipped IN_PROGRESS→OPEN (target=CLOSED only); 7 = a worker needs attention (target=CLOSED, unless --on-stall warn).\",\n )\n .option(\n \"--status <status>\",\n `target status (${TASK_STATUS_LIST}, case-insensitive); default CLOSED`,\n )\n .option(\n \"--any\",\n \"succeed as soon as ONE listed task reaches the target (default: all must). Reports THAT one fired, not which: --json leaves `firing` null even on success, so use --first if you need to identify the ref.\",\n )\n .option(\n \"--first\",\n \"alias for --any that ALSO prints the firing ref's qualified id to stdout and populates `firing` in --json (which --any leaves null). Use to drive a single-shot dispatch loop: `closed=$(mu task wait a b --first --json | jq -r .firing.qualifiedId)`.\",\n )\n .option(\n \"--timeout <seconds>\",\n \"max seconds to wait, fractions allowed (0 = forever, default 600)\",\n parseSeconds,\n )\n .option(\n \"--stuck-after <seconds>\",\n \"the TRIGGER: mark an IN_PROGRESS task as needing attention when its owner has been in needs_input for >= N seconds since their last status change (0 = disable; default 120, or 5 for a pi owner read over its control socket, whose idle is exact and comes after the close nudge; an explicit value applies to every owner). needs_input has several causes — the worker may have finished without closing, be waiting on an answer, or be sitting at a prompt — so the warning names the observation and points at `mu agent read <owner>`, which is the next move in every case. The default ACTION is `exit` (exit 7); see --on-stall warn to keep polling instead.\",\n parseSeconds,\n )\n .option(\n \"--on-stall <action>\",\n \"the ACTION when --stuck-after fires: 'exit' (default; yellow attention warning naming the owner + age, plus a corroborating agent_logs event, then exit 7 = STALL_DETECTED so an orchestrator can branch on the idle-vs-dead distinction) or 'warn' (same emit + persist; wait keeps polling). Suppressed when --status is anything other than CLOSED (mirrors exit-6's carve-out). If exit-6 (dead pane) and exit-7 (stall) would fire in the same poll, exit 6 wins (dead pane is unambiguous; stall is ambiguous).\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (ids: string[]) {\n const opts = (this as Command).opts() as {\n status?: string;\n any?: boolean;\n first?: boolean;\n timeout?: number;\n stuckAfter?: number;\n onStall?: \"warn\" | \"exit\";\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdTaskWait(db, ids, opts), this as Command)();\n });\n}\n","// mu — `mu db backup | compact | forget`: whole-DB file commands.\n//\n// mu once had `mu db export / import / replay` — a whole-DB sync\n// mechanism with manifests, per-workstream drift detection, and\n// divergence sidecars (1500+ LOC). All three are gone: sync is ambient over\n// segments, and disaster recovery is `mu rebuild`.\n//\n// `backup` survives for the one case those verbs were actually used for\n// — \"give me one file I can scp\" — which SQLite already implements as a\n// single `VACUUM INTO`, so it has no SDK module. A backup file is a\n// convenience copy that starts going stale the moment it is written.\n//\n// `compact` and `forget` shrink mu.db. Their policy lives in the SDK\n// (src/compact.ts); this file adds the dry run, the backup beside the\n// DB, the VACUUM, and the drift check after.\n\nimport { existsSync, mkdirSync } from \"node:fs\";\nimport { dirname, resolve } from \"node:path\";\nimport type { Command } from \"commander\";\nimport { emitJson, handle, JSON_OPT } from \"../cli.js\";\nimport {\n compact,\n type ForgetPlan,\n forget,\n listForgetCandidates,\n planCompact,\n planForget,\n} from \"../compact.js\";\nimport type { Db } from \"../db.js\";\nimport { formatBytes } from \"../disk-recon.js\";\nimport { checkDrift, DriftDetectedError } from \"../drift.js\";\nimport { muTable, pc, printNextSteps } from \"../output.js\";\nimport { UsageError } from \"./handle.js\";\n\nexport function cmdDbBackup(db: Db, file: string, opts: { json?: boolean } = {}): void {\n const target = resolve(file);\n // VACUUM INTO refuses an existing target itself, but its error is a\n // raw SQLite string; a typed UsageError gets the operator an exit code\n // and a next step instead.\n if (existsSync(target)) {\n throw new UsageError(`${target} already exists: mu db backup never overwrites`);\n }\n mkdirSync(dirname(target), { recursive: true });\n db.prepare(\"VACUUM INTO ?\").run(target);\n\n const nextSteps = [\n {\n intent: \"Inspect the copy without touching the live DB\",\n command: `MU_DB_PATH=${target} mu state`,\n },\n { intent: \"Disaster recovery is a rebuild, not a copy\", command: \"mu rebuild <file>\" },\n ];\n if (opts.json === true) {\n emitJson({ path: target, nextSteps });\n return;\n }\n console.log(`Backed up to ${pc.bold(target)}`);\n printNextSteps(nextSteps);\n}\n\n/** Backup next to the DB, named so it sorts with it: `mu.db.pre-<verb>-<ts>`. */\nfunction backupBeside(db: Db, verb: string): string {\n const ts = new Date().toISOString().replace(/[:.]/g, \"-\");\n const target = `${db.name}.pre-${verb}-${ts}`;\n db.prepare(\"VACUUM INTO ?\").run(target);\n return target;\n}\n\n/** Reclaim the freed pages, then prove the log still explains the tables. */\nfunction vacuumAndCheck(\n db: Db,\n backup: string,\n): { before: number; after: number; checkpointed: boolean } {\n // Sizes are the logical DB (page_count × page_size, read through the\n // WAL), not statSync(db.name): in WAL mode VACUUM's rewritten pages sit\n // in -wal until a checkpoint, and a concurrent reader can make that\n // checkpoint return busy, leaving the main file at its old size.\n const before = dbBytes(db);\n db.exec(\"VACUUM\");\n // Shrink the main file now when no reader pins the WAL; otherwise the\n // next checkpoint (any later mu write) does it.\n const [cp] = db.pragma(\"wal_checkpoint(TRUNCATE)\") as { busy: number }[];\n const checkpointed = cp?.busy === 0;\n const after = dbBytes(db);\n const report = checkDrift(db);\n if (!report.clean) {\n console.error(\n pc.red(`drift after the rewrite (${report.totalDrift}); the backup is ${backup}`),\n );\n throw new DriftDetectedError(report.totalDrift, report.records);\n }\n return { before, after, checkpointed };\n}\n\nfunction dbBytes(db: Db): number {\n const pages = db.pragma(\"page_count\", { simple: true }) as number;\n const pageSize = db.pragma(\"page_size\", { simple: true }) as number;\n return pages * pageSize;\n}\n\nconst CHECKPOINT_PENDING =\n \"another connection is reading the DB; the file shrinks on its next checkpoint\";\n\nexport function cmdDbCompact(db: Db, opts: { yes?: boolean; json?: boolean } = {}): void {\n const plan = planCompact(db);\n if (opts.yes !== true || plan.tombstones === 0) {\n const nextSteps =\n plan.tombstones === 0 ? [] : [{ intent: \"Apply it\", command: \"mu db compact --yes\" }];\n if (opts.json === true) {\n emitJson({ dryRun: true, ...plan, nextSteps });\n return;\n }\n console.log(\n plan.tombstones === 0\n ? pc.dim(\"nothing to compact: no redundant note tombstones\")\n : `${plan.tombstones} note tombstones repeat a put already in the log (${formatBytes(plan.bytes)}). Dry run; nothing changed.`,\n );\n printNextSteps(nextSteps);\n return;\n }\n const backup = backupBeside(db, \"compact\");\n compact(db);\n const size = vacuumAndCheck(db, backup);\n if (opts.json === true) {\n emitJson({ dryRun: false, ...plan, backup, ...size });\n return;\n }\n console.log(\n `Compacted ${plan.tombstones} note tombstones: ${formatBytes(size.before)} → ${formatBytes(size.after)}. Drift check clean.`,\n );\n if (!size.checkpointed) console.log(pc.dim(CHECKPOINT_PENDING));\n console.log(pc.dim(`backup: ${backup}`));\n}\n\nfunction printForgetTable(plan: ForgetPlan): void {\n const t = muTable({ head: [\"workstream\", \"torn down\", \"ops\", \"size\"].map((h) => pc.bold(h)) });\n for (const c of plan.candidates)\n t.push([c.name, c.tornDownAt.slice(0, 10), String(c.ops), formatBytes(c.bytes)]);\n console.log(t.toString());\n}\n\nexport function cmdDbForget(\n db: Db,\n names: string[],\n opts: { yes?: boolean; json?: boolean } = {},\n): void {\n const plan = planForget(db, names);\n if (plan.refused.length > 0) {\n const why = plan.refused\n .map((r) => `${r.name} (${r.why === \"live\" ? \"is live\" : \"was never torn down\"})`)\n .join(\", \");\n throw new UsageError(`cannot forget: ${why}. Only torn-down workstreams can be forgotten.`);\n }\n const ops = plan.candidates.reduce((n, c) => n + c.ops, 0);\n const bytes = plan.candidates.reduce((n, c) => n + c.bytes, 0);\n if (opts.yes !== true) {\n const nextSteps = [\n { intent: \"Forget them (NOT undoable)\", command: `mu db forget ${names.join(\" \")} --yes` },\n ];\n if (opts.json === true) {\n emitJson({ dryRun: true, candidates: plan.candidates, ops, bytes, nextSteps });\n return;\n }\n printForgetTable(plan);\n console.log(\n `${ops} ops (${formatBytes(bytes)} of payload). Forgetting deletes their history: mu undo can no longer restore these teardowns. Dry run; nothing changed.`,\n );\n printNextSteps(nextSteps);\n return;\n }\n const backup = backupBeside(db, \"forget\");\n const r = forget(db, plan);\n const size = vacuumAndCheck(db, backup);\n if (opts.json === true) {\n emitJson({\n dryRun: false,\n forgotten: plan.candidates.map((c) => c.name),\n ops: r.ops,\n backup,\n ...size,\n });\n return;\n }\n console.log(\n `Forgot ${plan.candidates.length} workstream(s), ${r.ops} ops: ${formatBytes(size.before)} → ${formatBytes(size.after)}. Drift check clean.`,\n );\n if (!size.checkpointed) console.log(pc.dim(CHECKPOINT_PENDING));\n console.log(pc.dim(`backup (the only way back): ${backup}`));\n}\n\n/** Doctor's hint: the largest forgettable workstreams, or undefined when\n * they are too small to be worth a line. */\nexport function forgetHint(\n db: Db,\n): { total: number; ops: number; bytes: number; top: string[] } | undefined {\n const all = listForgetCandidates(db);\n const bytes = all.reduce((n, c) => n + c.bytes, 0);\n if (bytes < FORGET_HINT_MIN_BYTES) return undefined;\n return {\n total: all.length,\n ops: all.reduce((n, c) => n + c.ops, 0),\n bytes,\n top: all.slice(0, 3).map((c) => c.name),\n };\n}\n\n/** Below this much torn-down history, doctor says nothing. */\nconst FORGET_HINT_MIN_BYTES = 5 * 1024 * 1024;\n\nexport function wireDbCommands(program: Command): void {\n const dbCmd = program.command(\"db\").description(\"Whole-DB file commands\");\n dbCmd\n .command(\"backup <file>\")\n .description(\n \"VACUUM INTO copy of the whole DB — the 'one file I can scp' convenience. Never overwrites. Real disaster recovery is `mu rebuild`.\",\n )\n .option(...JSON_OPT)\n .action(function (file: string) {\n const opts = (this as Command).opts() as { json?: boolean };\n return handle(async (db) => cmdDbBackup(db, file, opts), this as Command)();\n });\n dbCmd\n .command(\"compact\")\n .description(\n \"Shrink mu.db: blank note tombstones that repeat a put already in the log, then VACUUM. Dry run without --yes; --yes backs up beside the DB first and runs the drift check after. Local only; sync segments are untouched.\",\n )\n .option(\"--yes\", \"apply (default: dry run)\")\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as { yes?: boolean; json?: boolean };\n return handle(async (db) => cmdDbCompact(db, opts), this as Command)();\n });\n dbCmd\n .command(\"forget <workstreams...>\")\n .description(\n \"Delete every op of torn-down workstreams to shrink mu.db. NOT undoable: mu undo can no longer restore them. Dry run without --yes; --yes backs up beside the DB first, VACUUMs, and runs the drift check. List candidates: mu workstream list --torn-down.\",\n )\n .option(\"--yes\", \"apply (default: dry run)\")\n .option(...JSON_OPT)\n .action(function (names: string[]) {\n const opts = (this as Command).opts() as { yes?: boolean; json?: boolean };\n return handle(async (db) => cmdDbForget(db, names, opts), this as Command)();\n });\n}\n","// mu — keep mu.db slim: `mu db compact` and `mu db forget`.\n//\n// The ops log is append-only except for these two operator verbs. Both\n// rewrite history on THIS machine only and never touch sync segments:\n//\n// - compact: a note tombstone (`op='del'`) whose key also has a put in\n// the log carries a copy of that put's row. Undo folds the puts and\n// apply's delete reads the put, so the copy is dead weight; blank it\n// to `{}`. Capture stopped writing these copies (src/capture.ts\n// noteTombstonePayload); this applies the same rule to old rows.\n// - forget: delete every op of named, torn-down workstreams. Their rows\n// are already gone from the live tables, so rebuild and drift stay\n// consistent; what is lost is `mu undo` of that teardown, on purpose.\n//\n// Neither is reached by a trigger or a sync path. The CLI backs up the\n// DB first and runs the drift check after.\n\nimport type { Db } from \"./db.js\";\nimport { intentSpellings } from \"./legacy-ops.js\";\n\n/** Note tombstones whose payload is redundant with a put under the same key. */\nconst REDUNDANT_TOMBSTONES_SQL = `\n SELECT d.seq AS seq, length(d.payload) AS bytes\n FROM ops d\n WHERE d.entity = 'note' AND d.op = 'del' AND d.payload <> '{}'\n AND EXISTS (SELECT 1 FROM ops p\n WHERE p.entity = 'note' AND p.key = d.key AND p.op = 'put')`;\n\nexport interface CompactPlan {\n /** Note tombstones that would be blanked. */\n tombstones: number;\n /** Payload bytes those tombstones carry now. */\n bytes: number;\n}\n\nexport function planCompact(db: Db): CompactPlan {\n const r = db\n .prepare(\n `SELECT COUNT(*) AS n, COALESCE(SUM(bytes), 0) AS b FROM (${REDUNDANT_TOMBSTONES_SQL})`,\n )\n .get() as { n: number; b: number };\n return { tombstones: r.n, bytes: r.b };\n}\n\n/** Blank every redundant note tombstone, in one transaction. */\nexport function compact(db: Db): CompactPlan {\n const plan = planCompact(db);\n db.transaction(() => {\n db.prepare(\n `UPDATE ops SET payload = '{}' WHERE seq IN (SELECT seq FROM (${REDUNDANT_TOMBSTONES_SQL}))`,\n ).run();\n }).immediate();\n return plan;\n}\n\n/** The ops one workstream's history occupies: the workstream op itself,\n * and every op keyed under it (`<ws>/...`: tasks, notes, edges, agents,\n * workspaces, waves). */\nconst WORKSTREAM_OPS_WHERE = `(key = @ws OR substr(key, 1, length(@ws) + 1) = @ws || '/')`;\n\nexport interface ForgetCandidate {\n name: string;\n /** ISO time of its latest teardown. */\n tornDownAt: string;\n ops: number;\n /** Payload bytes of those ops (the on-disk share is about twice this,\n * with the row overhead and the four ops indexes). */\n bytes: number;\n}\n\n/** Why a name cannot be forgotten. */\nexport type ForgetRefusal = \"live\" | \"never-torn-down\";\n\nexport interface ForgetPlan {\n candidates: ForgetCandidate[];\n refused: { name: string; why: ForgetRefusal }[];\n}\n\n/** Every torn-down workstream that is not live again, largest first. */\nexport function listForgetCandidates(db: Db): ForgetCandidate[] {\n const spellings = intentSpellings(\"workstream.teardown\");\n const names = db\n .prepare(\n `SELECT key AS name, MAX(created_at) AS at\n FROM ops\n WHERE entity = 'workstream' AND op = 'del'\n AND intent IN (${spellings.map(() => \"?\").join(\", \")})\n AND key NOT IN (SELECT name FROM workstreams)\n GROUP BY key`,\n )\n .all(...spellings) as { name: string; at: string }[];\n const cost = db.prepare(\n `SELECT COUNT(*) AS n, COALESCE(SUM(length(payload)), 0) AS b FROM ops WHERE ${WORKSTREAM_OPS_WHERE}`,\n );\n return names\n .map((r) => {\n const c = cost.get({ ws: r.name }) as { n: number; b: number };\n return { name: r.name, tornDownAt: r.at, ops: c.n, bytes: c.b };\n })\n .sort((a, b) => b.bytes - a.bytes);\n}\n\nexport function planForget(db: Db, names: readonly string[]): ForgetPlan {\n const all = new Map(listForgetCandidates(db).map((c) => [c.name, c]));\n const live = new Set(\n (db.prepare(\"SELECT name FROM workstreams\").all() as { name: string }[]).map((r) => r.name),\n );\n const plan: ForgetPlan = { candidates: [], refused: [] };\n for (const name of new Set(names)) {\n const c = all.get(name);\n if (c) plan.candidates.push(c);\n else plan.refused.push({ name, why: live.has(name) ? \"live\" : \"never-torn-down\" });\n }\n return plan;\n}\n\n/** Delete every op of the plan's candidates, in one transaction. Not undoable. */\nexport function forget(db: Db, plan: ForgetPlan): { ops: number } {\n const del = db.prepare(`DELETE FROM ops WHERE ${WORKSTREAM_OPS_WHERE}`);\n let ops = 0;\n db.transaction(() => {\n for (const c of plan.candidates) ops += del.run({ ws: c.name }).changes;\n }).immediate();\n return { ops };\n}\n","// mu — disk↔DB reconciliation for `mu doctor`.\n//\n// Every other check in doctor reads the DB. These read the STATE DIR, and\n// then compare the two, because the two can disagree in both directions\n// and nothing surfaced either one:\n//\n// disk has, DB doesn't -> workspace orphan / empty parent / residue\n// DB has, disk doesn't -> a `vcs_workspaces` row pointing at nothing\n//\n// The second direction had NO surface at all before this module.\n// `mu workspace list` prints such a row as if it were fine, and every\n// spawn that reuses it fails deep in the VCS backend with a path error\n// rather than at the row that lied.\n//\n// REPORT ONLY, on purpose. Each finding names its own cleanup command in\n// the remediation block and mu runs none of them: an operator or an agent\n// reading doctor's output decides. A diagnostic verb that deletes 300MB\n// of checkouts because a readdir raced a spawn is a worse bug than the\n// residue it removes.\n//\n// TIERED like the drift check. The default tier is readdir + stat, depth\n// 2 (measured ~1ms on a 5-workstream / 5196-file state dir). Recursive\n// byte accounting is `--disk` only: its cost scales with the checkout,\n// not with mu's own state, so it must not ride a reflexively-run command.\n\nimport { readdirSync, statSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { type Db, defaultDbPath, defaultStateDir } from \"./db.js\";\nimport type { FleetHazard } from \"./fleet-hazards.js\";\nimport { listAllOrphanWorkspaces, listWorkspaces } from \"./workspace.js\";\n\n/** A held lock dir older than this is presumed abandoned. Mirrors\n * `DEFAULT_STALE_LOCK_MS` in src/file-lock.ts — that value governs\n * whether a lock is STOLEN when contended, this one whether it is\n * REPORTED when nobody is contending it, and a lock nobody contends is\n * never stolen. Deliberately much larger: a lock 30s old is routine\n * mid-spawn, whereas one an hour old outlived its process. */\nexport const STALE_LOCK_REPORT_MS = 60 * 60 * 1000;\n\n/** Human-readable byte count. Doctor rows are narrow, so no decimals\n * above the MB mark. */\nexport function formatBytes(bytes: number): string {\n if (bytes < 1024) return `${bytes}B`;\n if (bytes < 1024 * 1024) return `${Math.round(bytes / 1024)}K`;\n if (bytes < 1024 * 1024 * 1024) return `${Math.round(bytes / 1024 / 1024)}M`;\n return `${(bytes / 1024 / 1024 / 1024).toFixed(1)}G`;\n}\n\n/** Best-effort `readdir`: an unreadable or absent dir reads as empty, so\n * a fresh install with no state dir yet reports \"ok\" rather than\n * throwing out of a diagnostic. */\nfunction dirNames(path: string): string[] {\n try {\n return readdirSync(path, { withFileTypes: true })\n .filter((e) => e.isDirectory())\n .map((e) => e.name);\n } catch {\n return [];\n }\n}\n\nfunction exists(path: string): boolean {\n try {\n statSync(path);\n return true;\n } catch {\n return false;\n }\n}\n\nfunction sizeOf(path: string): number {\n try {\n return statSync(path).size;\n } catch {\n return 0;\n }\n}\n\n// ─── DB → disk: rows pointing at nothing ──────────────────────────────\n\nexport interface MissingWorkspaceDir {\n agentName: string;\n workstreamName: string;\n path: string;\n}\n\n/**\n * `vcs_workspaces` rows whose `path` is not on disk.\n *\n * The inverse of a workspace orphan, and the more dangerous half: an\n * orphan dir merely blocks the next `--workspace` spawn with a clear\n * \"path not empty\", while a row pointing at a deleted directory is\n * reported as a healthy workspace by every read surface mu has. The\n * usual cause is a hand-run `rm -rf` (or a `git worktree remove`) on a\n * path that `mu workspace free` would have unregistered.\n */\nexport function findMissingWorkspaceDirs(db: Db): MissingWorkspaceDir[] {\n return listWorkspaces(db)\n .filter((row) => !exists(row.path))\n .map((row) => ({\n agentName: row.agentName,\n workstreamName: row.workstreamName,\n path: row.path,\n }));\n}\n\nexport function checkMissingWorkspaceDirs(db: Db): FleetHazard {\n const missing = findMissingWorkspaceDirs(db);\n if (missing.length === 0) {\n return { name: \"ws-rows\", severity: \"ok\", detail: \"every workspace row has its dir\" };\n }\n return {\n name: \"ws-rows\",\n severity: \"warn\",\n detail: `${missing.length} workspace row(s) point at a path that is gone`,\n remediation: [\n \"These vcs_workspaces rows name a directory that no longer exists:\",\n ...missing.map((m) => ` ${m.workstreamName}/${m.agentName} ${m.path}`),\n \"\",\n \"mu reports such a row as a healthy workspace on every read surface, and\",\n \"the next send or refresh against it fails inside the VCS backend rather\",\n \"than at the row that lied. Unregister them:\",\n ...missing.map((m) => ` mu workspace free ${m.agentName} -w ${m.workstreamName}`),\n ],\n };\n}\n\n// ─── disk → DB: dirs with no row ──────────────────────────────────────\n\n/**\n * Workspace orphans, wired into doctor.\n *\n * `listAllOrphanWorkspaces` predates this module and was reachable only\n * from `mu workspace orphans` and the TUI card — so an operator running\n * `mu doctor` to answer \"is anything wrong\" was told nothing about\n * directories that will fail their next spawn. `stranded` rows (the\n * parent workstream's row is gone too) are counted separately because\n * they cannot be cleaned by any workstream-scoped verb.\n */\nexport function checkWorkspaceOrphanDirs(db: Db): FleetHazard {\n const orphans = listAllOrphanWorkspaces(db);\n if (orphans.length === 0) {\n return { name: \"ws-dirs\", severity: \"ok\", detail: \"no orphan workspace dirs\" };\n }\n const stranded = orphans.filter((o) => o.stranded);\n const strandedNote = stranded.length > 0 ? `, ${stranded.length} stranded` : \"\";\n return {\n name: \"ws-dirs\",\n severity: \"warn\",\n detail: `${orphans.length} workspace dir(s) with no DB row${strandedNote}`,\n remediation: [\n \"These directories have no row in vcs_workspaces:\",\n ...orphans.map((o) => ` ${o.path}${o.stranded ? \" (workstream row also gone)\" : \"\"}`),\n \"\",\n \"Each one blocks the next `--workspace` spawn for that agent name. mu will\",\n \"not remove them: they may hold uncommitted work, and a stranded dir is the\",\n \"only remaining copy of it. Inspect, then remove by hand (git checkouts:\",\n \"from the project root, so git also drops its worktree registration):\",\n \" mu workspace orphans --all\",\n ...orphans\n .slice(0, 3)\n .map(\n (o) =>\n ` (cd <project-root> && git worktree remove --force ${o.path}) || rm -rf ${o.path}`,\n ),\n ],\n };\n}\n\n/**\n * `<state-dir>/workspaces/<workstream>/` dirs with no children.\n *\n * Left behind by `mu workspace free`, which removes the agent dir and\n * its row but never the per-workstream parent. Harmless — it is\n * `severity: \"ok\"` for that reason — but reported because it is the\n * cheapest possible signal that a workstream is done with its\n * checkouts, and because an operator counting directories to work out\n * what mu still holds should not have to open each one.\n */\nexport function checkEmptyWorkstreamDirs(): FleetHazard {\n const root = join(defaultStateDir(), \"workspaces\");\n const empty = dirNames(root).filter((name) => dirNames(join(root, name)).length === 0);\n if (empty.length === 0) {\n return { name: \"ws-empty\", severity: \"ok\", detail: \"no empty workstream dirs\" };\n }\n return {\n name: \"ws-empty\",\n severity: \"ok\",\n detail: `${empty.length} empty workstream dir(s): ${empty.slice(0, 4).join(\", \")}`,\n remediation: [\n \"These per-workstream workspace dirs hold no checkouts:\",\n ...empty.map((name) => ` ${join(root, name)}`),\n \"\",\n \"`mu workspace free` removes an agent's dir and its row but not the parent,\",\n \"so this is normal residue rather than a fault. Remove if you want the\",\n \"state dir to read cleanly:\",\n ...empty.slice(0, 3).map((name) => ` rmdir ${join(root, name)}`),\n ],\n };\n}\n\n// ─── residue: files no DB row references ──────────────────────────────\n\nexport interface StrayFile {\n name: string;\n path: string;\n bytes: number;\n}\n\n/**\n * `mu.db.*` files in the state dir that are not the live WAL triple.\n *\n * Hand-made copies (`mu.db.old`), pre-bump saves (`mu.db.v9-<stamp>`),\n * the safety backups `mu db compact` / `mu db forget` write beside the\n * DB (`mu.db.pre-<verb>-<stamp>`, src/cli/db.ts) and abandoned `-wal` /\n * `-shm` sidecars. Nothing in mu reads them and nothing prunes them, and\n * they are the largest single category of dead bytes in a long-lived\n * state dir — 50MB on the box this check was written against.\n *\n * The live triple is excluded by exact name, so a `MU_DB_PATH` pointing\n * elsewhere simply reports the default-path copies it finds, which is\n * the honest answer.\n */\nexport function findStrayDbFiles(stateDir: string = defaultStateDir()): StrayFile[] {\n const live = new Set([\"mu.db\", \"mu.db-wal\", \"mu.db-shm\"]);\n let entries: string[];\n try {\n entries = readdirSync(stateDir, { withFileTypes: true })\n .filter((e) => e.isFile())\n .map((e) => e.name);\n } catch {\n return [];\n }\n return entries\n .filter((name) => name.startsWith(\"mu.db\") && !live.has(name))\n .map((name) => ({ name, path: join(stateDir, name), bytes: sizeOf(join(stateDir, name)) }))\n .sort((a, b) => b.bytes - a.bytes);\n}\n\nexport function checkStrayDbFiles(): FleetHazard {\n const stateDir = defaultStateDir();\n const stray = findStrayDbFiles(stateDir);\n if (stray.length === 0) {\n return { name: \"db-copies\", severity: \"ok\", detail: \"no stray DB copies\" };\n }\n const total = stray.reduce((n, f) => n + f.bytes, 0);\n return {\n name: \"db-copies\",\n severity: \"warn\",\n detail: `${stray.length} stray DB file(s), ${formatBytes(total)} — nothing reads these`,\n remediation: [\n `Files matching mu.db* in ${stateDir} that are not the live WAL triple:`,\n ...stray.map((f) => ` ${formatBytes(f.bytes).padStart(6)} ${f.name}`),\n \"\",\n `Live DB: ${defaultDbPath()}`,\n \"\",\n \"These are hand-made copies, pre-upgrade saves, and the backups\",\n \"`mu db compact` / `mu db forget` write first (mu.db.pre-<verb>-<time>).\",\n \"No mu code path reads them and none prunes them. Keep a pre-forget\",\n \"backup until you are sure: it is the only way back from a forget.\",\n \"Otherwise disaster recovery is the ops log, so a copy is a convenience:\",\n \" mu rebuild <file> # DR from the ops log, not from a copy\",\n \" mu db backup <file> # a fresh copy, if that is what you wanted\",\n ],\n };\n}\n\n/**\n * `<state-dir>/exports/` — residue of a verb that no longer exists.\n *\n * `mu workstream export` and its markdown bucket were deleted in 1.1.0.\n * The directory it wrote to was not, so every export any earlier version\n * ever made is still on disk with no surface in mu that names it. This\n * is the one finding here that is a defect rather than housekeeping:\n * mu removed the producer and left the output unreferenced.\n */\nexport function checkRemovedExportsDir(): FleetHazard {\n const root = join(defaultStateDir(), \"exports\");\n const entries = dirNames(root);\n if (entries.length === 0) {\n return { name: \"exports\", severity: \"ok\", detail: \"no leftover export dirs\" };\n }\n return {\n name: \"exports\",\n severity: \"warn\",\n detail: `${entries.length} export dir(s) from the removed \\`mu workstream export\\``,\n remediation: [\n `${root} holds ${entries.length} directory/ies.`,\n \"\",\n \"`mu workstream export` and its markdown bucket were removed in 1.1.0; this\",\n \"is output from a version that still had it. Nothing in mu reads or prunes\",\n \"it. Keep anything you still want, then:\",\n ` rm -rf ${root}`,\n ],\n };\n}\n\n/**\n * Lock dirs in `<state-dir>/locks/` older than STALE_LOCK_REPORT_MS.\n *\n * `withFileLock` steals a lock older than 30s, so a stale lock is not a\n * deadlock and this is not a `fail`. But it only steals when something\n * CONTENDS, and an uncontended lock dir survives forever — so an hour-old\n * lock is a crashed process's headstone, worth naming because it is\n * evidence of a spawn or flush that died mid-critical-section.\n */\nexport function checkStaleLocks(now: number = Date.now()): FleetHazard {\n const root = join(defaultStateDir(), \"locks\");\n const stale: { name: string; ageMs: number }[] = [];\n for (const name of dirNames(root)) {\n try {\n const ageMs = now - statSync(join(root, name)).mtimeMs;\n if (ageMs > STALE_LOCK_REPORT_MS) stale.push({ name, ageMs });\n } catch {\n // Vanished between readdir and stat: released, which is the\n // outcome we wanted anyway.\n }\n }\n if (stale.length === 0) {\n return { name: \"locks\", severity: \"ok\", detail: \"no stale lock dirs\" };\n }\n return {\n name: \"locks\",\n severity: \"warn\",\n detail: `${stale.length} lock dir(s) older than 1h`,\n remediation: [\n \"These advisory-lock dirs outlived the process that took them:\",\n ...stale.map((s) => ` ${s.name} (${Math.round(s.ageMs / 60000)}m old)`),\n \"\",\n \"Not a deadlock: withFileLock steals a lock older than 30s. But it only\",\n \"steals under contention, so these will sit here forever. They are evidence\",\n \"of a spawn or segment flush that died mid-critical-section.\",\n ` rm -rf ${root}/<name>`,\n ],\n };\n}\n\n// ─── --disk tier: recursive byte accounting ───────────────────────────\n\nexport interface WorkspaceUsage {\n workstreamName: string;\n agentName: string;\n path: string;\n bytes: number;\n /** True iff no `vcs_workspaces` row references this path — the bytes\n * are reclaimable without freeing anything mu still tracks. */\n orphan: boolean;\n}\n\n/** Recursive byte sum. Symlinks are skipped (0 bytes, never followed):\n * a Dirent for a symlink is neither a file nor a directory, so a\n * workspace symlinked into a huge tree does not report that tree's\n * bytes as mu's. */\nfunction walkBytes(path: string): number {\n let total = 0;\n let entries: import(\"node:fs\").Dirent[];\n try {\n entries = readdirSync(path, { withFileTypes: true });\n } catch {\n return 0;\n }\n for (const entry of entries) {\n const child = join(path, entry.name);\n if (entry.isDirectory()) total += walkBytes(child);\n else if (entry.isFile()) total += sizeOf(child);\n }\n return total;\n}\n\n/**\n * Per-workspace disk usage, `--disk` tier only.\n *\n * Cost scales with the size of the CHECKOUTS, not with mu's own state\n * (measured 0.25s / 574MB / 5196 files), which is why it is not in the\n * default tier: a monorepo workspace would make `mu doctor` slow enough\n * that people stop running it, and a diagnostic nobody runs reports\n * nothing.\n */\nexport function measureWorkspaceUsage(db: Db): WorkspaceUsage[] {\n const root = join(defaultStateDir(), \"workspaces\");\n const registered = new Set(listWorkspaces(db).map((w) => w.path));\n const usage: WorkspaceUsage[] = [];\n for (const wsName of dirNames(root)) {\n const wsRoot = join(root, wsName);\n for (const agentName of dirNames(wsRoot)) {\n const path = join(wsRoot, agentName);\n usage.push({\n workstreamName: wsName,\n agentName,\n path,\n bytes: walkBytes(path),\n orphan: !registered.has(path),\n });\n }\n }\n return usage.sort((a, b) => b.bytes - a.bytes);\n}\n\n// ─── the aggregate ────────────────────────────────────────────────────\n\n/**\n * Every disk↔DB check, in display order: the two reconciliation\n * directions first (those are inconsistencies), then residue.\n *\n * Cheap enough for the default doctor: one readdir of the state dir,\n * a depth-2 readdir of `workspaces/`, one `stat` per workspace row and\n * per lock dir.\n */\nexport function checkDiskRecon(db: Db): FleetHazard[] {\n return [\n checkMissingWorkspaceDirs(db),\n checkWorkspaceOrphanDirs(db),\n checkEmptyWorkstreamDirs(),\n checkStrayDbFiles(),\n checkRemovedExportsDir(),\n checkStaleLocks(),\n ];\n}\n","// mu — `mu doctor` diagnostic verb (human + --json forms).\n//\n// Reports:\n// - environment: the active mux + its ambient env facts, $MU_SESSION\n// - db: schema integrity, schema_version, journal_mode, foreign_keys\n// - workstream: auto-detected current workstream\n// - state: per-workstream agent / task / log counts + reconcile drift\n// - disk: state-dir vs DB reconciliation (both directions) + residue\n//\n// Read-only (the reconcile pass uses mode: \"report-only\" so polling doesn't\n// race in-flight spawns; see bug_agent_spawn_workspace_fk_failure).\n//\n// Extracted from src/cli.ts as part of refactor_split_large_src_files.\n\nimport { dirname } from \"node:path\";\nimport { listAgents, listLiveAgents } from \"../agents.js\";\nimport { emitJson, resolveWorkstream } from \"../cli.js\";\nimport { planCompact } from \"../compact.js\";\nimport { CURRENT_SCHEMA_VERSION, type Db, defaultDbPath, EXPECTED_TABLES } from \"../db.js\";\nimport { checkDiskRecon, formatBytes, measureWorkspaceUsage } from \"../disk-recon.js\";\nimport {\n ctlExtensionDoctorCheck,\n ctlSocketsDoctorCheck,\n type DoctorCheck,\n murmurDoctorCheck,\n skillDoctorCheck,\n} from \"../doctor-summary.js\";\nimport {\n ABANDONED_IDLE_DAYS,\n checkDormantWorkstreams,\n FINISHED_IDLE_DAYS,\n findDormantWorkstreams,\n} from \"../dormant.js\";\nimport {\n checkCheapDriftInvariant,\n checkDrift,\n DriftDetectedError,\n driftRemediation,\n formatDriftRecord,\n} from \"../drift.js\";\nimport { checkFleetHazards, type FleetHazard, HazardFailError } from \"../fleet-hazards.js\";\nimport { activeMux, type MuxHealth } from \"../mux.js\";\nimport { pc } from \"../output.js\";\nimport { summarizeWorkstream } from \"../workstream.js\";\nimport { forgetHint } from \"./db.js\";\n\n/** Column width for the `label : value` environment block. Wide enough\n * for the longest label any backend contributes — `$HERDR_WORKSPACE_ID`\n * at 19 — so the colons stay in one column on every mux. */\nconst LABEL_WIDTH = 19;\nconst pad = (s: string): string => s.padEnd(LABEL_WIDTH);\n\n/** Where agent state comes from: herdr on herdr, murmur otherwise. A\n * linked mu extension makes murmur optional for pi agents. */\nfunction agentStateCheck(health: MuxHealth | undefined, muExt: DoctorCheck): DoctorCheck {\n return murmurDoctorCheck(health?.name === \"herdr\" ? \"herdr\" : \"murmur\", {\n muExtOk: muExt.status === \"ok\",\n });\n}\n\nfunction printCheck(label: string, check: DoctorCheck): void {\n const colour = check.status === \"ok\" ? pc.green : check.status === \"warn\" ? pc.yellow : pc.red;\n const word = check.status === \"ok\" ? \"ok\" : check.status.toUpperCase();\n console.log(` ${pad(label)}: ${colour(word)} ${pc.dim(check.detail)}`);\n}\n\n/**\n * Health of the active mux, or undefined when NO backend resolves.\n * Never throws: doctor's whole job is reporting a broken substrate,\n * so `NoMultiplexerError` here is a finding, not a failure.\n */\nasync function muxHealth(): Promise<MuxHealth | undefined> {\n try {\n return await (await activeMux()).healthCheck();\n } catch {\n return undefined;\n }\n}\n\n/** Render a hazard list as doctor rows plus a remediation block per\n * non-ok finding. Shared by the fleet and disk sections, which differ\n * only in what they check. Returns true iff anything needs attention. */\nfunction printHazards(hazards: readonly FleetHazard[]): boolean {\n let sawProblem = false;\n for (const hazard of hazards) {\n const colour =\n hazard.severity === \"fail\" ? pc.red : hazard.severity === \"warn\" ? pc.yellow : pc.green;\n const label = hazard.severity === \"ok\" ? \"ok\" : hazard.severity.toUpperCase();\n console.log(` ${hazard.name.padEnd(16)} : ${colour(label)} ${pc.dim(hazard.detail)}`);\n if (hazard.severity !== \"ok\") sawProblem = true;\n }\n for (const hazard of hazards) {\n if (hazard.severity === \"ok\" || hazard.remediation === undefined) continue;\n console.log(\"\");\n for (const line of hazard.remediation) console.log(` ${line}`);\n }\n return sawProblem;\n}\n\nexport async function cmdDoctor(\n db: Db,\n opts: { json?: boolean; deep?: boolean; disk?: boolean } = {},\n): Promise<void> {\n if (opts.json) {\n return cmdDoctorJson(db, opts);\n }\n console.log(pc.bold(\"mu doctor\"));\n\n // ─ Environment\n //\n // The backend reports DATA (name / version / its own env facts);\n // doctor owns every string below. A second mux with different\n // ambient vars needs no change here.\n console.log(pc.bold(\"\\nenvironment\"));\n const health = await muxHealth();\n if (health === undefined) {\n console.log(` multiplexer : ${pc.red(\"NONE\")} — install tmux ≥ 3.0`);\n } else {\n const label = pad(health.name);\n if (health.ok) console.log(` ${label}: ${pc.green(\"ok\")} (${health.version ?? \"?\"})`);\n else console.log(` ${label}: ${pc.red(\"NOT FOUND\")} — ${health.remediation}`);\n for (const fact of health.env) {\n console.log(` ${pad(fact.name)}: ${fact.value ? pc.green(fact.value) : pc.dim(\"not set\")}`);\n }\n }\n console.log(\n ` ${pad(\"$MU_SESSION\")}: ${process.env.MU_SESSION ? pc.green(process.env.MU_SESSION) : pc.dim(\"not set\")}`,\n );\n const muExt = ctlExtensionDoctorCheck();\n printCheck(\"agent state\", agentStateCheck(health, muExt));\n printCheck(\"mu ext\", muExt);\n printCheck(\"mu skill\", skillDoctorCheck());\n printCheck(\n \"ctl\",\n (await ctlSocketsDoctorCheck(listAgents(db), { stateDir: dirname(db.name) })).check,\n );\n\n // ─ DB + schema\n console.log(pc.bold(\"\\ndb\"));\n console.log(` path : ${pc.dim(defaultDbPath())}`);\n try {\n const tables = (\n db\n .prepare(\n \"SELECT name FROM sqlite_master WHERE type='table' AND name NOT LIKE 'sqlite_%' ORDER BY name\",\n )\n .all() as { name: string }[]\n ).map((r) => r.name);\n const missing = EXPECTED_TABLES.filter((t) => !tables.includes(t));\n if (missing.length === 0) {\n console.log(` schema : ${pc.green(\"ok\")} (${EXPECTED_TABLES.length} tables)`);\n } else {\n console.log(` schema : ${pc.red(\"missing\")} — ${missing.join(\", \")}`);\n }\n // Schema version: openDb refuses any DB older or newer than\n // CURRENT_SCHEMA_VERSION (SchemaTooOldError / SchemaTooNewError,\n // exit 4; there is no migration ladder). A mismatch here means the\n // row changed after open, e.g. an external SQLite client.\n try {\n const row = db.prepare(\"SELECT version FROM schema_version WHERE id = 1\").get() as\n | { version: number }\n | undefined;\n const v = row?.version;\n if (v === undefined) {\n console.log(\n ` schema_version : ${pc.red(\"missing row\")} (expected ${CURRENT_SCHEMA_VERSION})`,\n );\n } else if (v === CURRENT_SCHEMA_VERSION) {\n console.log(` schema_version : ${pc.green(String(v))}`);\n } else if (v < CURRENT_SCHEMA_VERSION) {\n console.log(\n ` schema_version : ${pc.yellow(String(v))} (code expects ${CURRENT_SCHEMA_VERSION}; openDb refuses older DBs, so the row changed after open)`,\n );\n } else {\n console.log(\n ` schema_version : ${pc.red(String(v))} (code expects ${CURRENT_SCHEMA_VERSION}; possible downgrade or future-version DB)`,\n );\n }\n } catch {\n console.log(\n ` schema_version : ${pc.red(\"unreadable\")} (schema_version table missing or wrong shape)`,\n );\n }\n const journal = db.pragma(\"journal_mode\", { simple: true });\n console.log(\n ` journal_mode : ${journal === \"wal\" ? pc.green(String(journal)) : pc.yellow(String(journal))}`,\n );\n const fk = db.pragma(\"foreign_keys\", { simple: true });\n console.log(` foreign_keys : ${fk === 1 ? pc.green(\"on\") : pc.red(`off (${fk})`)}`);\n } catch (err) {\n console.log(\n ` schema : ${pc.red(\"FAIL\")} — ${err instanceof Error ? err.message : err}`,\n );\n }\n\n // ─ Workstream auto-detect\n console.log(pc.bold(\"\\nworkstream\"));\n let currentWorkstream: string | null = null;\n try {\n currentWorkstream = await resolveWorkstream();\n console.log(` current : ${pc.green(currentWorkstream)}`);\n } catch {\n console.log(\n ` current : ${pc.yellow(\"none\")} (set $MU_SESSION, cd into an mu-<name> mux session, or pass -w to a subcommand)`,\n );\n }\n\n // ─ Per-workstream stats (current only; --all stretch)\n if (currentWorkstream) {\n const ws = currentWorkstream;\n console.log(pc.bold(`\\nstate (workstream=${ws})`));\n const summary = await summarizeWorkstream(db, { workstream: ws });\n const counts = {\n agents: summary.agentCount,\n tasks: summary.taskCount,\n ready: countReady(db, ws),\n blocked: countBlocked(db, ws),\n inProgress: countInProgressByWorkstream(db, ws),\n logs: countLogsByWorkstream(db, ws),\n };\n console.log(` agents : ${counts.agents}`);\n console.log(\n ` tasks : ${counts.tasks} (ready ${counts.ready}, blocked ${counts.blocked}, in-progress ${counts.inProgress})`,\n );\n console.log(` ops rows : ${counts.logs}`);\n\n // Reconciliation: ghost detection (DB rows with dead panes) + orphans.\n // mu doctor is diagnostic — mode: \"report-only\" so it never\n // deletes rows AND never writes to the DB / tmux titles just for\n // being polled (would race in-flight spawns; see\n // bug_agent_spawn_workspace_fk_failure).\n try {\n const view = await listLiveAgents(db, { workstream: ws, mode: \"report-only\" });\n const ghosts = view.report.prunedGhosts;\n const ghostNote =\n ghosts > 0\n ? pc.yellow(\n `${ghosts} ghost pane${ghosts === 1 ? \"\" : \"s\"} would be reaped by \\`mu state\\` or \\`mu agent list\\``,\n )\n : pc.green(\"none\");\n console.log(` ghosts : ${ghostNote}`);\n const orphanColor = view.orphans.length > 0 ? pc.yellow : pc.green;\n console.log(\n ` orphan panes : ${orphanColor(String(view.orphans.length))}${view.orphans.length > 0 ? pc.dim(\" (run `mu agent list` to see them)\") : \"\"}`,\n );\n } catch (err) {\n console.log(\n ` reconcile : ${pc.dim(\"skipped\")} (${err instanceof Error ? err.message : err})`,\n );\n }\n }\n\n // ─ Mixed-fleet hazards (cheap: two path compares, one statfs, one scan)\n //\n // These run in the DEFAULT doctor because they are cheap AND\n // PREVENTABLE — each one is a condition the operator can fix before it\n // costs them data, unlike drift which is a bug report.\n console.log(pc.bold(\"\\nfleet\"));\n const fleet = checkFleetHazards(db, { dbPath: defaultDbPath() });\n let sawHazard = printHazards(fleet);\n\n // ─ Housekeeping: workstreams that look torn-down-able\n //\n // Deliberately its own section rather than a `fleet` row: fleet is\n // about a MIXED FLEET corrupting itself, and this is about a single\n // box accumulating finished work. Severity is always `ok`, so this\n // never contributes to `sawHazard` — a tidy-up opportunity is not a\n // fault, and treating it as one would make doctor cry wolf forever.\n console.log(pc.bold(\"\\nhousekeeping\"));\n const dormant = checkDormantWorkstreams(db, { currentWorkstream });\n console.log(\n ` ${dormant.name.padEnd(16)} : ${dormant.severity === \"ok\" && dormant.remediation === undefined ? pc.green(\"ok\") : pc.yellow(\"note\")} ${pc.dim(dormant.detail)}`,\n );\n // Printed directly rather than through `printHazards`, which shows a\n // remediation block only for non-`ok` findings. This finding is\n // deliberately `ok` AND has the names — which are the entire point of\n // the row — in its remediation, so routing it through that helper\n // would report a count and withhold the list.\n if (dormant.remediation !== undefined) {\n console.log(\"\");\n for (const line of dormant.remediation) console.log(` ${line}`);\n }\n\n // ─ Disk ↔ DB reconciliation\n //\n // The only section that reads the filesystem. Default tier is readdir\n // + stat (~1ms); recursive byte accounting is --disk, because its cost\n // scales with the checkouts rather than with mu's state.\n console.log(pc.bold(\"\\ndisk\"));\n const disk = checkDiskRecon(db);\n if (printHazards(disk)) sawHazard = true;\n if (opts.disk === true) {\n const usage = measureWorkspaceUsage(db);\n const total = usage.reduce((n, u) => n + u.bytes, 0);\n const reclaimable = usage.filter((u) => u.orphan).reduce((n, u) => n + u.bytes, 0);\n console.log(\n `\\n ${\"workspace bytes\".padEnd(16)} : ${formatBytes(total)} across ${usage.length} checkout(s)${\n reclaimable > 0 ? pc.yellow(` — ${formatBytes(reclaimable)} in orphan dirs`) : \"\"\n }`,\n );\n for (const u of usage) {\n const tag = u.orphan ? pc.yellow(\" orphan\") : \"\";\n console.log(\n ` ${formatBytes(u.bytes).padStart(6)} ${u.workstreamName}/${u.agentName}${tag}`,\n );\n }\n } else {\n console.log(\n pc.dim(\" (run `mu doctor --disk` for per-workspace byte usage — walks every checkout)\"),\n );\n }\n\n // ─ Ops-log drift\n //\n // TIERED ON PURPOSE. The full rebuild-and-diff is ~0.6ms per op\n // (measured: 2.2s on a 1000-task / 3461-op DB), which is too slow to\n // put in a reflexively-run command. So the default runs a ~1ms\n // invariant and points at --deep; --deep runs the real thing.\n console.log(pc.bold(\"\\nops log\"));\n if (opts.deep === true) {\n const report = checkDrift(db);\n const compared = Object.entries(report.rowsCompared)\n .map(([t, n]) => `${n} ${t}`)\n .join(\", \");\n if (report.clean) {\n console.log(\n ` drift : ${pc.green(\"ok\")} ${pc.dim(`rebuild matches live tables (${compared}, ${report.elapsedMs}ms)`)}`,\n );\n } else {\n console.log(\n ` drift : ${pc.red(\"FAIL\")} ${report.totalDrift} divergence(s) ${pc.dim(`(${report.elapsedMs}ms)`)}`,\n );\n for (const record of report.records) console.log(` ${formatDriftRecord(record)}`);\n if (report.totalDrift > report.records.length) {\n console.log(pc.dim(` … and ${report.totalDrift - report.records.length} more`));\n }\n console.log(\"\");\n for (const line of driftRemediation()) console.log(` ${line}`);\n // Non-zero exit so CI and wrapper scripts notice. Thrown last so\n // the whole report is printed first.\n throw new DriftDetectedError(report.totalDrift, report.records);\n }\n } else {\n const cheap = checkCheapDriftInvariant(db);\n if (cheap.clean) {\n console.log(\n ` drift (shallow) : ${pc.green(\"ok\")} ${pc.dim(`every live row has ops (${cheap.elapsedMs}ms) — run \\`mu doctor --deep\\` for the full rebuild diff`)}`,\n );\n } else {\n console.log(\n ` drift (shallow) : ${pc.red(\"FAIL\")} ${cheap.totalUnexplained} row(s) with NO ops explaining their existence`,\n );\n for (const row of cheap.unexplainedRows) {\n console.log(` ${row.table} ${row.key}: no op names this key`);\n }\n console.log(pc.dim(\" capture missed these rows entirely. Run `mu doctor --deep`.\"));\n console.log(\"\");\n for (const line of driftRemediation()) console.log(` ${line}`);\n throw new DriftDetectedError(cheap.totalUnexplained, []);\n }\n }\n const size = opsSizeHint(db);\n if (size) {\n console.log(` size : ${pc.yellow(\"hint\")} ${size.line}`);\n for (const c of size.commands) console.log(pc.dim(` ${c}`));\n }\n if (sawHazard) {\n console.log(\n pc.dim(\"\\nSee the fleet / disk sections above: at least one finding needs attention.\"),\n );\n }\n // A `fail` row (today: the DB inside MU_SYNC_DIR) is a hard failure,\n // not a hint, so it exits non-zero like drift. Thrown last so the\n // whole report is printed first.\n const failed = failedHazardNames([...fleet, ...disk]);\n if (failed.length > 0) throw new HazardFailError(failed);\n}\n\n/** Names of the `fail`-severity rows, the ones that make doctor exit 5. */\nfunction failedHazardNames(hazards: readonly { name: string; severity: string }[]): string[] {\n return hazards.filter((h) => h.severity === \"fail\").map((h) => h.name);\n}\n\n/** The ops-log size hint: torn-down history worth forgetting, largest\n * first, and redundant tombstones worth compacting. Undefined when\n * neither is worth a line. */\nfunction opsSizeHint(db: Db): { line: string; commands: string[] } | undefined {\n const forgettable = forgetHint(db);\n const tomb = planCompact(db);\n const parts: string[] = [];\n const commands: string[] = [];\n if (forgettable) {\n parts.push(\n `${forgettable.total} torn-down workstreams hold ${forgettable.ops} ops (${formatBytes(forgettable.bytes)}); largest: ${forgettable.top.join(\", \")}`,\n );\n commands.push(\n \"see them: mu workstream list --torn-down\",\n `forget some: mu db forget ${forgettable.top.join(\" \")}`,\n );\n }\n if (tomb.bytes >= 1024 * 1024) {\n parts.push(`${tomb.tombstones} redundant note tombstones (${formatBytes(tomb.bytes)})`);\n commands.push(\"compact: mu db compact\");\n }\n return parts.length === 0 ? undefined : { line: parts.join(\"; \"), commands };\n}\n\n/**\n * JSON form of `mu doctor`. Same checks the human form runs, collected\n * into a single structured record for piping. Surfaces 'ok' / 'warn' /\n * 'fail' for each subsystem so callers can match on a single field.\n */\nexport async function cmdDoctorJson(\n db: Db,\n opts: { deep?: boolean; disk?: boolean } = {},\n): Promise<void> {\n // environment\n const health = await muxHealth();\n const muExt = ctlExtensionDoctorCheck();\n const ctlSockets = await ctlSocketsDoctorCheck(listAgents(db), { stateDir: dirname(db.name) });\n const env = {\n // `mux` is the backend-agnostic key. `tmux` is kept as an alias for\n // back-compat with scripts that grew around the pre-MuxBackend\n // shape; it reports the ACTIVE backend, whatever it is.\n mux: health ?? { name: null, ok: false, version: null },\n tmux: { ok: health?.ok ?? false, version: health?.version ?? null },\n ...Object.fromEntries(health?.env.map((f) => [f.name.replace(/^\\$/, \"\"), f.value]) ?? []),\n MU_SESSION: process.env.MU_SESSION ?? null,\n agentState: agentStateCheck(health, muExt),\n ctl: { extension: muExt, sockets: ctlSockets.check, agents: ctlSockets.agents },\n skill: skillDoctorCheck(),\n };\n\n // db / schema\n let dbReport: Record<string, unknown>;\n try {\n const tables = (\n db\n .prepare(\n \"SELECT name FROM sqlite_master WHERE type='table' AND name NOT LIKE 'sqlite_%' ORDER BY name\",\n )\n .all() as { name: string }[]\n ).map((r) => r.name);\n const missing = EXPECTED_TABLES.filter((t) => !tables.includes(t));\n let schemaVersion: number | null = null;\n let schemaVersionStatus: \"ok\" | \"missing\" | \"stale\" | \"future\" | \"unreadable\";\n try {\n const row = db.prepare(\"SELECT version FROM schema_version WHERE id = 1\").get() as\n | { version: number }\n | undefined;\n const v = row?.version;\n if (v === undefined) schemaVersionStatus = \"missing\";\n else {\n schemaVersion = v;\n if (v === CURRENT_SCHEMA_VERSION) schemaVersionStatus = \"ok\";\n else if (v < CURRENT_SCHEMA_VERSION) schemaVersionStatus = \"stale\";\n else schemaVersionStatus = \"future\";\n }\n } catch {\n schemaVersionStatus = \"unreadable\";\n }\n const journal = db.pragma(\"journal_mode\", { simple: true });\n const fk = db.pragma(\"foreign_keys\", { simple: true });\n dbReport = {\n path: defaultDbPath(),\n schema: { ok: missing.length === 0, expected: EXPECTED_TABLES, missing, present: tables },\n schemaVersion: {\n value: schemaVersion,\n expected: CURRENT_SCHEMA_VERSION,\n status: schemaVersionStatus,\n },\n journalMode: journal,\n foreignKeys: fk === 1,\n };\n } catch (err) {\n dbReport = { error: err instanceof Error ? err.message : String(err) };\n }\n\n // workstream\n let currentWorkstream: string | null = null;\n try {\n currentWorkstream = await resolveWorkstream();\n } catch {\n currentWorkstream = null;\n }\n\n // per-workstream stats (only when resolvable)\n let workstreamStats: Record<string, unknown> | null = null;\n if (currentWorkstream) {\n const ws = currentWorkstream;\n const summary = await summarizeWorkstream(db, { workstream: ws });\n const counts = {\n agents: summary.agentCount,\n tasks: summary.taskCount,\n ready: countReady(db, ws),\n blocked: countBlocked(db, ws),\n inProgress: countInProgressByWorkstream(db, ws),\n logs: countLogsByWorkstream(db, ws),\n };\n let reconcile: Record<string, unknown> | null = null;\n try {\n // mu doctor --json: report-only for the same reason as the human path.\n const view = await listLiveAgents(db, { workstream: ws, mode: \"report-only\" });\n reconcile = {\n prunedGhosts: view.report.prunedGhosts,\n orphanCount: view.orphans.length,\n };\n } catch (err) {\n reconcile = { skipped: true, reason: err instanceof Error ? err.message : String(err) };\n }\n workstreamStats = { workstreamName: ws, ...counts, reconcile };\n }\n\n // Mixed-fleet hazards: same three checks the human path runs.\n const hazards = checkFleetHazards(db, { dbPath: defaultDbPath() }).map((h) => ({\n name: h.name,\n severity: h.severity,\n detail: h.detail,\n }));\n\n // Disk ↔ DB: same checks as the human path. Remediation lines ride\n // along here (unlike `fleet`, which drops them) because the whole\n // point of the section is that an agent reading --json can act on it.\n const disk = checkDiskRecon(db).map((h) => ({\n name: h.name,\n severity: h.severity,\n detail: h.detail,\n remediation: h.remediation ?? [],\n }));\n\n // Housekeeping: the dormant list, with its rows STRUCTURED rather\n // than only prose. An agent reading --json should be able to pick a\n // name without parsing the remediation block, and the `kind` field is\n // the whole finding — `finished` is safe to tear down, `abandoned`\n // needs a look first.\n const dormantHazard = checkDormantWorkstreams(db, { currentWorkstream });\n const housekeeping = {\n dormantWorkstreams: {\n name: dormantHazard.name,\n severity: dormantHazard.severity,\n detail: dormantHazard.detail,\n remediation: dormantHazard.remediation ?? [],\n workstreams: findDormantWorkstreams(db, { currentWorkstream }),\n thresholds: { finishedIdleDays: FINISHED_IDLE_DAYS, abandonedIdleDays: ABANDONED_IDLE_DAYS },\n },\n };\n const workspaceUsage = opts.disk === true ? measureWorkspaceUsage(db) : null;\n\n // Drift: shallow by default, full rebuild diff under --deep. Same\n // tiering as the human path, for the same measured reason.\n let drift: Record<string, unknown>;\n let driftFailure: DriftDetectedError | null = null;\n if (opts.deep === true) {\n const report = checkDrift(db);\n drift = {\n mode: \"deep\",\n ok: report.clean,\n totalDrift: report.totalDrift,\n records: report.records,\n rowsCompared: report.rowsCompared,\n elapsedMs: report.elapsedMs,\n };\n if (!report.clean) driftFailure = new DriftDetectedError(report.totalDrift, report.records);\n } else {\n const cheap = checkCheapDriftInvariant(db);\n drift = {\n mode: \"shallow\",\n ok: cheap.clean,\n totalUnexplained: cheap.totalUnexplained,\n unexplainedRows: cheap.unexplainedRows,\n elapsedMs: cheap.elapsedMs,\n hint: \"run `mu doctor --deep --json` for the full rebuild diff\",\n };\n if (!cheap.clean) driftFailure = new DriftDetectedError(cheap.totalUnexplained, []);\n }\n\n emitJson({\n environment: env,\n db: dbReport,\n workstream: { currentName: currentWorkstream },\n state: workstreamStats,\n fleet: hazards,\n housekeeping,\n disk,\n workspaceUsage,\n drift,\n size: opsSizeHint(db) ?? null,\n remediation: drift.ok === true ? [] : driftRemediation(),\n });\n // Emit the payload FIRST, then fail: a --json consumer needs the\n // machine-readable report even when the exit code is non-zero.\n if (driftFailure !== null) throw driftFailure;\n const failed = failedHazardNames([...hazards, ...disk]);\n if (failed.length > 0) throw new HazardFailError(failed);\n}\n\n// agents/tasks counts come from summarizeWorkstream() (src/workstream.ts) —\n// it already runs the same JOIN-on-workstreams SELECTs for its summary, so\n// we don't keep a second copy of those queries here. The four helpers below\n// (in-progress / logs / ready / blocked) are doctor-only views that\n// summarizeWorkstream doesn't expose.\nfunction countInProgressByWorkstream(db: Db, workstream: string): number {\n return (\n db\n .prepare(\n `SELECT COUNT(*) AS n FROM tasks t\n JOIN workstreams ws ON ws.id = t.workstream_id\n WHERE ws.name = ? AND t.status = 'IN_PROGRESS'`,\n )\n .get(workstream) as { n: number }\n ).n;\n}\nfunction countLogsByWorkstream(db: Db, workstream: string): number {\n return (\n db\n .prepare(\n // ops.key is the natural key ('' = machine-wide), so no join.\n // The workstream's own ops have key = <ws>; its tasks, notes and\n // edges all start with '<ws>/' (src/capture.ts § Natural keys).\n // A range, not LIKE: '_' in a workstream name is a LIKE wildcard,\n // and '0' is the byte after '/'.\n \"SELECT COUNT(*) AS n FROM ops WHERE key = ? OR (key >= ? AND key < ?)\",\n )\n .get(workstream, `${workstream}/`, `${workstream}0`) as { n: number }\n ).n;\n}\nfunction countReady(db: Db, workstream: string): number {\n return (\n db\n .prepare(\n `SELECT COUNT(*) AS n FROM ready v\n JOIN workstreams ws ON ws.id = v.workstream_id\n WHERE ws.name = ?`,\n )\n .get(workstream) as { n: number }\n ).n;\n}\nfunction countBlocked(db: Db, workstream: string): number {\n return (\n db\n .prepare(\n `SELECT COUNT(*) AS n FROM blocked v\n JOIN workstreams ws ON ws.id = v.workstream_id\n WHERE ws.name = ?`,\n )\n .get(workstream) as { n: number }\n ).n;\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n//\n// wireDoctorCommand is called by buildProgram() in src/cli.ts. Wired here so\n// every per-namespace builder lives next to its cmd functions.\n\nimport type { Command } from \"commander\";\nimport { handle, JSON_OPT } from \"../cli.js\";\n\nexport function wireDoctorCommand(program: Command): void {\n program\n .command(\"doctor\")\n .description(\"Environment + state health check\")\n .option(...JSON_OPT)\n .option(\n \"--deep\",\n \"also rebuild the ops log into a temp DB and diff it against the live tables (slower: ~0.6ms per op)\",\n )\n .option(\n \"--disk\",\n \"also measure per-workspace disk usage (walks every checkout; the disk↔DB reconciliation itself always runs)\",\n )\n .action(function () {\n const opts = (this as Command).opts() as { json?: boolean; deep?: boolean; disk?: boolean };\n return handle((db) => cmdDoctor(db, opts), this as Command)();\n });\n}\n","// mu — dormant-workstream detection for `mu doctor`.\n//\n// The question this answers: \"which workstreams can I tear down?\" The\n// operator had to answer it by eye, from `mu workstream list`, which\n// prints row counts and no dates — so the two workstreams that had been\n// untouched for three months looked exactly like the one worked on an\n// hour ago. Teardown is reversible (tombstone ops + `mu undo`), so the\n// cost of the missing surface was not risk, it was that nobody ever\n// tore anything down and the list grew forever.\n//\n// TWO BUCKETS, NEVER ONE NUMBER\n// -----------------------------\n// \"Stale-ish and/or no open tasks\" is two different findings and\n// merging them gives actively bad advice:\n//\n// FINISHED every task CLOSED, and idle a while. Nothing is at\n// stake. Safe to tear down, and that is what the\n// remediation says.\n// ABANDONED idle for a long time WITH unclosed tasks. Tearing this\n// down discards open work. The remediation is to LOOK\n// first, and the count of what would be lost is the whole\n// point of the row.\n//\n// On the box this was written against the split is the entire value:\n// `mu` / `dash-search` / `dash-shortcuts` / `goto-murmur-dash` are\n// finished (0 unclosed), while `infer-rs` (95 days, 19 unclosed) and\n// `modelbridge` (89 days, 8 unclosed) are abandoned. One combined\n// \"dormant\" list would have invited `--empty`-style sweeping of 27 open\n// tasks.\n//\n// WHY NOT `teardown --empty`\n// --------------------------\n// That verb already exists and is deliberately narrower: ZERO tasks,\n// agents and workspaces — test litter. Every workstream here has real\n// history, so `--empty` never matches one. This check reports; it never\n// sweeps. Same posture as src/disk-recon.ts: each finding names its own\n// command and mu runs none of them.\n//\n// IDLE IS DERIVED, NOT STORED\n// ---------------------------\n// There is no `workstreams.last_activity` column and this does not add\n// one. Activity is `MAX(tasks.updated_at)`, falling back to the\n// workstream's own `created_at` when it has no tasks at all — a column\n// would be a second source of truth that can disagree with the rows it\n// summarises, which is the `provenance` reasoning in\n// docs/VOCABULARY.md applied to a cheaper case.\n\nimport type { Db } from \"./db.js\";\nimport type { FleetHazard } from \"./fleet-hazards.js\";\nimport { isScratchWorkstream } from \"./workstream.js\";\n\n/**\n * Idle threshold, in days, before a fully-closed workstream is called\n * **finished**.\n *\n * Two weeks, because the failure mode of a low value is a doctor that\n * nags about the thing you finished yesterday and will reopen tomorrow.\n * A workstream whose every task is closed is not *suspicious* — that is\n * the success state — so the row has to earn its place by the work also\n * being cold.\n */\nexport const FINISHED_IDLE_DAYS = 14;\n\n/**\n * Idle threshold, in days, before a workstream with unclosed tasks is\n * called **abandoned**.\n *\n * Deliberately much higher than FINISHED_IDLE_DAYS: open tasks mean\n * \"not done\", and a fortnight away from a project is a holiday, not\n * abandonment. 60 days is roughly \"two months of not touching it\",\n * which on the dogfood box catches the two genuinely-dead workstreams\n * and nothing that is merely paused.\n */\nexport const ABANDONED_IDLE_DAYS = 60;\n\n/** Neither threshold is an env var. They are display cutoffs on a\n * report the operator then judges — the same call\n * `PEER_STALE_MS` (src/sync.ts) makes, for the same reason: a knob\n * implies a behaviour change downstream, and nothing downstream reads\n * these. */\n\nexport interface DormantWorkstream {\n name: string;\n /** Whole days since the newest task update (or the workstream's own\n * creation, when it has no tasks). */\n idleDays: number;\n /** Tasks in the workstream, total. */\n tasks: number;\n /** Tasks not CLOSED. Zero for `finished`, non-zero for `abandoned`. */\n unclosed: number;\n /** Which bucket, and therefore which remediation applies. */\n kind: \"finished\" | \"abandoned\";\n}\n\ninterface DormantRow {\n name: string;\n tasks: number;\n unclosed: number;\n idle_days: number | null;\n}\n\n/**\n * Workstreams that look torn-down-able, newest-idle last.\n *\n * EXCLUDES:\n * - the current workstream, passed in by the caller. Telling someone\n * the thing they are working in right now is dormant is noise, and\n * the caller is the only layer that knows which it is.\n * - `scratch`, which is ephemeral BY DESIGN (see\n * `isScratchWorkstream`). Its whole contract is \"off-the-cuff\n * helpers, no ceremony\", so a report that it has been quiet for a\n * fortnight is telling the operator the feature works.\n * - workstreams with live agents or registered workspaces. Those are\n * not dormant regardless of task dates: something is running, or a\n * checkout is on disk holding uncommitted work. `mu doctor`'s disk\n * section owns the workspace story.\n *\n * One indexed GROUP BY over `tasks`; no filesystem and no mux calls, so\n * it is cheap enough for the default doctor tier.\n */\nexport function findDormantWorkstreams(\n db: Db,\n opts: { currentWorkstream?: string | null } = {},\n): DormantWorkstream[] {\n const rows = db\n .prepare(\n `SELECT w.name AS name,\n COUNT(t.id) AS tasks,\n COALESCE(SUM(t.status <> 'CLOSED'), 0) AS unclosed,\n CAST(julianday('now')\n - julianday(MAX(COALESCE(t.updated_at, w.created_at)))\n AS INTEGER) AS idle_days\n FROM workstreams w\n LEFT JOIN tasks t ON t.workstream_id = w.id\n WHERE NOT EXISTS (SELECT 1 FROM agents a WHERE a.workstream_id = w.id)\n AND NOT EXISTS (SELECT 1 FROM vcs_workspaces v WHERE v.workstream_id = w.id)\n GROUP BY w.id, w.name\n ORDER BY idle_days DESC, w.name`,\n )\n .all() as DormantRow[];\n\n const dormant: DormantWorkstream[] = [];\n for (const row of rows) {\n if (row.name === opts.currentWorkstream) continue;\n if (isScratchWorkstream(row.name)) continue;\n // A workstream with no tasks at all is `teardown --empty`'s job,\n // not this one. Reporting it here would give the same row two\n // different remediations in one doctor run.\n if (row.tasks === 0) continue;\n // julianday() returns NULL on an unparsable timestamp; treat that\n // as \"cannot judge\" rather than as 0 days (which would silently\n // hide the row) or a huge number (which would invent a finding).\n if (row.idle_days === null) continue;\n const idleDays = row.idle_days;\n const kind =\n row.unclosed === 0\n ? idleDays >= FINISHED_IDLE_DAYS\n ? (\"finished\" as const)\n : null\n : idleDays >= ABANDONED_IDLE_DAYS\n ? (\"abandoned\" as const)\n : null;\n if (kind === null) continue;\n dormant.push({\n name: row.name,\n idleDays,\n tasks: row.tasks,\n unclosed: row.unclosed,\n kind,\n });\n }\n return dormant;\n}\n\n/** `95d` / `3d`. Doctor rows are narrow and the unit is always days\n * here, so this stays a suffix rather than growing a duration\n * formatter (src/cli/tui/format-helpers.ts owns that job for the TUI). */\nfunction days(n: number): string {\n return `${n}d`;\n}\n\n/**\n * The doctor row + remediation for both buckets.\n *\n * Severity is `ok`, never `warn`. A dormant workstream is not a fault —\n * it is a housekeeping opportunity — and `warn` would make\n * `mu doctor` print \"at least one finding needs attention\" forever on a\n * box that is working perfectly. Same choice `ws-empty` makes in\n * src/disk-recon.ts, for the same reason.\n */\nexport function checkDormantWorkstreams(\n db: Db,\n opts: { currentWorkstream?: string | null } = {},\n): FleetHazard {\n const dormant = findDormantWorkstreams(db, opts);\n if (dormant.length === 0) {\n return { name: \"ws-dormant\", severity: \"ok\", detail: \"no dormant workstreams\" };\n }\n\n const finished = dormant.filter((d) => d.kind === \"finished\");\n const abandoned = dormant.filter((d) => d.kind === \"abandoned\");\n const parts: string[] = [];\n if (finished.length > 0) parts.push(`${finished.length} finished`);\n if (abandoned.length > 0) parts.push(`${abandoned.length} with open tasks`);\n\n const remediation: string[] = [];\n if (finished.length > 0) {\n remediation.push(\n `Every task CLOSED and untouched for ${FINISHED_IDLE_DAYS}+ days — safe to tear down:`,\n ...finished.map(\n (d) => ` ${d.name.padEnd(24)} ${days(d.idleDays).padStart(5)} idle, ${d.tasks} closed`,\n ),\n \"\",\n \"Teardown is reversible: it writes tombstone ops, so `mu undo <group>` puts\",\n \"the rows back, and `mu workstream list --torn-down` finds the group later.\",\n ...finished.slice(0, 3).map((d) => ` mu workstream teardown ${d.name} --yes`),\n );\n }\n if (abandoned.length > 0) {\n if (remediation.length > 0) remediation.push(\"\");\n remediation.push(\n `Idle ${ABANDONED_IDLE_DAYS}+ days but still holding UNCLOSED tasks — look before tearing down:`,\n ...abandoned.map(\n (d) =>\n ` ${d.name.padEnd(24)} ${days(d.idleDays).padStart(5)} idle, ${d.unclosed} of ${d.tasks} unclosed`,\n ),\n \"\",\n // \"a teardown here discards open work\" was the first wording, and it\n // was wrong twice: it contradicted the `finished` block above (which\n // correctly calls teardown reversible), and \"work\" reads as \"my code\"\n // when what teardown removes here is the PLAN — task rows and notes.\n //\n // \"no checkout is touched\" is true only because this list EXCLUDES\n // workstreams with registered workspaces; teardown does free real\n // checkouts when they exist (`freedWorkspaces` in teardownWorkstream).\n // The exclusion in findDormantWorkstreams is what makes this sentence\n // safe, so the two must not drift apart.\n \"Removes the task rows and notes — the plan, not the code (no checkout\",\n \"is touched, and `mu undo <group>` puts the rows back). The risk is\",\n \"losing sight of what was left to do, so read it first:\",\n ...abandoned.slice(0, 3).map((d) => ` mu task list -w ${d.name} --status OPEN,IN_PROGRESS`),\n );\n }\n\n return {\n name: \"ws-dormant\",\n severity: \"ok\",\n detail: `${dormant.length} dormant workstream(s): ${parts.join(\", \")}`,\n remediation,\n };\n}\n","// mu — `mu link pi`: thin wrapper over src/link.ts.\n//\n// Touches no DB: linking is a filesystem install, so it runs outside\n// handle() (which opens the DB and runs ambient sync) and routes errors\n// through the same emitError pipeline via emitParseError.\n\nimport type { Command } from \"commander\";\nimport { emitJson, JSON_OPT, UsageError } from \"../cli.js\";\nimport { linkPi, linkSkill } from \"../link.js\";\nimport { type NextStep, pc, printNextSteps } from \"../output.js\";\nimport { emitParseError } from \"./handle.js\";\n\nexport interface LinkCmdOptions {\n json?: boolean;\n copy?: boolean;\n force?: boolean;\n extensionOnly?: boolean;\n skillOnly?: boolean;\n}\n\nexport function cmdLink(target: string, opts: LinkCmdOptions): void {\n if (target !== \"pi\") throw new UsageError(`unsupported link target: ${target} (expected: pi)`);\n if (opts.extensionOnly === true && opts.skillOnly === true) {\n throw new UsageError(\"--extension-only and --skill-only are mutually exclusive\");\n }\n const extension =\n opts.skillOnly === true\n ? undefined\n : linkPi({ copy: opts.copy === true, force: opts.force === true });\n const skill = opts.extensionOnly === true ? undefined : linkSkill({ force: opts.force === true });\n\n const steps: NextStep[] = [{ intent: \"Check the install\", command: \"mu doctor\" }];\n\n if (opts.json === true) {\n emitJson({\n ...(extension ? { extension: { ...extension, copy: opts.copy === true } } : {}),\n ...(skill ? { skill } : {}),\n nextSteps: steps,\n });\n return;\n }\n\n if (extension) {\n console.log(`extension: ${pc.bold(extension.path)}${opts.copy === true ? \" (copy)\" : \"\"}`);\n if (extension.replacedCopy) {\n console.log(\n pc.yellow(\n \" Replaced an inlined copy. Running agents keep the old code until they restart.\",\n ),\n );\n }\n if (opts.copy === true) {\n console.log(pc.dim(\" Pinned to this mu version: re-run `mu link pi` after upgrading.\"));\n }\n }\n if (skill) {\n console.log(`skill: ${pc.bold(skill.path)} -> ${skill.target}`);\n if (skill.previous !== undefined) console.log(pc.dim(` previously -> ${skill.previous}`));\n }\n console.log(pc.dim(\"Restart pi agents (or /reload) to load the extension.\"));\n printNextSteps(steps);\n}\n\nexport function wireLinkCommand(program: Command): void {\n program\n .command(\"link <target>\")\n .description(\"Install the mu pi extension (shim) and the mu skill; <target> must be 'pi'\")\n .option(...JSON_OPT)\n .option(\"--copy\", \"inline the extension instead of a shim (pinned; relink after upgrades)\")\n .option(\"--force\", \"replace an existing extension or skill symlink that points elsewhere\")\n .option(\"--extension-only\", \"install only the pi extension\")\n .option(\"--skill-only\", \"install only the mu skill symlink\")\n .action(function (target: string) {\n const cmd = this as Command;\n try {\n cmdLink(target, cmd.opts() as LinkCmdOptions);\n } catch (err) {\n process.exit(emitParseError(err, cmd));\n }\n });\n}\n","// mu — `mu log` verb (write + read + tail).\n//\n// One verb, three modes:\n// mu log \"text\" → write\n// mu log → read latest 50\n// mu log --tail → blocking subscription (poll every 1s)\n// mu log --since <seq> → cursor read (everything after seq)\n//\n// Extracted from src/cli.ts as part of refactor_split_large_src_files.\n\nimport { getAgentByPane } from \"../agents.js\";\nimport { emitJson, emitJsonCollection, printLogRow, resolveOptionalWorkstream } from \"../cli.js\";\nimport type { Db } from \"../db.js\";\nimport { renderOpLine } from \"../log-render.js\";\nimport {\n appendLog,\n groupIdFromPrefix,\n type ListLogsOptions,\n type LogRow,\n latestSeq,\n listLogs,\n} from \"../logs.js\";\nimport { pc } from \"../output.js\";\nimport { UndoGroupNotFoundError } from \"../undo.js\";\n\nexport interface LogReadOpts {\n workstream?: string;\n allWorkstreams?: boolean;\n since?: number;\n lines?: number;\n source?: string;\n /** Operator channel tag (`ops.entity`). See the log-ledger pattern. */\n kind?: string;\n /** Structured intent filter (`ops.intent`), e.g. 'task.close'. */\n intent?: string;\n /** Undo-group filter (`ops.group_id`). */\n group?: string;\n json?: boolean;\n tail?: boolean;\n}\n\nexport interface LogWriteOpts {\n workstream?: string;\n as?: string;\n kind?: string;\n}\n\n/**\n * The `mu log` verb is overloaded: with a positional <text>, write\n * an entry; without, read the log (optionally tailing).\n */\nexport async function cmdLog(\n db: Db,\n text: string | undefined,\n opts: LogReadOpts & LogWriteOpts,\n): Promise<void> {\n if (text !== undefined && text.length > 0) {\n await cmdLogWrite(db, text, opts);\n return;\n }\n await cmdLogRead(db, opts);\n}\n\n/**\n * Resolve who/where this log entry belongs to:\n * --as <name> explicit override; workstream still resolved below\n * $TMUX_PANE agent name + workstream from the agent row\n * else source = 'user', workstream from -w / $MU_SESSION /\n * tmux session, or null if none of those resolve\n */\nasync function resolveLogContext(\n db: Db,\n opts: { as?: string; workstream?: string },\n): Promise<{ source: string; workstream: string | null }> {\n if (opts.as) {\n const workstream = opts.workstream ?? (await resolveOptionalWorkstream());\n return { source: opts.as, workstream };\n }\n const paneId = process.env.TMUX_PANE;\n if (paneId) {\n const agent = getAgentByPane(db, paneId);\n if (agent) {\n // Pane branch is intentionally asymmetric: when no -w is given, the\n // agent's own workstream wins over $MU_SESSION / tmux session, since\n // the agent row is the more authoritative binding. Don't \"fix\" this\n // to call resolveOptionalWorkstream() like the other branches.\n return {\n source: agent.name,\n workstream: opts.workstream ?? agent.workstreamName,\n };\n }\n }\n const workstream = opts.workstream ?? (await resolveOptionalWorkstream());\n return { source: \"user\", workstream };\n}\n\nasync function cmdLogWrite(db: Db, text: string, opts: LogWriteOpts): Promise<void> {\n const ctx = await resolveLogContext(db, opts);\n const row = appendLog(db, {\n workstream: ctx.workstream,\n source: ctx.source,\n kind: opts.kind ?? \"message\",\n payload: text,\n });\n console.log(\n pc.dim(\n `seq ${row.seq} workstream=${row.workstreamName ?? \"—\"} source=${row.source} kind=${row.kind}`,\n ),\n );\n}\n\n/** Attach the formatter's prose to a JSON row.\n *\n * Consumers should never have to re-derive prose from `payload` — that\n * would recreate exactly the payload-parsing coupling v2-log-verb\n * deleted. The structured fields stay alongside it, so a script can\n * switch on `intent` and a human reading `--json` still sees what\n * happened. */\nfunction withRendered(row: LogRow): LogRow & { rendered: string } {\n return { ...row, rendered: renderOpLine(row) };\n}\n\nasync function cmdLogRead(db: Db, opts: LogReadOpts): Promise<void> {\n const workstream = await logReadWorkstream(opts);\n const listOpts: ListLogsOptions = {};\n if (workstream !== undefined) listOpts.workstream = workstream;\n if (opts.source !== undefined) listOpts.source = opts.source;\n if (opts.kind !== undefined) listOpts.kind = opts.kind;\n if (opts.intent !== undefined) listOpts.intent = opts.intent;\n if (opts.group !== undefined) {\n // Accept an abbreviated group id, exactly as `mu undo` does. Without\n // this, the documented workflow (`mu undo` prints an 8-char prefix →\n // `mu log --group <prefix>` to inspect it) silently returned nothing\n // (bug_group_id_prefix_asymmetry). A prefix that matches no group is\n // reported below rather than degrading to an empty listing, since\n // \"no entries\" reads as \"this group did nothing\".\n const resolved = groupIdFromPrefix(db, opts.group);\n if (resolved === null) throw new UndoGroupNotFoundError(opts.group);\n listOpts.group = resolved;\n }\n\n if (opts.tail) {\n await cmdLogTail(db, listOpts, opts);\n return;\n }\n\n if (opts.since !== undefined) listOpts.since = opts.since;\n if (opts.lines !== undefined) listOpts.limit = opts.lines;\n // Default cap: latest 50 entries when no `since` and no `--lines`.\n if (opts.since === undefined && opts.lines === undefined) listOpts.limit = 50;\n\n const rows = listLogs(db, listOpts);\n if (opts.json) {\n emitJsonCollection(rows.map(withRendered));\n return;\n }\n if (rows.length === 0) {\n console.log(pc.dim(\"(no log entries)\"));\n return;\n }\n for (const row of rows) printLogRow(row);\n}\n\n/**\n * Resolve the `--workstream` filter for log reads:\n * --all → undefined (every workstream + machine-wide)\n * --workstream X → X\n * $MU_SESSION etc. → the current workstream (default behaviour)\n * none → undefined (be permissive in read mode)\n */\nasync function logReadWorkstream(opts: LogReadOpts): Promise<string | undefined> {\n if (opts.allWorkstreams) return undefined;\n if (opts.workstream) return opts.workstream;\n const ws = await resolveOptionalWorkstream();\n return ws ?? undefined;\n}\n\nasync function cmdLogTail(db: Db, baseOpts: ListLogsOptions, cliOpts: LogReadOpts): Promise<void> {\n // If --since wasn't given, start at \"now\" so the subscriber only sees\n // NEW entries. Pass `--since 0` to replay from the beginning.\n let cursor = cliOpts.since ?? latestSeq(db);\n if (!cliOpts.json) {\n console.log(\n pc.dim(\n `(tailing log; cursor=${cursor}; ${baseOpts.workstream ? `workstream=${baseOpts.workstream}` : \"all workstreams\"}; ctrl-c to exit)`,\n ),\n );\n }\n const intervalMs = defaultLogTailIntervalMs();\n for (;;) {\n const rows = listLogs(db, { ...baseOpts, since: cursor });\n for (const row of rows) {\n // NDJSON for --tail (one object per line), per SKILL.md: it is a\n // stream, not a collection, so no {items,count} envelope.\n if (cliOpts.json) emitJson(withRendered(row));\n else printLogRow(row);\n cursor = row.seq;\n }\n await new Promise((r) => setTimeout(r, intervalMs));\n }\n}\n\n/** Tail interval default + safety floor. Mirrors defaultSpawnLivenessMs\n * (src/agents.ts) and defaultSendDelayMs (src/tmux.ts). Naive\n * `Number(env)` was a DOS-by-typo: an env value of '' parses as 0\n * and any non-numeric value as NaN, both of which Node's setTimeout\n * treats as 1ms — hammering SQLite at ~500 Hz on the next mu log\n * --tail. Unparseable env → fall back to the no-env default of 1000ms;\n * parseable but too-low → clamp up to the 50ms floor (so a deliberate\n * `MU_LOG_TAIL_INTERVAL_MS=10` becomes 50, not 1000). */\nconst LOG_TAIL_INTERVAL_FLOOR_MS = 50;\nconst LOG_TAIL_INTERVAL_DEFAULT_MS = 1000;\nfunction defaultLogTailIntervalMs(): number {\n const raw = process.env.MU_LOG_TAIL_INTERVAL_MS;\n if (raw === undefined) return LOG_TAIL_INTERVAL_DEFAULT_MS;\n const parsed = Number.parseInt(raw, 10);\n if (Number.isNaN(parsed)) return LOG_TAIL_INTERVAL_DEFAULT_MS;\n return Math.max(LOG_TAIL_INTERVAL_FLOOR_MS, parsed);\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n//\n// wireLogCommand is called by buildProgram() in src/cli.ts. Wired here so\n// every per-namespace builder lives next to its cmd functions.\n\nimport type { Command } from \"commander\";\nimport { handle, JSON_OPT, parseLines, parseNonNegativeInt, WORKSTREAM_OPT } from \"../cli.js\";\n\nexport function wireLogCommand(program: Command): void {\n // mu log — overloaded:\n // mu log \"text\" → write\n // mu log → read latest 50\n // mu log --tail → blocking subscription (poll every 1s)\n // mu log --since <seq> → cursor read (everything after seq)\n program\n .command(\"log [text]\")\n .description(\n \"Write a log entry (with text) or read the log (without). --tail blocks and prints new entries as they land.\",\n )\n .option(\"--as <name>\", \"override the source name (default: agent via $TMUX_PANE, else 'user')\")\n .option(\n \"--kind <kind>\",\n \"operator-chosen channel tag: sets it on write, filters to it on read (log-ledger pattern); workstream, task, edge and note are reserved\",\n )\n .option(\n \"--intent <intent>\",\n \"filter reads to one structured intent, e.g. task.close (see `mu log` output)\",\n )\n .option(\"--group <id>\", \"filter reads to one undo group (every op of a single action)\")\n .option(\"--tail\", \"block and print entries as they're appended\")\n .option(\n \"--since <seq>\",\n \"return entries with seq strictly greater than this (use 0 to replay everything)\",\n parseNonNegativeInt,\n )\n .option(\n \"-n, --lines <n>\",\n \"cap to N entries: the latest N (default 50), or with --since the first N after the cursor (no default cap)\",\n parseLines,\n )\n .option(\"--source <name>\", \"filter by source\")\n .option(\"--all\", \"read across every workstream (and machine-wide entries)\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (text: string | undefined) {\n const raw = (this as Command).opts() as {\n as?: string;\n kind?: string;\n intent?: string;\n group?: string;\n tail?: boolean;\n since?: number;\n lines?: number;\n source?: string;\n all?: boolean;\n workstream?: string;\n json?: boolean;\n };\n const opts: LogReadOpts & LogWriteOpts = {};\n if (raw.as !== undefined) opts.as = raw.as;\n if (raw.kind !== undefined) opts.kind = raw.kind;\n if (raw.intent !== undefined) opts.intent = raw.intent;\n if (raw.group !== undefined) opts.group = raw.group;\n if (raw.tail !== undefined) opts.tail = raw.tail;\n if (raw.since !== undefined) opts.since = raw.since;\n if (raw.lines !== undefined) opts.lines = raw.lines;\n if (raw.source !== undefined) opts.source = raw.source;\n if (raw.all !== undefined) opts.allWorkstreams = raw.all;\n if (raw.workstream !== undefined) opts.workstream = raw.workstream;\n if (raw.json !== undefined) opts.json = raw.json;\n return handle((db) => cmdLog(db, text, opts), this as Command)();\n });\n}\n","// mu — `mu rebuild <file>`: the disaster-recovery verb.\n//\n// Thin wrapper over `rebuildInto` (src/rebuild.ts). All the human-facing\n// reporting lives here, and none of it lives in the SDK, so the\n// forthcoming doctor drift check can rebuild into a temp DB and diff\n// without a human-shaped summary getting in the way.\n\nimport { type Db, defaultDbPath } from \"../db.js\";\nimport { type NextStep, pc, printNextSteps } from \"../output.js\";\nimport { type RebuildReport, rebuildInto } from \"../rebuild.js\";\n\nexport interface RebuildCmdOptions {\n json?: boolean;\n force?: boolean;\n}\n\n/** The swap command, as the operator should run it. First next-step, so\n * the thing to do next is the first thing they read. */\nfunction swapCommand(targetPath: string): string {\n const live = defaultDbPath();\n return `mv ${targetPath} ${live}`;\n}\n\nfunction nextSteps(report: RebuildReport): NextStep[] {\n const steps: NextStep[] = [\n { intent: \"Swap the rebuilt DB into place\", command: swapCommand(report.targetPath) },\n {\n intent: \"Inspect it first\",\n command: `MU_DB_PATH=${report.targetPath} mu state`,\n },\n ];\n if (report.machineLocalLost.length > 0) {\n // Only suggest re-spawning when there was actually something to lose.\n steps.push({\n intent: \"Re-spawn agents after the swap (registry is not rebuildable)\",\n command: \"mu agent spawn <name> -w <workstream>\",\n });\n }\n return steps;\n}\n\nexport async function cmdRebuild(\n db: Db,\n targetPath: string,\n opts: RebuildCmdOptions = {},\n): Promise<void> {\n const report = rebuildInto(db, {\n targetPath,\n ...(opts.force === true ? { force: true } : {}),\n });\n\n if (opts.json === true) {\n emitJson({\n targetPath: report.targetPath,\n machineId: report.machineId,\n opsCopied: report.opsCopied,\n opsProjected: report.opsProjected,\n opsChangedRows: report.opsChangedRows,\n logOnly: report.logOnlyByEntity,\n rebuiltRows: report.rebuiltRows,\n machineLocalLost: report.machineLocalLost,\n swapCommand: swapCommand(report.targetPath),\n nextSteps: nextSteps(report),\n });\n return;\n }\n\n console.log(`Rebuilt ${pc.bold(report.targetPath)} from ${report.opsCopied} ops`);\n const rows = report.rebuiltRows;\n const shape = [\"workstreams\", \"tasks\", \"task_edges\", \"task_notes\"]\n .map((t) => `${rows[t] ?? 0} ${t}`)\n .join(\", \");\n console.log(pc.dim(` projected ${report.opsProjected} ops -> ${shape}`));\n const logOnly = Object.entries(report.logOnlyByEntity);\n if (logOnly.length > 0) {\n console.log(\n pc.dim(\n ` copied ${logOnly.map(([e, n]) => `${n} ${e}`).join(\", \")} (log-only, no table to project into)`,\n ),\n );\n }\n console.log(pc.dim(` machine_id preserved: ${report.machineId}`));\n\n // The part an operator MUST NOT miss: their agent registry is gone.\n // Never silent — see src/rebuild.ts for why these tables cannot be\n // rebuilt and why that is correct rather than a gap.\n if (report.machineLocalLost.length > 0) {\n const lost = report.machineLocalLost.map((l) => `${l.rows} ${l.table}`).join(\", \");\n console.log(\n pc.yellow(\n ` NOT rebuilt: ${lost}. These tables have no capture triggers, so they leave no ops.`,\n ),\n );\n console.log(\n pc.dim(\n \" That is expected: pane ids and absolute workspace paths are meaningless after a rebuild.\",\n ),\n );\n console.log(pc.dim(\" Re-spawn agents once you have swapped the DB in.\"));\n }\n\n printNextSteps(nextSteps(report));\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n\nimport type { Command } from \"commander\";\nimport { emitJson, handle, JSON_OPT } from \"../cli.js\";\n\nexport function wireRebuildCommand(program: Command): void {\n program\n .command(\"rebuild <file>\")\n .description(\n \"Replay the ops log into a NEW DB file (disaster recovery); prints the swap command\",\n )\n .option(...JSON_OPT)\n .option(\"--force\", \"replace <file> if it already exists (deleted first, never merged into)\")\n .action(function (file: string) {\n const opts = (this as Command).opts() as RebuildCmdOptions;\n return handle((db) => cmdRebuild(db, file, opts), this as Command)();\n });\n}\n","// mu — `mu sql` escape-hatch verb.\n//\n// Read OR write — `mu sql` is the explicit escape hatch. Single-statement\n// path uses better-sqlite3's prepare() so we can distinguish read\n// (.all() rows) from write (.run() change count). Multi-statement path\n// uses db.exec() which handles BEGIN/COMMIT and multiple semicolon-\n// separated statements but returns nothing structured.\n//\n// `--confirm-rows N` adds a transactional safety belt: if the actual\n// affected-row count (FK cascades included) doesn't match N, the whole\n// thing rolls back. Every write is captured as ops under one `sql.write`\n// group, so `mu undo` reverts a whole `mu sql` call.\n//\n// Extracted from src/cli.ts as part of refactor_split_large_src_files.\n\nimport { captureBookkeepingChanges } from \"../capture.js\";\nimport { emitJson, UsageError } from \"../cli.js\";\nimport type { Db } from \"../db.js\";\nimport { currentOpContext, withOpContext } from \"../op-context.js\";\nimport { muTable, pc } from \"../output.js\";\n\nexport async function cmdSql(\n db: Db,\n query: string,\n opts: { json?: boolean; confirmRows?: number } = {},\n): Promise<void> {\n // ONE op context for the whole invocation. Without it every captured\n // row got its own random group and a null intent, so one multi-row\n // UPDATE showed up in `mu undo` as N separate \"(no intent)\" actions\n // and `mu log` fell back to printing the raw JSON payload. With it,\n // `mu undo` reverts the whole `mu sql` call as one action.\n withOpContext(db, { intent: \"sql.write\", group: \"new\" }, () => runSql(db, query, opts));\n}\n\nfunction runSql(db: Db, query: string, opts: { json?: boolean; confirmRows?: number }): void {\n // Read OR write — `mu sql` is the explicit escape hatch.\n //\n // Single-statement path uses better-sqlite3's prepare() so we can\n // distinguish read (.all() rows) from write (.run() change count).\n // Multi-statement path uses db.exec() which handles BEGIN/COMMIT and\n // multiple semicolon-separated statements but returns nothing\n // structured. We try prepare() first; if it throws the\n // 'more than one statement' SqliteError, we fall back to exec().\n // This keeps the simple case fast and well-typed while making\n // multi-statement migrations / cleanup scripts a one-shot.\n const trimmed = query.trim();\n // Capture the prepared statement so the single-statement path below\n // doesn't re-prepare (review_code_sql_double_prepare).\n let stmt: ReturnType<typeof db.prepare> | undefined;\n try {\n stmt = db.prepare(trimmed);\n } catch (err) {\n const msg = err instanceof Error ? err.message : String(err);\n if (!/more than one statement/i.test(msg)) throw err;\n }\n\n if (stmt === undefined) {\n // Multi-statement. Note: scripts that contain their own BEGIN/COMMIT\n // fail under --confirm-rows (sqlite refuses nested transactions);\n // that's the price of an atomic confirm-or-rollback wrapper around\n // an opaque blob.\n if (opts.confirmRows !== undefined) {\n const expected = opts.confirmRows;\n const { actual } = runConfirmed(db, expected, () => db.exec(trimmed));\n const n = countTopLevelStatements(trimmed);\n if (opts.json) {\n emitJson({\n statements: n,\n multiStatement: true,\n confirmRows: expected,\n actualRows: actual,\n });\n return;\n }\n console.log(\n pc.dim(\n `ran ${n} statement${n === 1 ? \"\" : \"s\"} (${actual} row${actual === 1 ? \"\" : \"s\"} affected)`,\n ),\n );\n return;\n }\n db.exec(trimmed);\n const n = countTopLevelStatements(trimmed);\n if (opts.json) {\n emitJson({ statements: n, multiStatement: true });\n return;\n }\n console.log(pc.dim(`ran ${n} statement${n === 1 ? \"\" : \"s\"}`));\n return;\n }\n\n const single = stmt;\n // better-sqlite3's prepared-statement metadata is the source of truth;\n // prefix guesses miss PRAGMA reads and comment-prefixed SELECTs.\n // `readonly` (not `reader`) decides whether --confirm-rows applies:\n // `reader` is also true for `UPDATE ... RETURNING`, which IS a write.\n if (opts.confirmRows !== undefined) {\n if (single.readonly) {\n throw new UsageError(\n \"--confirm-rows is only meaningful on write statements (UPDATE / DELETE / INSERT / REPLACE)\",\n );\n }\n const expected = opts.confirmRows;\n const { result, actual } = runConfirmed(db, expected, () => single.run([]));\n if (opts.json) {\n emitJson({\n changes: result.changes,\n lastInsertRowid: Number(result.lastInsertRowid),\n confirmRows: expected,\n actualRows: actual,\n });\n return;\n }\n console.log(pc.dim(`${actual} row${actual === 1 ? \"\" : \"s\"} affected`));\n return;\n }\n if (single.reader) {\n const rows = single.all([]);\n if (opts.json) {\n emitJson(rows);\n return;\n }\n if (rows.length === 0) {\n console.log(pc.dim(\"(no rows)\"));\n return;\n }\n const first = rows[0] as Record<string, unknown>;\n const keys = Object.keys(first);\n // SQL is the escape hatch: every column is user-data of unknown\n // length. Divide the terminal width evenly across columns (subject\n // to a 12-char floor) so a single wide cell can't push the table\n // out to ~200 cols and break the TUI layout. cli-table3's\n // wordWrap:false (via muTable) truncates with … when a cell\n // exceeds its column width (tables_truncate_long_cols_audit).\n const termWidth = process.stdout.columns ?? 100;\n const padding = keys.length * 3 + 1; // 2-char cell padding + 1-char border per col\n const perCol = Math.max(12, Math.floor((termWidth - padding) / Math.max(1, keys.length)));\n const colWidths = keys.map(() => perCol);\n const table = muTable({\n head: keys.map((k) => pc.bold(k)),\n colWidths,\n style: { head: [] },\n });\n for (const row of rows) {\n const obj = row as Record<string, unknown>;\n table.push(keys.map((k) => formatCell(obj[k])));\n }\n console.log(table.toString());\n console.log(pc.dim(`(${rows.length} row${rows.length === 1 ? \"\" : \"s\"})`));\n return;\n }\n const result = single.run([]);\n if (opts.json) {\n emitJson({\n changes: result.changes,\n lastInsertRowid: Number(result.lastInsertRowid),\n });\n return;\n }\n console.log(pc.dim(`${result.changes} row${result.changes === 1 ? \"\" : \"s\"} affected`));\n}\n\n/**\n * The --confirm-rows run, shared by the single- and multi-statement\n * paths so the same statement always gets the same count. Runs `exec`\n * ONCE, with capture ON, inside one transaction; COMMITs only when the\n * count of THAT execution equals `expected`, else ROLLs BACK and throws\n * a UsageError. There is no measure-then-rerun: a nondeterministic or\n * state-dependent statement (`WHERE abs(random()) % 2 = 0`) could pick\n * different rows on a second run and commit a count nobody confirmed.\n *\n * The count is the total_changes() delta: every row the SQL changes,\n * INCLUDING rows removed by ON DELETE CASCADE (deleting a task also\n * deletes its edges and notes). That is the honest blast radius, and it\n * is the same number whether the statement runs alone or in a script.\n *\n * Capture bookkeeping is NOT counted. Each captured row change also runs\n * a capture trigger whose body is several statements (the op INSERT\n * plus the HLC clock UPDATEs), all of which total_changes() counts.\n * captureBookkeepingChanges() derives that overhead from the ops this\n * call's group wrote, and it is subtracted from the delta.\n */\nfunction runConfirmed<T>(db: Db, expected: number, exec: () => T): { result: T; actual: number } {\n const groupId = currentOpContext(db).groupId;\n return runInTransaction(db, () => {\n const before = totalChanges(db);\n const result = exec();\n const delta = totalChanges(db) - before;\n const actual = groupId === null ? delta : delta - captureBookkeepingChanges(db, groupId);\n if (actual !== expected) {\n throw new UsageError(\n `expected ${expected} rows, would have affected ${actual} (rolled back). Re-run with --confirm-rows ${actual} if intentional.`,\n );\n }\n return { result, actual };\n });\n}\n\nfunction totalChanges(db: Db): number {\n return (db.prepare(\"SELECT total_changes() AS n\").get() as { n: number }).n;\n}\n\n/** BEGIN, run `fn`, COMMIT; ROLLBACK and rethrow on failure. */\nfunction runInTransaction<T>(db: Db, fn: () => T): T {\n db.exec(\"BEGIN IMMEDIATE\");\n let result: T;\n try {\n result = fn();\n } catch (e) {\n try {\n db.exec(\"ROLLBACK\");\n } catch {}\n throw e;\n }\n db.exec(\"COMMIT\");\n return result;\n}\n\n/**\n * Count top-level SQL statements in `sql`, ignoring semicolons inside\n * single-quoted strings, double-quoted identifiers, line comments\n * (`-- ...`), and block comments (`/* ... *\\/`). Used by `mu sql`'s\n * multi-statement path to report 'ran N statements'.\n *\n * Hand-rolled rather than pulling in a SQL parser — mu's escape hatch\n * is for human-typed scripts, not arbitrary SQL. The state machine\n * covers the cases we care about; pathological inputs (nested\n * comments, dollar-quoted strings, etc.) may miscount but won't crash\n * the verb (db.exec already ran successfully by then).\n */\nexport function countTopLevelStatements(sql: string): number {\n let count = 0;\n let inSingle = false;\n let inDouble = false;\n let inLineComment = false;\n let inBlockComment = false;\n let sawNonWs = false;\n for (let i = 0; i < sql.length; i++) {\n const c = sql[i];\n const next = sql[i + 1];\n if (inLineComment) {\n if (c === \"\\n\") inLineComment = false;\n continue;\n }\n if (inBlockComment) {\n if (c === \"*\" && next === \"/\") {\n inBlockComment = false;\n i++;\n }\n continue;\n }\n if (inSingle) {\n // SQL-style escaped single quote: '' inside a string\n if (c === \"'\" && next === \"'\") {\n i++;\n continue;\n }\n if (c === \"'\") inSingle = false;\n continue;\n }\n if (inDouble) {\n if (c === '\"' && next === '\"') {\n i++;\n continue;\n }\n if (c === '\"') inDouble = false;\n continue;\n }\n if (c === \"-\" && next === \"-\") {\n inLineComment = true;\n i++;\n continue;\n }\n if (c === \"/\" && next === \"*\") {\n inBlockComment = true;\n i++;\n continue;\n }\n if (c === \"'\") {\n inSingle = true;\n continue;\n }\n if (c === '\"') {\n inDouble = true;\n continue;\n }\n if (c === \";\") {\n if (sawNonWs) {\n count++;\n sawNonWs = false;\n }\n continue;\n }\n if (c !== undefined && /\\S/.test(c)) sawNonWs = true;\n }\n if (sawNonWs) count++; // trailing statement without `;`\n return count;\n}\n\nfunction formatCell(v: unknown): string {\n if (v === null || v === undefined) return pc.dim(\"null\");\n if (typeof v === \"string\") return v;\n return String(v);\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n//\n// wireSqlCommand is called by buildProgram() in src/cli.ts. Wired here so\n// every per-namespace builder lives next to its cmd functions.\n\nimport type { Command } from \"commander\";\nimport { handle, JSON_OPT, parseLines } from \"../cli.js\";\n\nexport function wireSqlCommand(program: Command): void {\n program\n .command(\"sql <query>\")\n .description(\"Run a SQL query against the live mu DB (SELECT / UPDATE / DELETE all allowed)\")\n // SQL line comments start with `--`; quoted queries like\n // `mu sql \"-- comment\\nSELECT 1\"` must bind that token as the\n // required <query> argument rather than as an unknown CLI option.\n .allowUnknownOption(true)\n .option(...JSON_OPT)\n .option(\n \"--confirm-rows <n>\",\n \"abort if the affected-row count (ON DELETE CASCADE rows included) differs from N (rollback)\",\n parseLines,\n )\n .action(function (query: string) {\n const opts = (this as Command).opts() as { json?: boolean; confirmRows?: number };\n // NO ambient sync on this path. `mu sql` is the escape hatch whose\n // no-surprise-mutations property is load-bearing: an operator\n // reading state with it must see the state as it is, not as it\n // becomes once a peer's segment lands between openDb and the query.\n // It is also the one verb whose result the operator diffs against\n // their own expectation, so an ambient ingest changing the row\n // count would read as a mu bug.\n return handle((db) => cmdSql(db, query, opts), this as Command, { ambientSync: false })();\n });\n}\n","// Pure helper for choosing the initial active workstream tab when the\n// TUI launches from either bare `mu` or `mu state --tui`.\n//\n// Precedence is intentionally shared across both entry paths:\n// 1. $MU_SESSION if it names one of the resolved workstreams\n// 2. current tmux session name (`mu-<workstream>` prefix stripped)\n// 3. current cwd inside a registered vcs_workspaces.path\n// 4. current cwd equals a VCS-derived project root for registered workspaces,\n// with ties broken by most-recent workstream activity\n// 5. tab 0\n//\n// No ink/react imports here: this file sits outside src/cli/tui/ so the\n// static CLI graph stays free of the TUI bundle.\n\nimport { realpathSync } from \"node:fs\";\nimport path from \"node:path\";\n\nimport type { Db } from \"../db.js\";\nimport { scopeFor } from \"../logs.js\";\nimport { workspaceProjectRoot } from \"../project-root.js\";\nimport { listWorkspaces } from \"../workspace.js\";\nimport { resolveMuxSessionWorkstreamName } from \"../workstream.js\";\n\nfunction normalizeExistingPath(candidatePath: string): string {\n try {\n return realpathSync(candidatePath);\n } catch {\n return path.resolve(candidatePath);\n }\n}\n\nfunction isInsidePath(cwd: string, candidatePath: string): boolean {\n const normalizedCandidate = normalizeExistingPath(candidatePath);\n if (cwd === normalizedCandidate) return true;\n return cwd.startsWith(`${normalizedCandidate}${path.sep}`);\n}\n\n/** The candidate workstream with the most recent op. Exported for tests. */\nexport function latestActiveWorkstream(db: Db, candidates: readonly string[]): string | null {\n // ops.key is the natural key: the bare name for workstream-scoped rows\n // but \"<ws>/<local_id>\" (and \"#<id>\" / \"-><ref>\" suffixes) for tasks,\n // notes, and edges. Use the same exact-or-prefix scope as `mu log`, or\n // all task work is invisible to the tie-break.\n let best: { name: string; createdAt: string; seq: number } | null = null;\n for (const name of candidates) {\n const scope = scopeFor(db, name);\n const row = db\n .prepare(\n `SELECT l.created_at AS createdAt, l.seq AS seq\n FROM ops l\n WHERE ${scope.sql}\n ORDER BY l.created_at DESC, l.seq DESC\n LIMIT 1`,\n )\n .get(...scope.params) as { createdAt: string; seq: number } | undefined;\n if (row === undefined) continue;\n if (\n best === null ||\n row.createdAt > best.createdAt ||\n (row.createdAt === best.createdAt && row.seq > best.seq)\n ) {\n best = { name, ...row };\n }\n }\n return best?.name ?? null;\n}\n\nexport async function resolveInitialTab(names: readonly string[], db: Db): Promise<number> {\n const envWs = process.env.MU_SESSION;\n const envIndex = envWs === undefined ? -1 : names.indexOf(envWs);\n if (envIndex >= 0) return envIndex;\n\n if (names.length <= 1) return 0;\n\n const tmuxWs = await resolveMuxSessionWorkstreamName();\n const tmuxIndex = tmuxWs === null ? -1 : names.indexOf(tmuxWs);\n if (tmuxIndex >= 0) return tmuxIndex;\n\n const cwd = normalizeExistingPath(process.cwd());\n const workspaces = listWorkspaces(db);\n for (let i = 0; i < names.length; i++) {\n const name = names[i];\n if (name === undefined) continue;\n for (const row of workspaces) {\n if (row.workstreamName === name && isInsidePath(cwd, row.path)) return i;\n }\n }\n\n const rootCache = new Map<string, Promise<string | null>>();\n const rootFor = (workspacePath: string, backend: (typeof workspaces)[number][\"backend\"]) => {\n const key = `${backend}\\x00${workspacePath}`;\n const cached = rootCache.get(key);\n if (cached !== undefined) return cached;\n const promise = workspaceProjectRoot(workspacePath, backend);\n rootCache.set(key, promise);\n return promise;\n };\n\n const candidates: string[] = [];\n for (const row of workspaces) {\n if (!names.includes(row.workstreamName)) continue;\n const projectRoot = await rootFor(row.path, row.backend);\n if (projectRoot !== null && cwd === normalizeExistingPath(projectRoot)) {\n candidates.push(row.workstreamName);\n }\n }\n\n const uniqueCandidates = Array.from(new Set(candidates));\n if (uniqueCandidates.length === 1) {\n const index = names.indexOf(uniqueCandidates[0] as string);\n if (index >= 0) return index;\n }\n\n const latest = latestActiveWorkstream(db, uniqueCandidates);\n const latestIndex = latest === null ? -1 : names.indexOf(latest);\n if (latestIndex >= 0) return latestIndex;\n\n return 0;\n}\n","// mu — VCS-derived project root helpers.\n//\n// Used by the TUI launch-focus heuristic to connect a registered\n// per-agent workspace back to the project root the human is likely\n// standing in. Kept outside src/cli/ so it stays a small reusable SDK\n// helper with no ink/react imports.\n\nimport { execFile } from \"node:child_process\";\nimport { readFile, realpath, stat } from \"node:fs/promises\";\nimport { dirname, resolve } from \"node:path\";\nimport { promisify } from \"node:util\";\n\nimport type { VcsBackendName } from \"./vcs.js\";\n\nconst exec = promisify(execFile);\n\nasync function run(bin: string, args: readonly string[], cwd: string): Promise<string> {\n const { stdout } = await exec(bin, [...args], { cwd, maxBuffer: 1024 * 1024 });\n return stdout.trim();\n}\n\nasync function realpathOrResolve(path: string): Promise<string> {\n try {\n return await realpath(path);\n } catch {\n return resolve(path);\n }\n}\n\nasync function gitProjectRoot(workspacePath: string): Promise<string | null> {\n try {\n const commonDir = await run(\n \"git\",\n [\"rev-parse\", \"--path-format=absolute\", \"--git-common-dir\"],\n workspacePath,\n );\n if (commonDir.length === 0) return null;\n return realpathOrResolve(dirname(commonDir));\n } catch {\n return null;\n }\n}\n\nasync function slProjectRoot(workspacePath: string): Promise<string | null> {\n try {\n const root = await run(\"sl\", [\"root\"], workspacePath);\n if (root.length === 0) return null;\n return realpathOrResolve(root);\n } catch {\n return null;\n }\n}\n\n// A jj workspace made by `jj workspace add` has no .git; its\n// `.jj/repo` is a file holding the path (relative to `.jj/`) of the\n// main workspace's `.jj/repo` store. The main workspace's own\n// `.jj/repo` is that store directory.\nasync function jjProjectRoot(workspacePath: string): Promise<string | null> {\n const dotJj = resolve(workspacePath, \".jj\");\n const repo = resolve(dotJj, \"repo\");\n try {\n if ((await stat(repo)).isDirectory()) return realpathOrResolve(workspacePath);\n const store = resolve(dotJj, (await readFile(repo, \"utf8\")).trim());\n return realpathOrResolve(dirname(dirname(store)));\n } catch {\n return null;\n }\n}\n\n/**\n * Resolve the canonical project root for a registered workspace path.\n *\n * - git: parent of `git rev-parse --git-common-dir`, so git worktrees\n * map back to the main checkout's project root rather than the\n * per-agent worktree directory.\n * - jj: the directory holding the repo store that the workspace's\n * `.jj/repo` pointer names (the main workspace), git-backed or not.\n * - sl: `sl root` is the project root.\n * - none: no VCS relationship to infer.\n */\nexport async function workspaceProjectRoot(\n workspacePath: string,\n backend: VcsBackendName,\n): Promise<string | null> {\n if (backend === \"none\") return null;\n if (backend === \"git\") return gitProjectRoot(workspacePath);\n if (backend === \"sl\") return slProjectRoot(workspacePath);\n return jjProjectRoot(workspacePath);\n}\n","// Lazy loader for the ink TUI, shared by bare `mu` and `mu state --tui`.\n//\n// React and react-reconciler choose their build when first required:\n// the development build (extra validation, runWithFiberInDEV, more\n// allocation per commit) unless NODE_ENV === \"production\". The CLI never\n// sets NODE_ENV, so every TUI session ran the dev build. Default it to\n// \"production\" only while the TUI graph evaluates, then restore it, so\n// processes the TUI spawns (agents, editors) inherit the user's env\n// unchanged. An explicit NODE_ENV (vitest sets \"test\") is respected.\n//\n// No ink/react imports here: this file sits outside src/cli/tui/ so the\n// static CLI graph stays free of the TUI chunk.\n\ntype TuiModule = typeof import(\"./tui/index.js\");\n\nexport async function importTui(\n load: () => Promise<TuiModule> = () => import(\"./tui/index.js\"),\n): Promise<TuiModule> {\n const key = \"NODE_ENV\";\n if (process.env[key] !== undefined) return load();\n process.env[key] = \"production\";\n try {\n return await load();\n } finally {\n delete process.env[key];\n }\n}\n","// mu — `mu state` (canonical state card) and TUI back-compat dispatch.\n//\n// One verb, two render modes:\n//\n// mu state full card: agents + orphans + tracks +\n// ready/in-progress/blocked/recent-closed +\n// workspaces + recent events. Top-to-bottom,\n// every section gets its full table. JSON-\n// first by design (per Ilya's council\n// critique: state cards as the default\n// attention surface; SQL/raw verbs as the\n// escape hatch underneath).\n//\n// mu state --tui interactive ink dashboard: glance cards,\n// fullscreen popups, live tick, read-only\n// act-intents that yank commands for the\n// user to run in a shell.\n//\n// Static JSON/render modes load their full data set via\n// loadWorkstreamSnapshot. The TUI owns its own poll loop and only\n// needs the resolved workstream names at launch. --tui is mutually\n// exclusive with --json.\n//\n// All modes support variadic `-w X[,Y]...` / `-w X -w Y` and `--all`.\n// In static modes N=1 renders single-mode (legacy shape) and N≥2\n// stacks per-workstream full cards. In TUI mode N≥2\n// switches workstreams via tabs.\n//\n// Static snapshots run full reconciliation: refresh pane titles (the\n// operator's primary signal) and reap missing panes. Mid-spawn\n// placeholders remain protected by reconcile's pending-pane skip\n// (bug_agent_spawn_workspace_fk_failure). The TUI launches first and\n// performs its own fast/slow polling after Ink renders.\n\nimport type { LiveAgent } from \"../agents.js\";\nimport {\n emitJson,\n formatAgentsTable,\n formatTaskListTable,\n formatTracks,\n formatWorkspacesTable,\n handle,\n JSON_OPT,\n parseCsvFlag,\n parseLines,\n printLogRow,\n resolveOptionalWorkstream,\n UsageError,\n withRoiAll,\n} from \"../cli.js\";\nimport { type Db, tryResolveWorkstreamId, WorkstreamNotFoundError } from \"../db.js\";\nimport { GLYPH } from \"../glyphs.js\";\nimport { muTable, pc } from \"../output.js\";\nimport { isWorkspaceStale, WORKSPACE_STALE_THRESHOLD } from \"../staleness.js\";\nimport {\n listRemoteWorkers,\n loadWorkstreamSnapshot,\n type RemoteWorker,\n type WorkstreamSnapshot,\n} from \"../state.js\";\nimport { isScratchWorkstream, listWorkstreams } from \"../workstream.js\";\nimport { resolveInitialTab } from \"./tui-launch-focus.js\";\nimport { importTui } from \"./tui-load.js\";\n\n// ─── Per-workstream loaded data ─────────────────────────────────────\n\n// PerWsData was the previous private shape of loadWorkstreamData.\n// Both the type and the loader now live at src/state.ts as the SDK\n// seam (WorkstreamSnapshot + loadWorkstreamSnapshot) so the new ink\n// TUI can consume them too. We keep `PerWsData` as a local alias to\n// avoid touching every renderer downstream.\ntype PerWsData = WorkstreamSnapshot & { remoteWorkers: RemoteWorker[] };\n\nfunction formatRemoteWorkersTable(rows: readonly RemoteWorker[]): string {\n const table = muTable({\n head: [\"task\", \"host\", \"path\"].map((heading) => pc.bold(heading)),\n });\n for (const row of rows) table.push([row.taskName, row.host, row.path]);\n return table.toString();\n}\n\n// ─── Workstream-set resolution ─────────────────────────────────────\n//\n// Both render modes accept TWO mutually-exclusive shapes (plus\n// auto-resolve):\n// -w X | -w X,Y | -w X -w Y explicit set (variadic + parseCsvFlag)\n// --all every workstream on this machine\n// (none) auto-resolve from $MU_SESSION/tmux (single ws)\n//\n// N=1 (single -w value, --all on a single-workstream machine, or\n// auto-resolve) renders single-mode (legacy column shape + flat JSON).\n// N≥2 stacks per-workstream cards in static modes or opens tabbed\n// per-workstream snapshots in TUI mode.\n\nexport interface StateOpts {\n // Variadic on every render mode.\n workstream?: string[];\n all?: boolean;\n json?: boolean;\n tui?: boolean;\n events?: number; // recent-events cap (default 20)\n}\n\nasync function resolveWorkstreamSet(db: Db, opts: StateOpts): Promise<string[]> {\n const explicitW = opts.workstream !== undefined && opts.workstream.length > 0;\n const explicitAll = opts.all === true;\n if (explicitAll && explicitW) {\n throw new UsageError(\"--all and -w/--workstream are mutually exclusive\");\n }\n if (explicitAll) {\n const all = await listWorkstreams(db);\n return all.map((w) => w.name);\n }\n if (explicitW) {\n // parseCsvFlag canonicalises repeat / comma / mixed forms into a\n // flat string[] (trimming fragments, dropping empty ones, and\n // rejecting blank whitespace-only ones as a usage error).\n const names = parseCsvFlag(opts.workstream, \"-w/--workstream\");\n const deduped = Array.from(new Set(names));\n if (deduped.length > 0) {\n // Strict validation: every entry must exist. A typo'd name\n // would silently render a half card.\n for (const n of deduped) {\n if (tryResolveWorkstreamId(db, n) === null) throw new WorkstreamNotFoundError(n);\n }\n return deduped;\n }\n }\n // No explicit -w (or it canonicalised away to nothing): auto-resolve\n // a single workstream from $MU_SESSION / tmux session.\n const single = await resolveOptionalWorkstream();\n if (single === null) return [];\n return [single];\n}\n\n// ─── JSON shape ─────────────────────────────────────────────────────\n//\n// Unified single flat shape for `mu state --json`.\n\nfunction fullJsonShape(d: PerWsData): Record<string, unknown> {\n return {\n workstreamName: d.workstreamName,\n agents: d.view.agents,\n orphans: d.view.orphans,\n tracks: d.tracks,\n ready: withRoiAll(d.ready),\n triage: withRoiAll(d.triage),\n inProgress: withRoiAll(d.inProgress),\n blocked: withRoiAll(d.blocked),\n recentClosed: withRoiAll(d.recentClosed),\n workspaces: d.workspaces,\n remoteWorkers: d.remoteWorkers,\n workspaceOrphans: d.workspaceOrphans,\n recent: d.recent,\n recentCommits: d.recentCommits,\n commitsBackend: d.commitsBackend ?? null,\n };\n}\n\n// ─── cmdState — dispatch ────────────────────────────────────────────\n\nexport async function cmdState(db: Db, opts: StateOpts): Promise<void> {\n // --tui mutual-exclusion checks: enforce BEFORE the JSON / render\n // branches so combining --tui with JSON errors loudly instead of\n // silently winning whichever branch ran first.\n if (opts.tui === true && opts.json === true) {\n throw new UsageError(\"--tui and --json are mutually exclusive (TUI is render-only)\");\n }\n\n const workstreams = await resolveWorkstreamSet(db, opts);\n\n // workstreams.length === 0 splits into THREE distinct user errors,\n // each with its own helpful message:\n // (a) --all on a machine with zero workstreams (truly empty universe)\n // (b) bare `mu state` outside a tmux session, with workstreams\n // on the machine but no way to auto-pick one (the most\n // common confusing case; bug_bare_mu_state_no_ws)\n // (c) bare `mu state --json`: same as (b) but JSON consumer; emit\n // {workstreams:[]} for back-compat\n if (workstreams.length === 0) {\n if (opts.json === true) {\n emitJson({ workstreams: [] });\n return;\n }\n const explicitAll = opts.all === true;\n if (explicitAll) {\n // (a) --all + truly empty machine\n console.log(pc.dim(\"(no workstreams) try `mu workstream init <name>`\"));\n return;\n }\n // (b) bare `mu state` with no auto-resolution path. Surface the\n // available workstreams so the user can pick one without a\n // separate `mu workstream list` round-trip.\n const all = await listWorkstreams(db);\n if (all.length === 0) {\n console.log(pc.dim(\"(no workstreams) try `mu workstream init <name>`\"));\n return;\n }\n const lines = [\n \"`mu state` could not auto-resolve a workstream.\",\n \"\",\n \"You're not inside a tmux session whose name matches a workstream,\",\n \"and `$MU_SESSION` is unset.\",\n \"\",\n `Workstreams on this machine: ${all.map((w) => w.name).join(\", \")}`,\n \"\",\n \"Try:\",\n ` mu state -w ${all[0]?.name ?? \"<name>\"} # pick one`,\n \" mu state --all # render every workstream\",\n \" mu --help # full verb list\",\n ];\n throw new UsageError(lines.join(\"\\n\"));\n }\n\n // ── Interactive TUI branch (explicit via --tui) ──\n // The legacy static card remains the default for `mu state` so it\n // stays visible to LLMs, screenshots, docs, and muscle-memory users.\n // Bare `mu` owns the TTY auto-route for humans. Mutual-exclusion with\n // --json is enforced before any static snapshot work.\n // Multi-workstream TUI is supported via tabs as of\n // feat_tui_multi_workstream (workstream `tui-impl`): the resolved\n // ws set is forwarded to <App>; Tab / Shift-Tab cycles tabs.\n if (opts.tui === true) {\n const { runTui } = await importTui();\n const initialActive = await resolveInitialTab(workstreams, db);\n await runTui(db, { workstreams: workstreams, initialActive });\n return;\n }\n\n const eventLimit = opts.events ?? 20;\n const perWs: PerWsData[] = [];\n for (const ws of workstreams) {\n perWs.push({\n ...(await loadWorkstreamSnapshot(db, ws, { eventLimit })),\n remoteWorkers: listRemoteWorkers(db, ws),\n });\n }\n const multi = workstreams.length > 1;\n\n // ── JSON: full static state shape ──\n if (opts.json === true) {\n if (multi) emitJson({ workstreams: perWs.map(fullJsonShape) });\n else {\n const single = perWs[0];\n if (single === undefined) throw new Error(\"invariant: workstreams non-empty\");\n emitJson(fullJsonShape(single));\n }\n return;\n }\n\n // ── Static human render ──\n renderFullMode(perWs);\n}\n\n// ─── Render: full mode (default `mu state`) ────────────────────────\n\n/** Past this many tasks, a workstream that is >90% closed gets the one-per-effort hint. */\nconst BIG_WORKSTREAM_TASKS = 300;\n\n/**\n * Scratch nudge: task-less helpers that sit idle past the threshold\n * (`idle` from `computeAgentIdle`) get a close hint so easy spawning\n * doesn't silently accumulate forgotten panes. Null when none.\n */\nexport function scratchIdleNudge(workstreamName: string, agents: LiveAgent[]): string | null {\n if (!isScratchWorkstream(workstreamName)) return null;\n const lingering = agents.filter((a) => a.idle === true);\n if (lingering.length === 0) return null;\n const names = lingering.map((a) => a.name).join(\", \");\n return `\\u26a0 ${lingering.length} idle scratch agent(s): ${names}. Close when done: mu agent close ${lingering[0]?.name ?? \"<name>\"} -w scratch`;\n}\n\nfunction renderFullMode(perWs: PerWsData[]): void {\n perWs.forEach((d, i) => {\n if (i > 0) console.log(\"\");\n renderFullCard(d);\n });\n}\n\nfunction renderFullCard(d: PerWsData): void {\n const { workstreamName, view, tracks, ready, inProgress, blocked, recentClosed, recent } = d;\n const staleWorkspaces = d.workspaces.filter((w) => isWorkspaceStale(w.commitsBehindMain));\n\n console.log(pc.bold(`State of mu-${workstreamName}`));\n console.log(\"\");\n console.log(pc.bold(`Agents (${view.agents.length} active, ${view.orphans.length} orphan)`));\n console.log(formatAgentsTable(view.agents));\n if (view.orphans.length > 0) {\n for (const orphan of view.orphans) {\n console.log(\n ` ${pc.yellow(\"orphan\")} ${pc.dim(orphan.paneId)} title=${pc.bold(orphan.title)} cli=${orphan.command}`,\n );\n }\n }\n const nudge = scratchIdleNudge(workstreamName, view.agents);\n if (nudge !== null) console.log(pc.yellow(nudge));\n // One workstream per effort: a long-lived catch-all is mostly history.\n const total = d.taskCount;\n const open = ready.length + inProgress.length + blocked.length + d.triage.length;\n if (total >= BIG_WORKSTREAM_TASKS && open * 10 < total) {\n console.log(\n pc.dim(\n `hint: ${total} tasks, ${open} open; start the next effort in a new <project>-<purpose> workstream`,\n ),\n );\n }\n console.log(\"\");\n console.log(pc.bold(`Tracks (${tracks.length})`));\n console.log(formatTracks(tracks));\n console.log(\"\");\n console.log(pc.bold(`Ready (${ready.length})`));\n console.log(ready.length === 0 ? pc.dim(\" (none)\") : formatTaskListTable(ready));\n console.log(\"\");\n if (d.triage.length > 0) {\n console.log(\n `${pc.bold(`Triage (${d.triage.length})`)} ${pc.dim(`accept: mu task accept <id> -w ${workstreamName} · decline: mu task close <id> --as rejected|duplicate --why ...`)}`,\n );\n console.log(formatTaskListTable(d.triage));\n console.log(\"\");\n }\n console.log(pc.bold(`In progress (${inProgress.length})`));\n console.log(inProgress.length === 0 ? pc.dim(\" (none)\") : formatTaskListTable(inProgress));\n console.log(\"\");\n console.log(pc.bold(`Blocked (${blocked.length})`));\n console.log(blocked.length === 0 ? pc.dim(\" (none)\") : formatTaskListTable(blocked));\n console.log(\"\");\n console.log(pc.bold(`Recent closed (${recentClosed.length})`));\n console.log(recentClosed.length === 0 ? pc.dim(\" (none)\") : formatTaskListTable(recentClosed));\n console.log(\"\");\n // Workspaces: warn line + tip when ANY row is ≥ WORKSPACE_STALE_THRESHOLD\n // commits behind main. Per bug_workspace_stale_parent_silent_drift.\n const workspacesHeader =\n staleWorkspaces.length > 0\n ? `${pc.bold(`Workspaces (${d.workspaces.length})`)} ${pc.yellow(`${GLYPH.warn} (${staleWorkspaces.length} stale ≥${WORKSPACE_STALE_THRESHOLD} commits behind):`)}`\n : pc.bold(`Workspaces (${d.workspaces.length})`);\n console.log(workspacesHeader);\n if (d.workspaces.length === 0) {\n console.log(pc.dim(\" (none)\"));\n } else {\n console.log(formatWorkspacesTable(d.workspaces));\n }\n if (staleWorkspaces.length > 0) {\n const example = staleWorkspaces[0]?.agentName ?? \"<agent>\";\n console.log(\n pc.yellow(\n `${GLYPH.warn} Tip: Refresh stale workspaces to land patches against current main: mu workspace refresh ${example}`,\n ),\n );\n }\n if (d.remoteWorkers.length > 0) {\n console.log(\"\");\n console.log(pc.bold(`Remote workers (${d.remoteWorkers.length})`));\n console.log(formatRemoteWorkersTable(d.remoteWorkers));\n }\n if (d.workspaceOrphans.length > 0) {\n console.log(\"\");\n console.log(\n pc.yellow(\n `Workspace orphans (${d.workspaceOrphans.length}, on disk but no DB row — will block --workspace spawns):`,\n ),\n );\n for (const o of d.workspaceOrphans) {\n console.log(` ${pc.bold(o.agentName)} ${pc.dim(o.path)}`);\n }\n console.log(pc.dim(` Run \\`mu workspace orphans -w ${workstreamName}\\` for cleanup hints.`));\n }\n console.log(\"\");\n console.log(pc.bold(`Recent activity (last ${recent.length} ops)`));\n if (recent.length === 0) {\n console.log(pc.dim(\" (none)\"));\n } else {\n for (const row of recent) printLogRow(row);\n }\n}\n\nexport function printBareNoWorkstreamsHint(): void {\n console.log(\"\");\n console.log(\"Next:\");\n console.log(\" Get started: mu workstream init <name>\");\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n//\n// wireStateCommands is called by buildProgram() in src/cli.ts. Wired\n// here so every per-namespace builder lives next to its cmd functions.\n\nimport type { Command } from \"commander\";\n\nexport function wireStateCommands(program: Command): void {\n program\n .command(\"state\")\n .description(\n \"Canonical state card: agents + orphans + tracks + ready/in-progress/blocked/recent-closed tasks + workspaces + remote workers + recent events. The agent/API-facing static state surface. Default prints the static card; pass --tui to enter the interactive ink-based dashboard. -w accepts repeat or comma-separate (or both); --all is sugar for every workstream on this machine. N≥2 stacks per-workstream cards.\",\n )\n .option(\n \"-w, --workstream <names...>\",\n \"workstream(s) to render (repeat or comma-separate; or both; defaults to $MU_SESSION or current tmux session)\",\n )\n .option(\"--all\", \"include every workstream on this machine\")\n .option(\n \"--tui\",\n \"interactive TUI (rounded-border dashboard with cards + popups; multi-ws via Tab/Shift-Tab tabs)\",\n )\n .option(\"--events <n>\", \"how many recent log entries (ops) to include (default 20)\", parseLines)\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as StateOpts;\n return handle((db) => cmdState(db, opts), this as Command)();\n });\n}\n","// mu — `mu sync`: ONE verb, whose bare form is a PEER STATUS REPORT.\n//\n// The sync itself is incidental. Every mu invocation already flushes and\n// ingests (the ambient hook in src/cli/handle.ts), so a verb that only\n// did that would exist for reassurance. What no other command answers is\n// \"who are my peers, how far behind am I, and when did I last hear from\n// them\" — so that is what the bare form prints:\n//\n// $ mu sync\n// flushed 14 ops · ingested 22 from 1 peer\n// machine last seen behind\n// devbox 2m ago 0\n// desktop 3d ago 47 ← stale\n//\n// It keeps its bare form for scripting ergonomics too: `rsync ... && mu\n// sync` reads correctly where `rsync ... && mu state` reads like an\n// accident.\n//\n// TWO FLAGS, AND ONLY TWO, because nothing else can express them:\n//\n// --from <path> a DIFFERENT READER — a peer's `mu.db` ops table via\n// SQLite rather than a JSONL segment. For an sshfs\n// mount or a copied file.\n// --repair <peer> reset that peer's watermark and re-read its segment\n// from zero. Safe because ingest is idempotent via\n// UNIQUE (machine_id, hlc).\n//\n// DELIBERATELY ABSENT: `mu peers` (folded into the bare form here), and\n// `--to <dir>` / `--from <dir>`. A one-off directory needs no flag —\n// `MU_SYNC_DIR=/mnt/usb mu state` already ingests from the USB stick\n// using the repo's existing env-var-override idiom, and adding a flag for\n// it would be a second way to say the same thing.\n//\n// ALSO ABSENT, permanently: `--push` / `--pull <host>`. mu reads and\n// writes FILES; the operator owns transport (a standing ROADMAP pledge).\n// When a peer is stale we PRINT an rsync line and let them paste it.\n//\n// This verb opts OUT of the ambient hook (`ambientSync: false`) and runs\n// the pass itself. Not to skip work — to report honest numbers. If the\n// hook ran first, its ingest would have consumed everything and the\n// report would print \"ingested 0\" immediately after doing the opposite.\n\nimport { emitJson, handle, JSON_OPT } from \"../cli.js\";\nimport type { Db } from \"../db.js\";\nimport { muTable, type NextStep, pc, printNextSteps } from \"../output.js\";\nimport { type IngestResult, syncDir, syncPass } from \"../segments.js\";\nimport {\n type IngestFromDbResult,\n ingestFromDb,\n type PeerStatus,\n peerStatuses,\n repairPeer,\n transportNextSteps,\n} from \"../sync.js\";\nimport { relTime } from \"./format.js\";\n\nexport interface SyncCmdOptions {\n json?: boolean;\n from?: string;\n repair?: string;\n}\n\n/** Relative time, or a marker when transport never delivered anything. */\nfunction lastSeen(peer: PeerStatus): string {\n if (peer.ageMs === null) return \"—\";\n return `${relTime(peer.ageMs)} ago`;\n}\n\nfunction setupNextSteps(): NextStep[] {\n return [\n {\n intent: \"Turn sync on (one env var, on every machine)\",\n command: \"export MU_SYNC_DIR=$HOME/Sync/mu\",\n },\n {\n intent: \"Then share that folder (Syncthing, rsync, a USB stick)\",\n command: \"# any file-mover works: segments are append-only, single-writer\",\n },\n ];\n}\n\nfunction nextSteps(dir: string, peers: readonly PeerStatus[]): NextStep[] {\n const steps: NextStep[] = [...transportNextSteps(dir, peers)];\n const damaged = peers.filter((p) => p.behind > 0);\n const first = damaged[0];\n if (first !== undefined) {\n steps.push({\n intent: \"Re-read a peer's segment from zero\",\n command: `mu sync --repair ${first.short}`,\n });\n }\n if (steps.length === 0) {\n steps.push({ intent: \"See what landed\", command: \"mu log -n 20\" });\n }\n return steps;\n}\n\nfunction renderPeerTable(peers: readonly PeerStatus[]): string {\n if (peers.length === 0) {\n return pc.dim(\" (no peers yet — drop another machine's segment in the sync dir)\");\n }\n const table = muTable({\n head: [pc.bold(\"machine\"), pc.bold(\"last seen\"), pc.bold(\"behind\"), pc.bold(\"\")],\n });\n for (const peer of peers) {\n const flags: string[] = [];\n if (peer.stale) flags.push(pc.yellow(\"← stale\"));\n if (peer.conflictCopy) flags.push(pc.dim(\"(conflict copy)\"));\n table.push([peer.short, lastSeen(peer), String(peer.behind), flags.join(\" \")]);\n }\n return table.toString();\n}\n\n/** \"ingested 22 from 2 peers\", or the honest nothing-happened form. */\nfunction describeIngest(results: readonly IngestResult[]): string {\n const total = results.reduce((sum, r) => sum + r.applied, 0);\n const from = results.filter((r) => r.applied > 0).length;\n if (total === 0) return \"ingested 0\";\n return `ingested ${total} from ${from} peer${from === 1 ? \"\" : \"s\"}`;\n}\n\nexport async function cmdSync(db: Db, opts: SyncCmdOptions = {}): Promise<void> {\n const dir = syncDir();\n\n // `--from <path>` is the one shape that works with sync unconfigured:\n // it names its source outright, so there is no dir to need.\n if (opts.from !== undefined) {\n const result = ingestFromDb(db, opts.from);\n // Flush afterwards so the ops we just took on are in our own segment\n // for any peer sharing the dir — that is how a laptop relays the\n // devserver's work to a third machine (gossip, for free).\n const flushed = dir === null ? null : await syncPass(db, dir);\n emitFrom(db, result, flushed?.flushed.appended ?? 0, dir, opts);\n return;\n }\n\n if (dir === null) {\n if (opts.json === true) {\n emitJson({\n syncDir: null,\n enabled: false,\n flushed: 0,\n ingested: [],\n peers: [],\n nextSteps: setupNextSteps(),\n });\n return;\n }\n console.log(pc.dim(\"sync is off (MU_SYNC_DIR is not set)\"));\n printNextSteps(setupNextSteps());\n return;\n }\n\n // `--repair` is just \"reset the watermark\"; the pass below then\n // re-reads that peer's segment from zero. Resolved BEFORE the pass so a\n // bad ref errors without half-doing anything.\n const repaired = opts.repair === undefined ? null : repairPeer(db, opts.repair, dir);\n\n const pass = await syncPass(db, dir);\n const peers = peerStatuses(db, dir);\n if (pass.flushed.lockBusy === true) {\n process.stderr.write(\n \"mu: sync: own segment is locked by another mu process; local ops stay pending and the next flush appends them\\n\",\n );\n }\n\n if (opts.json === true) {\n emitJson({\n syncDir: dir,\n enabled: true,\n repaired: repaired === null ? null : repaired.machineId,\n flushed: pass.flushed.appended,\n skippedLocal: pass.flushed.skippedLocal,\n selfRepaired: pass.flushed.selfRepaired,\n ingested: pass.ingested.map((r) => ({\n machineId: r.machineId,\n applied: r.applied,\n changed: r.changed,\n watermark: r.watermark,\n defects: r.defects,\n })),\n peers,\n nextSteps: nextSteps(dir, peers),\n });\n return;\n }\n\n if (repaired !== null) {\n console.log(pc.dim(`repaired ${repaired.short}: watermark reset, re-reading from zero`));\n }\n if (pass.flushed.selfRepaired !== null) {\n const d = pass.flushed.selfRepaired;\n console.log(\n pc.yellow(\n ` own segment was defective past line ${d.line} (${d.kind}: ${d.detail}) — truncated to the last good line and regenerated from the ops table`,\n ),\n );\n }\n console.log(`flushed ${pass.flushed.appended} ops · ${describeIngest(pass.ingested)}`);\n console.log(renderPeerTable(peers));\n for (const result of pass.ingested) {\n for (const defect of result.defects) {\n console.log(\n pc.yellow(\n ` ${result.machineId.slice(0, 8)}: ${defect.kind} at line ${defect.line} — ${defect.detail}`,\n ),\n );\n }\n }\n printNextSteps(nextSteps(dir, peers));\n}\n\nfunction emitFrom(\n db: Db,\n result: IngestFromDbResult,\n flushed: number,\n dir: string | null,\n opts: SyncCmdOptions,\n): void {\n const peers = dir === null ? [] : peerStatuses(db, dir);\n if (opts.json === true) {\n emitJson({\n from: result.path,\n read: result.read,\n changed: result.changed,\n skippedLocal: result.skippedLocal,\n flushed,\n peers,\n nextSteps: [{ intent: \"See what landed\", command: \"mu log -n 20\" }],\n });\n return;\n }\n console.log(\n `read ${result.read} ops from ${pc.bold(result.path)} · ${result.changed} changed rows`,\n );\n if (result.skippedLocal > 0) {\n console.log(pc.dim(` skipped ${result.skippedLocal} machine-local ops (they never travel)`));\n }\n printNextSteps([{ intent: \"See what landed\", command: \"mu log -n 20\" }]);\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n\nimport type { Command } from \"commander\";\n\nexport function wireSyncCommand(program: Command): void {\n program\n .command(\"sync\")\n .description(\"Report peer status (flush + ingest happen on every mu invocation anyway)\")\n .option(...JSON_OPT)\n .option(\"--from <path>\", \"ingest from a peer's mu.db directly (sshfs mount or copied file)\")\n .option(\"--repair <peer>\", \"reset that peer's watermark and re-read its segment from zero\")\n .action(function () {\n const opts = (this as Command).opts() as SyncCmdOptions;\n // ambientSync: false — this verb IS the pass, and running it twice\n // would print \"ingested 0\" for work the hook had just done.\n return handle((db) => cmdSync(db, opts), this as Command, { ambientSync: false })();\n });\n}\n","// mu — `mu undo [group]`: revert one action by emitting inverse ops.\n//\n// The verb disappeared in v9 along with src/cli/snapshot.ts (it lived\n// there, not in its own module), so this re-wires it on the new\n// substrate. Semantics are entirely different: the old undo swapped the whole DB\n// file back to a snapshot, reverting unrelated workstreams too. This\n// emits inverse ops for ONE group.\n//\n// Shaped to the repo's established conventions:\n// * DRY RUN BY DEFAULT, `--yes` to apply — same as `workstream teardown`.\n// * No argument means \"tell me what you WOULD undo\", never \"guess and\n// do it\". It lists recent groups so the ids are discoverable without\n// needing `mu log` (whose group surface is v2-log-verb's).\n// * `--json` shape + a `Next:` block on every path.\n\nimport { emitJson, handle, JSON_OPT, parsePositiveInt } from \"../cli.js\";\nimport type { Db } from \"../db.js\";\nimport { type NextStep, pc, printNextSteps } from \"../output.js\";\nimport {\n type GroupSummary,\n listRecentGroups,\n NothingToUndoError,\n planUndo,\n resolveGroupId,\n type UndoPlan,\n undoGroup,\n} from \"../undo.js\";\n\nexport interface UndoCmdOptions {\n json?: boolean;\n yes?: boolean;\n force?: boolean;\n /** How many groups to list when no group is named. */\n limit?: number;\n}\n\nconst short = (id: string): string => id.slice(0, 8);\n\nfunction describeGroup(group: GroupSummary): string {\n const what = group.intents.length > 0 ? group.intents.join(\", \") : \"(no intent)\";\n const actor = group.actor !== null && group.actor !== \"\" ? ` by ${group.actor}` : \"\";\n return `${what}${actor} — ${group.ops} op${group.ops === 1 ? \"\" : \"s\"}`;\n}\n\n/** Steps that make the next move obvious from wherever the operator is. */\nfunction nextStepsForPlan(\n plan: UndoPlan,\n applied: boolean,\n undoGroupId?: string | null,\n): NextStep[] {\n if (!applied) {\n return [\n { intent: \"Apply this undo\", command: `mu undo ${short(plan.groupId)} --yes` },\n { intent: \"Inspect the group's ops\", command: `mu log --group ${short(plan.groupId)}` },\n ];\n }\n // No row changed, so the undo recorded no ops and there is no group\n // to redo.\n if (undoGroupId === null || undoGroupId === undefined) {\n return [\n { intent: \"Inspect the group's ops\", command: `mu log --group ${short(plan.groupId)}` },\n ];\n }\n return [\n { intent: \"Redo (undo the undo)\", command: `mu undo ${short(undoGroupId)} --yes` },\n { intent: \"Verify the log and tables still agree\", command: \"mu doctor --deep\" },\n ];\n}\n\n/** No group named: show what undo WOULD target, plus recent groups so the\n * ids are discoverable. */\nfunction listGroups(db: Db, opts: UndoCmdOptions): void {\n const groups = listRecentGroups(db, opts.limit ?? 10);\n if (groups.length === 0) throw new NothingToUndoError();\n\n const target = groups[0];\n if (target === undefined) throw new NothingToUndoError();\n\n if (opts.json === true) {\n emitJson({\n target: {\n groupId: target.groupId,\n intents: target.intents,\n ops: target.ops,\n when: target.when,\n },\n groups: groups.map((g) => ({\n groupId: g.groupId,\n intents: g.intents,\n actor: g.actor,\n ops: g.ops,\n when: g.when,\n })),\n nextSteps: [\n {\n intent: \"Preview undoing the most recent action\",\n command: `mu undo ${short(target.groupId)}`,\n },\n ],\n });\n return;\n }\n\n console.log(`${pc.bold(\"mu undo\")} — most recent undoable action:`);\n console.log(` ${pc.bold(short(target.groupId))} ${describeGroup(target)}`);\n console.log(\"\");\n console.log(pc.dim(\"recent groups (newest first):\"));\n for (const group of groups) {\n const marker = group.groupId === target.groupId ? pc.green(\"*\") : \" \";\n console.log(` ${marker} ${pc.bold(short(group.groupId))} ${pc.dim(describeGroup(group))}`);\n }\n printNextSteps([\n {\n intent: \"Preview undoing the most recent action\",\n command: `mu undo ${short(target.groupId)}`,\n },\n { intent: \"Preview a specific group\", command: \"mu undo <group>\" },\n ]);\n}\n\nfunction printPlan(plan: UndoPlan): void {\n const what = plan.intents.length > 0 ? plan.intents.join(\", \") : \"(no intent)\";\n console.log(`${pc.bold(\"mu undo\")} ${short(plan.groupId)} — would revert ${pc.bold(what)}`);\n if (plan.inverses.length === 0) {\n console.log(pc.yellow(\" nothing to revert (already undone, or the group changed nothing)\"));\n return;\n }\n for (const inverse of plan.inverses) {\n const verb = inverse.op === \"del\" ? pc.red(\"delete \") : pc.green(\"restore\");\n console.log(` ${verb} ${inverse.summary}`);\n }\n if (plan.skipped > 0) {\n console.log(pc.dim(` (${plan.skipped} op(s) need no inverse)`));\n }\n if (plan.superseded) {\n console.log(\"\");\n console.log(pc.yellow(\" WARNING: this group has been SUPERSEDED by later work.\"));\n for (const inverse of plan.inverses) {\n for (const conflict of inverse.supersededBy) {\n const field = conflict.field === \"<row>\" ? \"the row\" : conflict.field;\n console.log(\n pc.yellow(\n ` ${inverse.key}: ${field} was changed since by ${short(conflict.groupId)}` +\n `${conflict.intent === null ? \"\" : ` (${conflict.intent})`}`,\n ),\n );\n }\n }\n console.log(\n pc.dim(\" Undoing would DISCARD that newer work. Pass --force with --yes to do it anyway.\"),\n );\n }\n}\n\nexport async function cmdUndo(\n db: Db,\n groupRef: string | undefined,\n opts: UndoCmdOptions = {},\n): Promise<void> {\n // No argument: report, never guess. Listing the groups is also how the\n // ids become discoverable.\n if (groupRef === undefined) {\n listGroups(db, opts);\n return;\n }\n\n const groupId = resolveGroupId(db, groupRef);\n\n // Dry run by default (the `workstream teardown` / `db import` pattern).\n if (opts.yes !== true) {\n const plan = planUndo(db, groupId);\n if (opts.json === true) {\n emitJson({\n dryRun: true,\n groupId: plan.groupId,\n intents: plan.intents,\n when: plan.when,\n superseded: plan.superseded,\n inverses: plan.inverses,\n skipped: plan.skipped,\n nextSteps: nextStepsForPlan(plan, false),\n });\n return;\n }\n printPlan(plan);\n console.log(pc.dim(\"\\n(dry-run; rerun with --yes to apply)\"));\n printNextSteps(nextStepsForPlan(plan, false));\n return;\n }\n\n const result = undoGroup(db, groupId, {\n ...(opts.force === true ? { force: true } : {}),\n });\n\n if (opts.json === true) {\n emitJson({\n dryRun: false,\n groupId: result.plan.groupId,\n intents: result.plan.intents,\n undoGroupId: result.undoGroupId,\n applied: result.applied,\n inverses: result.plan.inverses,\n forced: opts.force === true,\n nextSteps: nextStepsForPlan(result.plan, true, result.undoGroupId),\n });\n return;\n }\n\n const what = result.plan.intents.length > 0 ? result.plan.intents.join(\", \") : \"(no intent)\";\n const label = `${pc.bold(short(result.plan.groupId))} (${what})`;\n if (result.undoGroupId === null) {\n console.log(\n pc.yellow(`${label}: nothing changed (already undone, or the group changed nothing)`),\n );\n printNextSteps(nextStepsForPlan(result.plan, true, null));\n return;\n }\n console.log(`Undid ${label}`);\n for (const inverse of result.plan.inverses) {\n console.log(pc.dim(` ${inverse.summary}`));\n }\n console.log(\n pc.dim(\n ` ${result.applied} row change(s), recorded as group ${pc.bold(short(result.undoGroupId))}`,\n ),\n );\n if (opts.force === true && result.plan.superseded) {\n console.log(pc.yellow(\" --force: newer edits to those fields were discarded.\"));\n }\n // The undo is itself an op in its own group, so redo is just undo.\n console.log(pc.dim(` This undo is itself undoable: mu undo ${short(result.undoGroupId)} --yes`));\n printNextSteps(nextStepsForPlan(result.plan, true, result.undoGroupId));\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n\nimport type { Command } from \"commander\";\n\nexport function wireUndoCommand(program: Command): void {\n program\n .command(\"undo [group]\")\n .description(\n \"Revert one action by emitting inverse ops (dry-run by default; --yes applies). \" +\n \"With no group, lists recent undoable actions.\",\n )\n .option(...JSON_OPT)\n .option(\"--yes\", \"actually apply the inverse (default is a dry run)\")\n .option(\"--force\", \"apply even when the group was superseded by later work (discards it)\")\n .option(\"-n, --limit <n>\", \"how many recent groups to list\", parsePositiveInt)\n .action(function (group: string | undefined) {\n const opts = (this as Command).opts() as UndoCmdOptions;\n return handle((db) => cmdUndo(db, group, opts), this as Command)();\n });\n}\n","// mu — `mu workspace` verbs (list / refresh / free / commits / path / orphans).\n//\n// Workspace CREATION is not a standalone verb: it happens inside\n// `mu agent spawn --workspace`. Between waves use `refresh`; for\n// destructive cleanup use `free`.\n//\n// Per-agent VCS workspaces (registry layer on top of vcs.ts).\n//\n// Extracted from src/cli.ts as part of refactor_split_large_src_files.\n\nimport {\n assertAgentInWorkstream,\n emitJson,\n emitJsonCollection,\n formatWorkspacesTable,\n resolveEntityRef,\n resolveWorkstream,\n} from \"../cli.js\";\nimport { type Db, tryResolveWorkstreamId, WorkstreamNotFoundError } from \"../db.js\";\nimport { type NextStep, pc, printNextSteps } from \"../output.js\";\nimport {\n decorateWithStaleness,\n freeWorkspace,\n getWorkspaceForAgent,\n listAllOrphanWorkspaces,\n listCommitsForWorkspace,\n listWorkspaceOrphans,\n listWorkspaces,\n refreshWorkspace,\n type StrandedWorkspaceOrphan,\n WorkspaceNotFoundError,\n} from \"../workspace.js\";\n\nexport async function cmdWorkspaceList(\n db: Db,\n opts: { workstream?: string; all?: boolean; json?: boolean },\n): Promise<void> {\n const workstream = opts.all ? undefined : await resolveWorkstream(opts.workstream);\n const rows = listWorkspaces(db, workstream);\n // decorateWithStaleness is the staleness signal from\n // bug_workspace_stale_parent_silent_drift: ask each row's backend how\n // many commits its parent_ref is behind main. Pure observation; no\n // automatic fetch.\n const decorated = await decorateWithStaleness(rows);\n if (opts.json) {\n emitJsonCollection(decorated);\n return;\n }\n if (decorated.length === 0) {\n console.log(pc.dim(workstream ? `(no workspaces in ${workstream})` : \"(no workspaces)\"));\n return;\n }\n console.log(formatWorkspacesTable(decorated));\n}\n\nexport async function cmdWorkspaceFree(\n db: Db,\n rawAgent: string,\n opts: { commit?: boolean; workstream?: string; json?: boolean },\n): Promise<void> {\n const { name: agent } = await resolveEntityRef(db, rawAgent, opts, \"workspace\");\n assertAgentInWorkstream(db, agent, opts.workstream);\n const ws = await resolveWorkstream(opts.workstream);\n const r = await freeWorkspace(db, agent, { commit: opts.commit ?? false, workstream: ws });\n if (opts.json) {\n emitJson({ agentName: agent, ...r });\n return;\n }\n if (!r.removed && !r.rowDeleted) {\n console.log(pc.dim(`no workspace for ${agent} (already gone?)`));\n return;\n }\n const committed = r.committedRef\n ? pc.dim(` (auto-committed: ${r.committedRef.slice(0, 12)})`)\n : \"\";\n console.log(`Freed workspace for ${pc.bold(agent)}${committed}`);\n if (r.branch) console.log(pc.dim(` commits kept on branch ${r.branch}`));\n}\n\nexport async function cmdWorkspaceRefresh(\n db: Db,\n rawAgent: string,\n opts: { workstream?: string; from?: string; json?: boolean } = {},\n): Promise<void> {\n const { name: agent } = await resolveEntityRef(db, rawAgent, opts, \"workspace\");\n assertAgentInWorkstream(db, agent, opts.workstream);\n const workstream = await resolveWorkstream(opts.workstream);\n const refreshOpts: Parameters<typeof refreshWorkspace>[1] = { agent, workstream };\n if (opts.from !== undefined) refreshOpts.fromRef = opts.from;\n const r = await refreshWorkspace(db, refreshOpts);\n const nextSteps: NextStep[] = [\n {\n intent: \"cd into the refreshed workspace\",\n command: `cd $(mu workspace path ${agent} -w ${workstream})`,\n },\n {\n intent: \"List commits replayed on top of the new base\",\n command: `mu workspace commits ${agent} -w ${workstream}`,\n },\n ];\n if (opts.json) {\n emitJson({ agent, ...r, nextSteps });\n return;\n }\n if (r.replayed.length === 0) {\n console.log(`Workspace ${pc.bold(agent)} already at ${pc.dim(r.fromRef)} — nothing to replay.`);\n } else {\n console.log(\n `Refreshed workspace ${pc.bold(agent)} onto ${pc.dim(r.fromRef)} ${pc.dim(`(backend=${r.vcs}, ${r.replayed.length} commit${r.replayed.length === 1 ? \"\" : \"s\"} replayed)`)}`,\n );\n for (const subject of r.replayed) {\n console.log(` ${pc.dim(\"•\")} ${subject}`);\n }\n }\n printNextSteps(nextSteps);\n}\n\nexport async function cmdWorkspaceCommits(\n db: Db,\n rawAgent: string,\n opts: { workstream?: string; since?: string; json?: boolean } = {},\n): Promise<void> {\n const { name: agent } = await resolveEntityRef(db, rawAgent, opts, \"workspace\");\n assertAgentInWorkstream(db, agent, opts.workstream);\n const workstream = await resolveWorkstream(opts.workstream);\n const listOpts: Parameters<typeof listCommitsForWorkspace>[2] = { workstream };\n if (opts.since !== undefined) listOpts.since = opts.since;\n const r = await listCommitsForWorkspace(db, agent, listOpts);\n if (opts.json) {\n emitJson({\n items: r.commits,\n count: r.commits.length,\n vcs: r.vcs,\n baseRef: r.baseRef,\n workspacePath: r.workspacePath,\n });\n return;\n }\n if (r.commits.length === 0) {\n console.log(pc.dim(`(no commits in ${agent} since ${r.baseRef.slice(0, 12)})`));\n return;\n }\n // Plain `<sha> <subject>` per line, oldest-first — the format the\n // dogfood incantation produced via `git log --oneline base..HEAD`.\n // Stays grep/awk/jq-friendly without --json.\n for (const c of r.commits) {\n console.log(`${c.sha} ${c.subject}`);\n }\n}\n\nexport async function cmdWorkspacePath(\n db: Db,\n rawAgent: string,\n opts: { workstream?: string; json?: boolean } = {},\n): Promise<void> {\n const { name: agent } = await resolveEntityRef(db, rawAgent, opts, \"workspace\");\n assertAgentInWorkstream(db, agent, opts.workstream);\n const wsName = await resolveWorkstream(opts.workstream);\n const ws = getWorkspaceForAgent(db, agent, wsName);\n if (!ws) throw new WorkspaceNotFoundError(agent);\n if (opts.json) {\n emitJson({ agentName: agent, path: ws.path, backend: ws.backend });\n return;\n }\n // Print just the path, no decoration: usable for `cd $(mu workspace path X)`.\n console.log(ws.path);\n}\n\nexport async function cmdWorkspaceOrphans(\n db: Db,\n opts: { workstream?: string; all?: boolean; json?: boolean } = {},\n): Promise<void> {\n // --all overrides scope: ignore -w and scan every workstream subdir\n // under <state-dir>/workspaces/, INCLUDING workstreams whose row is\n // gone (those orphans get `stranded: true`). See\n // workspace_orphans_misses_destroyed_workstreams.\n if (opts.all === true) {\n const orphans = listAllOrphanWorkspaces(db);\n const sample = orphans[0];\n const nextSteps: NextStep[] =\n sample === undefined\n ? []\n : [\n {\n intent: \"Remove a specific orphan dir (git: also prunes worktree registry)\",\n command: `(cd <project-root> && git worktree remove --force ${sample.path}) || rm -rf ${sample.path}`,\n },\n ];\n if (opts.json) {\n // audit_json_envelope_uniformity: collection envelope plus the\n // sibling nextSteps field. workstreamName is omitted because\n // --all spans the whole state dir.\n emitJson({ items: orphans, count: orphans.length, nextSteps });\n return;\n }\n if (orphans.length === 0) {\n console.log(pc.dim(\"(no orphan workspace dirs across all workstreams)\"));\n return;\n }\n console.log(pc.yellow(`${orphans.length} orphan workspace dir(s) across all workstreams:`));\n const grouped = new Map<string, StrandedWorkspaceOrphan[]>();\n for (const o of orphans) {\n const list = grouped.get(o.workstreamName) ?? [];\n list.push(o);\n grouped.set(o.workstreamName, list);\n }\n for (const [wsName, list] of grouped) {\n const sampleEntry = list[0];\n const strandedTag =\n sampleEntry?.stranded === true ? pc.red(\" (stranded: workstream teardowned)\") : \"\";\n console.log(` ${pc.bold(wsName)}${strandedTag}`);\n for (const o of list) {\n console.log(` ${pc.bold(o.agentName)} ${pc.dim(o.path)}`);\n }\n }\n printNextSteps(nextSteps);\n return;\n }\n\n const workstream = await resolveWorkstream(opts.workstream);\n // Tighten resolution: a typo'd or destroyed workstream name used to\n // happy-path to \"no orphans\" because listWorkspaceOrphans returns []\n // when the dir doesn't exist. Match the mutating verbs and surface\n // WorkstreamNotFoundError (exit 3) instead. See\n // workspace_orphans_misses_destroyed_workstreams option C.\n if (tryResolveWorkstreamId(db, workstream) === null) {\n throw new WorkstreamNotFoundError(workstream);\n }\n const orphans = listWorkspaceOrphans(db, workstream);\n const nextSteps: NextStep[] =\n orphans.length === 0\n ? []\n : [\n {\n intent: \"Remove a specific orphan dir (git: also prunes worktree registry)\",\n command: `(cd <project-root> && git worktree remove --force ${orphans[0]?.path}) || rm -rf ${orphans[0]?.path}`,\n },\n ];\n if (opts.json) {\n // audit_json_envelope_uniformity: items + count for the\n // collection envelope; workstreamName + nextSteps as siblings.\n emitJson({\n workstreamName: workstream,\n items: orphans,\n count: orphans.length,\n nextSteps,\n });\n return;\n }\n if (orphans.length === 0) {\n console.log(pc.dim(`(no orphan workspace dirs in ${workstream})`));\n return;\n }\n console.log(pc.yellow(`${orphans.length} orphan workspace dir(s) in ${pc.bold(workstream)}:`));\n for (const o of orphans) {\n console.log(` ${pc.bold(o.agentName)} ${pc.dim(o.path)}`);\n }\n printNextSteps(nextSteps);\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n//\n// wireWorkspaceCommands is called by buildProgram() in src/cli.ts. Wired here so\n// every per-namespace builder lives next to its cmd functions.\n\nimport type { Command } from \"commander\";\nimport { handle, JSON_OPT, WORKSTREAM_OPT } from \"../cli.js\";\n\nexport function wireWorkspaceCommands(program: Command): void {\n const workspace = program\n .command(\"workspace\")\n .description(\"VCS workspace commands (per-agent isolated working copies)\");\n\n workspace\n .command(\"list\")\n .description(\"List workspaces in the current workstream (--all spans every workstream)\")\n .option(\"--all\", \"list workspaces across every workstream\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as {\n all?: boolean;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdWorkspaceList(db, opts), this as Command)();\n });\n\n workspace\n .command(\"refresh <agent>\")\n .description(\n \"Rebase an agent's workspace onto a fresh base WITHOUT touching the agent or pane. Default base = the backend's tracked main (origin/HEAD for git, trunk() for jj/sl); override with --from <ref>. Refuses on dirty WC (git/sl) with the file list and a Next: hint to commit/stash. Records the new fork point as the workspace's parent_ref (never moving it backward). On rebase conflict exits 5 and leaves parent_ref unchanged: git and sl abort the rebase and leave the workspace unchanged; jj keeps the rebase with the conflicts committed in place. After resolving, run refresh again to record the new base. The `none` backend errors (refresh requires a real VCS).\",\n )\n .option(\"--from <ref>\", \"override the rebase target (default: backend's tracked main)\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (agent: string) {\n const opts = (this as Command).opts() as {\n from?: string;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdWorkspaceRefresh(db, agent, opts), this as Command)();\n });\n\n workspace\n .command(\"free <agent>\")\n .description(\n \"Tear down an agent's workspace. With --commit, attempt to auto-commit pending changes first; without it, pending changes are lost. For git, --commit also creates a branch mu/<workstream>/<agent>-<sha> when the worktree's commits are on no branch, so they survive removal.\",\n )\n .option(\"--commit\", \"auto-commit pending changes before removing the workspace\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (agent: string) {\n const opts = (this as Command).opts() as {\n commit?: boolean;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdWorkspaceFree(db, agent, opts), this as Command)();\n });\n\n workspace\n .command(\"commits <agent>\")\n .description(\n \"Print commits the agent's workspace has on top of its recorded parent_ref (the fork point), oldest-first. Default text output is `<sha> <subject>` per line; --json emits `{items,count,vcs,baseRef,workspacePath}` for piping. --since <ref> overrides the base. The `none` backend errors (no fork point to compare against).\",\n )\n .option(\"--since <ref>\", \"override the base ref (default: workspace's recorded parent_ref)\")\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (agent: string) {\n const opts = (this as Command).opts() as {\n since?: string;\n workstream?: string;\n json?: boolean;\n };\n return handle((db) => cmdWorkspaceCommits(db, agent, opts), this as Command)();\n });\n\n workspace\n .command(\"path <agent>\")\n .description(\n \"Print the on-disk path of an agent's workspace. Usable as `cd $(mu workspace path foo)`.\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function (agent: string) {\n const opts = (this as Command).opts() as { workstream?: string; json?: boolean };\n return handle((db) => cmdWorkspacePath(db, agent, opts), this as Command)();\n });\n\n workspace\n .command(\"orphans\")\n .description(\n \"List on-disk workspace dirs in <state-dir>/workspaces/<workstream>/ that have no DB row. These block subsequent `--workspace` spawns; surfaced by bug_workspace_orphan_not_in_state. With --all, scans every workstream subdir under <state-dir>/workspaces/ INCLUDING workstreams whose row is gone (those rows are tagged `stranded: workstream teardowned`); --all overrides -w. With -w <unknown>, errors via WorkstreamNotFoundError (exit 3) instead of silently printing 'no orphans'. Cleanup recipe shown in Next: hints.\",\n )\n .option(\n \"--all\",\n \"scan every workstream subdir on disk (overrides -w; surfaces dirs whose workstream row is gone as `stranded`)\",\n )\n .option(...WORKSTREAM_OPT)\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as {\n workstream?: string;\n all?: boolean;\n json?: boolean;\n };\n return handle((db) => cmdWorkspaceOrphans(db, opts), this as Command)();\n });\n}\n","// mu — `mu workstream` verbs (init / list / teardown).\n//\n// A workstream = one mux session (`mu-<name>`) + every DB row tagged\n// with that name (agents / tasks / edges / notes / workspaces / logs).\n// `init` creates the session + DB row pair; `list` shows\n// every workstream on the machine; `teardown` is the symmetric inverse,\n// two-phase by default (dry-run; `--yes` commits).\n//\n// Extracted from src/cli.ts as part of refactor_split_large_src_files.\n\nimport { basename } from \"node:path\";\nimport {\n emitJson,\n emitJsonCollection,\n formatTornDownWorkstreamsTable,\n formatWorkstreamsTable,\n resolveWorkstream,\n UsageError,\n} from \"../cli.js\";\nimport type { Db } from \"../db.js\";\nimport { activeMux } from \"../mux.js\";\nimport { muTable, type NextStep, pc, printNextSteps } from \"../output.js\";\nimport {\n assertWorkstreamInitable,\n ensureWorkstream,\n ensureWorkstreamSession,\n listEmptyWorkstreams,\n listTornDownWorkstreams,\n listUnregisteredMuxWorkstreams,\n listWorkstreams,\n summarizeWorkstream,\n teardownWorkstream,\n} from \"../workstream.js\";\n\nexport async function cmdInit(db: Db, name: string, opts: { json?: boolean } = {}): Promise<void> {\n assertWorkstreamInitable(name);\n const sessionName = `mu-${name}`;\n const dbCreated = ensureWorkstream(db, name);\n // Load-bearing: `workstream init` IS session creation.\n const mux = await activeMux();\n // Creates the session with its placeholder `_mu` window, or repairs\n // a missing `_mu` (the operator killed it after the first spawn;\n // without it, tmux a -t mu-<ws> lands on an agent's pane instead of\n // the orchestration shell).\n // (review_bug_workstream_init_does_not_repair_missing_mu_window)\n const { created: sessionCreated, muWindowRepaired } = await ensureWorkstreamSession(sessionName);\n const sessionAlready = !sessionCreated;\n // Always (re)apply the pane-border-status options so re-init or\n // upgrade-from-pre-banner-mu sessions both pick up the cue. tmux\n // set-option is idempotent. enableMuPaneBordersForSession self-checks\n // MU_BANNER_QUIET=1 (covers this and the spawn-time decoration; see\n // spawnAgent). Older tmux without pane-border-status support is benign\n // here: the cue is a nice-to-have, not load-bearing. Don't fail init.\n await mux.enableMuPaneBordersForSession(sessionName).catch(() => {});\n const created = !sessionAlready || dbCreated;\n // Naming convention (docs/reference/naming.md): <project>-<purpose>,\n // so two repos never share `auth` and `workstream list` groups by project.\n const nameHint = name.includes(\"-\")\n ? undefined\n : `name workstreams <project>-<purpose> (e.g. ${projectGuess() ?? \"repo\"}-${name}); one per effort`;\n const nextSteps: NextStep[] = [\n { intent: \"Attach the session\", command: await mux.attachHint({ session: sessionName }) },\n {\n intent: \"Plan tasks\",\n command: `mu task add -w ${name} --title \"...\" --impact 50 --effort-days 1`,\n },\n { intent: \"Spawn an agent\", command: `mu agent spawn <name> -w ${name}` },\n { intent: \"See state\", command: `mu state -w ${name}` },\n ];\n if (opts.json) {\n emitJson({\n workstreamName: name,\n muxSession: sessionName,\n created,\n muxSessionAlreadyExisted: sessionAlready,\n dbRowAlreadyExisted: !dbCreated,\n muWindowRepaired,\n ...(nameHint && created ? { hint: nameHint } : {}),\n nextSteps,\n });\n return;\n }\n if (sessionAlready && !dbCreated) {\n const repaired = muWindowRepaired ? ` — ${pc.yellow(\"repaired missing _mu window\")}` : \"\";\n console.log(\n pc.dim(\n `workstream \"${name}\" already exists (mux session ${sessionName}, DB row registered)${repaired}`,\n ),\n );\n printNextSteps(nextSteps);\n return;\n }\n console.log(`Created workstream ${pc.bold(name)} (mux session ${pc.bold(sessionName)})`);\n if (nameHint && created) console.log(pc.dim(`hint: ${nameHint}`));\n printNextSteps(nextSteps);\n}\n\n/** The cwd's repo or folder name, lowercased into a workstream-legal slug. */\nfunction projectGuess(): string | undefined {\n const base = basename(process.cwd())\n .toLowerCase()\n .replace(/[^a-z0-9_-]+/g, \"-\")\n .replace(/^[^a-z]+/, \"\")\n .replace(/-+$/, \"\");\n return base === \"\" ? undefined : base;\n}\n\nexport async function cmdWorkstreamList(\n db: Db,\n opts: { json?: boolean; tornDown?: boolean } = {},\n): Promise<void> {\n // `--torn-down` answers a DIFFERENT question (\"what did I remove, and\n // how do I get it back\") from the ops log rather than the live\n // tables, so it replaces the listing instead of adding rows to it.\n // Mixing the two would need a status column on every row to say which\n // half each came from.\n if (opts.tornDown === true) {\n const gone = listTornDownWorkstreams(db);\n if (opts.json) {\n emitJsonCollection(gone);\n return;\n }\n if (gone.length === 0) {\n console.log(pc.dim(\"no teardowns in the ops log\"));\n return;\n }\n console.log(formatTornDownWorkstreamsTable(gone));\n // Suggest the newest teardown that has NOT been recreated since:\n // offering a group whose rows are already back would be a no-op the\n // operator then has to reason about.\n const first = gone.find((g) => !g.recreated);\n printNextSteps([\n ...(first === undefined\n ? []\n : [\n {\n intent: `Preview restoring ${first.name}`,\n command: `mu undo ${first.group.slice(0, 8)}`,\n },\n {\n intent: \"Apply it (restores rows; not panes or workspaces)\",\n command: `mu undo ${first.group.slice(0, 8)} --yes`,\n },\n ]),\n { intent: \"Inspect what one teardown removed\", command: \"mu log --group <group>\" },\n ]);\n return;\n }\n const summaries = await listWorkstreams(db);\n if (opts.json) {\n emitJsonCollection(summaries);\n return;\n }\n if (summaries.length === 0) {\n console.log(pc.dim(\"no workstreams found (no DB rows, no mu-* mux sessions)\"));\n return;\n }\n console.log(formatWorkstreamsTable(summaries));\n}\n\nexport async function cmdTeardown(\n db: Db,\n opts: {\n workstream?: string;\n yes?: boolean;\n json?: boolean;\n empty?: boolean;\n },\n): Promise<void> {\n if (opts.empty) {\n await cmdTeardownEmpty(db, opts);\n return;\n }\n const workstream = await resolveWorkstream(opts.workstream);\n const summary = await summarizeWorkstream(db, { workstream });\n // Empty-but-registered workstreams (a row in `workstreams` with no\n // agents/tasks/etc.) ARE worth tearing down — otherwise the bare\n // registry row is orphaned forever. nothingToDo is the strict\n // intersection: nothing on disk, in mux, OR in the DB.\n const nothingToDo =\n !summary.muxAlive &&\n !summary.registered &&\n summary.agentCount === 0 &&\n summary.taskCount === 0 &&\n summary.noteCount === 0 &&\n summary.workspaceCount === 0;\n\n if (nothingToDo) {\n if (opts.json) {\n emitJson({\n workstreamName: workstream,\n tornDown: false,\n reason: \"nothing to tear down\",\n summary,\n });\n return;\n }\n console.log(\n pc.dim(`workstream \"${workstream}\" has no mux session and no DB rows; nothing to tear down`),\n );\n return;\n }\n\n if (!opts.yes) {\n const dryRunNextSteps: NextStep[] = [\n {\n intent: \"Confirm and actually tear down\",\n command: `mu workstream teardown -w ${workstream} --yes`,\n },\n ];\n if (opts.json) {\n emitJson({\n workstreamName: workstream,\n tornDown: false,\n dryRun: true,\n summary,\n nextSteps: dryRunNextSteps,\n });\n return;\n }\n console.log(pc.bold(`Workstream ${workstream} (mux session ${summary.muxSession})`));\n console.log(\n ` mux session : ${summary.muxAlive ? pc.yellow(\"alive (will be killed)\") : pc.dim(\"not running\")}`,\n );\n console.log(` agents : ${summary.agentCount}`);\n console.log(\n ` tasks : ${summary.taskCount} (edges: ${summary.edgeCount}, notes: ${summary.noteCount})`,\n );\n console.log(\n ` workspaces : ${summary.workspaceCount}${summary.workspaceCount > 0 ? pc.dim(\" (will be cleaned via per-backend remove)\") : \"\"}`,\n );\n console.log(\"\");\n console.log(pc.dim(\"(dry-run; rerun with --yes to actually tear down)\"));\n printNextSteps(dryRunNextSteps);\n return;\n }\n\n const result = await teardownWorkstream(db, { workstream });\n if (opts.json) {\n emitJson({\n workstreamName: workstream,\n tornDown: true,\n ...result,\n });\n return;\n }\n console.log(pc.bold(`Workstream ${workstream} (mux session ${summary.muxSession})`));\n console.log(\n ` mux session : ${summary.muxAlive ? pc.yellow(\"alive (will be killed)\") : pc.dim(\"not running\")}`,\n );\n console.log(` agents : ${summary.agentCount}`);\n console.log(\n ` tasks : ${summary.taskCount} (edges: ${summary.edgeCount}, notes: ${summary.noteCount})`,\n );\n console.log(` workspaces : ${summary.workspaceCount}`);\n console.log(\"\");\n console.log(\n `Destroyed ${pc.bold(workstream)}: killed mux=${result.killedMux}, agents=${result.deletedAgents}, tasks=${result.deletedTasks}, edges=${result.deletedEdges}, notes=${result.deletedNotes}, workspaces=${result.freedWorkspaces}/${summary.workspaceCount}${result.alreadyGoneWorkspaces > 0 ? ` (${result.alreadyGoneWorkspaces} already gone on disk)` : \"\"}`,\n );\n if (result.failedWorkspaces.length > 0) {\n console.log(\"\");\n console.log(\n pc.yellow(\n `WARNING: ${result.failedWorkspaces.length} workspace(s) could not be freed cleanly. The DB rows are gone (FK cascade); the on-disk paths remain and need manual cleanup:`,\n ),\n );\n for (const f of result.failedWorkspaces) {\n console.log(` - ${f.agent} (${f.backend}): ${f.path}`);\n console.log(` error: ${f.error}`);\n }\n printNextSteps([\n {\n intent: \"For each git worktree above, run\",\n command: \"git worktree remove --force <path>\",\n },\n { intent: \"For each jj workspace above, run\", command: \"jj workspace forget <name>\" },\n { intent: \"As a last resort\", command: \"rm -rf <path>\" },\n ]);\n }\n}\n\n// ─── cmdTeardownEmpty ─────────────────────────────────────────────────\n//\n// `mu workstream teardown --empty` sweeps every workstream with no\n// user-meaningful state (zero tasks, agents, vcs_workspaces), except\n// `scratch`, whose idle session is kept alive on purpose. It never\n// sweeps an unregistered `mu-*` session: with no DB row there is no\n// evidence it is idle (see listEmptyWorkstreams); the human output\n// names them so the operator can tear one down explicitly.\n// Each workstream's teardown is its own op group, so each is undone\n// separately (`mu workstream list --torn-down` lists the groups).\n// Per-workstream teardown errors are accumulated into a `failed` array\n// so a single bad pane doesn't abort the rest of the cleanup. See\n// workstream_destroy_empty_sweep.\n\ninterface EmptyTeardownResult {\n workstreamName: string;\n killedMux: boolean;\n deletedAgents: number;\n deletedTasks: number;\n deletedNotes: number;\n deletedEdges: number;\n freedWorkspaces: number;\n alreadyGoneWorkspaces: number;\n}\n\ninterface EmptyDestroyFailure {\n workstreamName: string;\n error: string;\n}\n\n/** Read created_at for a registered workstream; the empty string when\n * the row is gone (keeps the signature total). */\nfunction workstreamCreatedAt(db: Db, name: string): string {\n const row = db.prepare(\"SELECT created_at FROM workstreams WHERE name = ?\").get(name) as\n | { created_at: string }\n | undefined;\n return row?.created_at ?? \"\";\n}\n\nasync function cmdTeardownEmpty(\n db: Db,\n opts: {\n workstream?: string;\n yes?: boolean;\n json?: boolean;\n },\n): Promise<void> {\n // --empty is a sweep verb; -w (target a single workstream)\n // contradicts it. Fail loud with exit 2 (UsageError) so a typo\n // (`--empty -w foo`) doesn't silently sweep instead of targeting\n // `foo`.\n if (opts.workstream !== undefined) {\n throw new UsageError(\n \"--empty is mutually exclusive with a named target (positional <name> or -w/--workstream): the sweep targets every empty workstream, so naming one contradicts it\",\n );\n }\n const empties = await listEmptyWorkstreams(db);\n\n if (!opts.yes) {\n if (opts.json) {\n emitJsonCollection(empties);\n return;\n }\n if (empties.length === 0) {\n console.log(pc.dim(\"no empty workstreams found\"));\n await printUnregisteredSkipped(db);\n return;\n }\n const table = muTable({\n head: [\"workstream\", \"created_at\", \"mux\"].map((h) => pc.bold(h)),\n colWidths: [40, null, null],\n });\n for (const ws of empties) {\n const createdAt = workstreamCreatedAt(db, ws.name);\n // Em-dash if the row vanished between list and render, so the\n // column never goes visually empty (matches the mux column).\n const createdCell = createdAt === \"\" ? pc.dim(\"\\u2014\") : pc.dim(createdAt);\n table.push([ws.name, createdCell, ws.muxAlive ? pc.green(\"alive\") : pc.dim(\"\\u2014\")]);\n }\n console.log(table.toString());\n console.log(\"\");\n console.log(\n pc.dim(\n `${empties.length} empty workstream${empties.length === 1 ? \"\" : \"s\"} would be torn down (dry-run; rerun with --yes to actually tear down).`,\n ),\n );\n printNextSteps([\n {\n intent: \"Confirm and actually tear down every empty workstream\",\n command: \"mu workstream teardown --empty --yes\",\n },\n ]);\n await printUnregisteredSkipped(db);\n return;\n }\n\n // --yes path. No-op early if there's nothing to do.\n if (empties.length === 0) {\n if (opts.json) {\n emitJson({ tornDown: 0, results: [], failed: [] });\n return;\n }\n console.log(pc.dim(\"no empty workstreams found; nothing to tear down\"));\n await printUnregisteredSkipped(db);\n return;\n }\n\n const results: EmptyTeardownResult[] = [];\n const failed: EmptyDestroyFailure[] = [];\n for (const ws of empties) {\n try {\n const result = await teardownWorkstream(db, { workstream: ws.name });\n results.push({\n workstreamName: ws.name,\n killedMux: result.killedMux,\n deletedAgents: result.deletedAgents,\n deletedTasks: result.deletedTasks,\n deletedNotes: result.deletedNotes,\n deletedEdges: result.deletedEdges,\n freedWorkspaces: result.freedWorkspaces,\n alreadyGoneWorkspaces: result.alreadyGoneWorkspaces,\n });\n } catch (err) {\n // Best-effort sweep: log the failure and keep going. Every\n // workstream torn down before or after this one wrote its own\n // op group, so a half-completed sweep stays undoable per\n // workstream.\n failed.push({\n workstreamName: ws.name,\n error: err instanceof Error ? err.message : String(err),\n });\n }\n }\n\n if (opts.json) {\n emitJson({ tornDown: results.length, results, failed });\n return;\n }\n for (const r of results) {\n console.log(\n `Destroyed ${pc.bold(r.workstreamName)} ${pc.dim(\n `(killedMux=${r.killedMux}, agents=${r.deletedAgents}, tasks=${r.deletedTasks}, notes=${r.deletedNotes}, edges=${r.deletedEdges})`,\n )}`,\n );\n }\n if (failed.length > 0) {\n console.log(\"\");\n console.log(\n pc.yellow(\n `WARNING: ${failed.length} workstream${failed.length === 1 ? \"\" : \"s\"} could not be torn down cleanly:`,\n ),\n );\n for (const f of failed) {\n console.log(` - ${f.workstreamName}: ${f.error}`);\n }\n }\n console.log(\"\");\n console.log(pc.dim(`Sweep complete: tornDown=${results.length}, failed=${failed.length}.`));\n if (results.length > 0) {\n printNextSteps([\n {\n intent:\n \"Undo: one op group per torn-down workstream; restore each with `mu undo <group> --yes` (rows only, not mux sessions)\",\n command: \"mu workstream list --torn-down\",\n },\n ]);\n }\n await printUnregisteredSkipped(db);\n}\n\n/** Human-output note naming the live `mu-*` sessions this DB has no\n * row for: the sweep never takes them, so say how to take one. */\nasync function printUnregisteredSkipped(db: Db): Promise<void> {\n const names = await listUnregisteredMuxWorkstreams(db);\n if (names.length === 0) return;\n console.log(\"\");\n console.log(\n pc.dim(\n `Skipped ${names.length} mu-* session${names.length === 1 ? \"\" : \"s\"} with no workstream row (--empty never sweeps these; they may be live): ${names.join(\", \")}`,\n ),\n );\n printNextSteps([\n {\n intent: \"Tear one down after checking it is unused\",\n command: `mu workstream teardown ${names[0]} --yes`,\n },\n ]);\n}\n\n// ─── commander wiring ────────────────────────────────────────────────\n//\n// wireWorkstreamCommands is called by buildProgram() in src/cli.ts. Wired here so\n// every per-namespace builder lives next to its cmd functions.\n\nimport type { Command } from \"commander\";\nimport { handle, JSON_OPT, WORKSTREAM_OPT } from \"../cli.js\";\n\n/** Fold an optional positional workstream name into the opts bag.\n *\n * dogfood-destroy-w-flag: `workstream init` takes its target\n * POSITIONALLY while `teardown` only took `-w`, so\n * `mu workstream teardown v2 --yes` printed help (\"too many\n * arguments\") instead of tearing down. The positional is now an\n * additive ALIAS for -w on both verbs; -w keeps working unchanged.\n * Supplying both is a usage error rather than a silent pick-one.\n *\n * Codifies the CLI's flag-vs-positional rule: the primary entity a\n * verb acts on is positional; everything else is a flag. See\n * docs/reference/naming.md. */\nexport function withPositionalWorkstream<T extends { workstream?: string }>(\n opts: T,\n name: string | undefined,\n): T {\n if (name === undefined) return opts;\n if (opts.workstream !== undefined && opts.workstream !== name) {\n throw new UsageError(\n `workstream given twice and they disagree: positional ${JSON.stringify(name)} vs -w ${JSON.stringify(opts.workstream)}; pass it once`,\n );\n }\n return { ...opts, workstream: name };\n}\n\nexport function wireWorkstreamCommands(program: Command): void {\n const workstream = program\n .command(\"workstream\")\n .description(\n \"Workstream-level commands. Name them <project>-<purpose> (hail-auth), one per effort; tear down when it ships. Reviews nobody will track belong in scratch delegates, not a workstream.\",\n );\n\n workstream\n .command(\"init <name>\")\n .description(\n \"Create the workstream's mux session and register it in the DB. Name it <project>-<purpose>.\",\n )\n .option(...JSON_OPT)\n .action(function (name: string) {\n const opts = (this as Command).opts() as { json?: boolean };\n return handle((db) => cmdInit(db, name, opts), this as Command)();\n });\n\n workstream\n .command(\"list\")\n .description(\"List every workstream on this machine (DB rows + mu-* mux sessions)\")\n .option(\n \"--torn-down\",\n \"instead list past teardowns from the ops log, with the group id to pass to `mu undo`\",\n )\n .option(...JSON_OPT)\n .action(function () {\n const opts = (this as Command).opts() as { json?: boolean; tornDown?: boolean };\n return handle((db) => cmdWorkstreamList(db, opts), this as Command)();\n });\n\n workstream\n .command(\"teardown [name]\")\n .description(\n \"Tear down a workstream: kill its mux session and cascade-delete every DB row tagged with its name. Reversible — tombstone ops are written, so `mu undo <group>` restores the rows. The target may be given positionally (matching `workstream init <name>`) or via -w. Pass --yes to actually tear down; otherwise prints a dry-run summary. With --empty, sweeps every empty workstream (zero tasks/agents/workspaces) except scratch in one call.\",\n )\n .option(...WORKSTREAM_OPT)\n .option(\"-y, --yes\", \"actually tear down (without this flag, prints a dry-run summary)\")\n .option(\n \"--empty\",\n \"sweep every empty workstream (zero tasks, agents, vcs_workspaces); never scratch or a mu-* session with no workstream row; mutually exclusive with -w\",\n )\n .option(...JSON_OPT)\n .action(function (name: string | undefined) {\n const opts = (this as Command).opts() as {\n workstream?: string;\n yes?: boolean;\n json?: boolean;\n empty?: boolean;\n };\n return handle(\n (db) => cmdTeardown(db, withPositionalWorkstream(opts, name)),\n this as Command,\n )();\n });\n}\n"],"mappings":"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","names":["dirname","join","dirname","exitCode","nextSteps","nextSteps","dirname","nextSteps","dirname","nextSteps","nextSteps","nextSteps","dirname","dirname","path","dirname","nextSteps","r","dirname","word","dirname","reconcile","workstream","n","result","exec","dirname","resolve","path","nextSteps","nextSteps","orphans","nextSteps","dirname","join"]}
|