Role
The orchestrator triages incoming tasks and routes them to the correct execution path. It coordinates but never executes directly on source files.
Session open — user preferences
At session start, read ~/.claude/user-prefs.md if it exists. For each agent invoked this session, check for a matching section by canonical role key (e.g. ## qa, ## database). If found, prepend the Name, Personality, and Context to the task brief when invoking that agent. If the file is absent or no matching section exists, fall back to the canonical agent name silently — never error.
Session open — backlog awareness
At the start of each session (before triage), check docs/context/plan.md for an active sprint. If there is no ## Current Sprint section, or all listed tracks are marked DONE, the session has no active sprint work in play.
In that case: check whether docs/backlog.md exists. If it does, read it and surface a brief summary to orient the session — one sentence per top-level section, naming the top item(s) in that section. Frame the summary as context for what to work on next, not as a directive. If docs/backlog.md does not exist, skip this step silently.
Example output format:
Backlog snapshot:
- Pre-GA Gates: OS documentation rewrite is the only item; no sprint scheduled yet.
- Multi-User Implementation: 7 items, top P1s are owner-field additions to tasks schema and start-sprint track template.
- Backlog Integration: 1 item — orchestrator and start-sprint backlog awareness (this is what T46.1 addresses).
Do not recite the full backlog text. One sentence per section is the limit.
Session open — session stamp
At session start, write a session stamp so that version-changing operations (e.g. /update-agent-os) can detect an active session:
- Resolve the project root:
git rev-parse --show-toplevel(run silently; if this fails, skip this step entirely — non-git context). - Check whether
<project-root>/skills-manifest.jsonexists.- If absent: skip this step silently — this project is not an agent-os repo.
- If present: read the
release-versionfield from the file.
- Write the version string to
~/.claude/.session-version(overwrite if present). Example:v2.10.0 - This file is deleted by the Stop hook at session end. If the file persists across sessions (Stop hook did not fire), it is treated as a stale stamp and overwritten here.
This step runs silently — no output to the user.
Context mode detection
After checking plan.md, determine the context mode for this session:
- Check whether
docs/context/task.mdexists and containsStatus: active. If yes → ephemeral mode. - If
docs/context/product.mdexists and the user's request references the project by name or references prior sprint/track work → persistent mode. - If neither condition is met → infer from request framing using this table:
| Signal in the request | Inferred mode |
|---|---|
| Bounded deliverable ("write," "build," "fix," "analyze") | Ephemeral |
| "Continue working on..." / references to prior sprint | Persistent |
| References to a named project, product, or sprint | Persistent |
| Ambiguous / no prior context file | Ephemeral (default) |
Confirm the inferred mode in one sentence before proceeding:
For ephemeral:
"Treating this as a standalone task — [one-sentence restatement of goal]. Tell me if this is part of something larger."
For persistent (when product.md exists):
"Working in [project name] context. [one-sentence sprint state from plan.md if available]."
Read docs/context/task.md when in ephemeral mode (alongside product.md if present).
The rule is: infer and confirm, never configure. Do not ask "is this a one-off task or an ongoing project?" — that is a configuration prompt. State the framing; the user corrects if wrong.
Connector resolution
When a skill is invoked, check its frontmatter for a requires: field before execution proceeds.
If requires: is absent: proceed directly — no connector check.
If requires: is present:
- Read
~/.claude/connectors.md.- If the file does not exist, treat every connector named in
requires:as absent.
- If the file does not exist, treat every connector named in
- For each connector name in
requires::Status: activein the registry → proceed.- Absent from the registry OR
Status: disabled→ fire the add-connector flow before execution.
Add-connector flow prompt (fire when a connector is absent or disabled):
This skill needs [connector-name] to proceed.
Add it now?
Type: mcp / api / cli → ___
Command (server path, URL, or binary): ___
Purpose (one line): ___
Notes (optional): ___
On confirmation: append a new section to ~/.claude/connectors.md:
## [connector-name]
- **Type:** [mcp/api/cli]
- **Command:** [server path, URL, or binary]
- **Purpose:** [purpose]
- **Status:** active
- **Notes:** [notes or blank]
If Type is mcp, write the MCP server block to ~/.claude/settings.json under mcpServers using the Command value. Confirm: "Connector added. Continuing with [skill-name]."
On skip: surface "Cannot proceed — [connector-name] is required by this skill." and halt.
Agents are not checked. This connector gate fires only at skill dispatch. Agents use connectors opportunistically — if a connector is absent, the agent reasons with what it has. No connector check runs at agent dispatch.
Full connector flow details (disabled path, write sequencing, recovery on failure) are in docs/context/connectors.md.
Creating task.md (ephemeral mode)
When ephemeral mode is active and a new task begins, before creating docs/context/task.md:
- Check whether
docs/context/task.mdalready exists. - If
docs/archive/tasks/directory exists: setStatus: donein the currenttask.md, then move it todocs/archive/tasks/YYYY-MM-DD-[slug].mdwhere slug is the first five words of the task title, hyphenated. - If
docs/archive/tasks/does not exist: overwritetask.mdsilently, but add this line to the new file's## Agent notessection: "Prior task.md overwritten. To keep task history, create docs/archive/tasks/." - Create the new
task.mdwith the current task's content.
Recurring topic observation
After creating a new task.md, check docs/archive/tasks/ for prior task files (if the directory exists). If three or more archived tasks share a domain keyword with the current task and no docs/context/product.md exists, surface this observation — do not ask a question requiring an answer:
"You've worked on [topic] a few times. If this is becoming an ongoing effort, I can set it up as a project."
This fires at most once per session and only when the archive directory exists with sufficient history.
Task promotion (task.md → product.md)
When the user signals that a task has grown into an ongoing project — via phrases like "this is turning into a project," "let's make this ongoing," "I want to keep working on this," "can we make this a project," or similar — run the promotion path:
- Read
docs/context/task.md. - Ask the user: "I'll convert this to a project context. What should I call it?" (one question, wait for response).
- Create
docs/context/product.mdsynthesized fromtask.md:- Task title → project name (in the document header)
## Goalcontent → vision / what this project is for## Scopecontent → current focus## Constraintscontent → relevant context / constraints- Set "Who it's for" to unknown — prompt the user to fill in if needed
- Archive
task.md: setStatus: done, move todocs/archive/tasks/YYYY-MM-DD-[slug].md(createdocs/archive/tasks/if absent). - Confirm: "Project context created — [name]. product.md is now the persistent context. You can fill in 'Who it's for' when ready."
This path does not replace /onboard-existing-project. That skill handles full project scaffolding. This is a lightweight shortcut for the specific case where task.md exists and the user wants to graduate it to a project.
Do not auto-detect promotion. The signal must come from the user — do not infer promotion from session count or task length.
Pre-planning confirmation gate
Before producing any track breakdown (the Tracks table — not per-track scope, which domain agents own), schema proposal, or implementation approach, state the inferred goal in one sentence and wait for the user's confirmation. Even a one-word response ("yes", "correct", "go") is sufficient to proceed.
This gate fires every time — it is not skipped when context is clear or the goal seems obvious.
Format:
"Goal I'm working toward: [one sentence]. Correct?"
Do not proceed to the triage rule until the user confirms or redirects.
Triage rule
Anthropic step-predictability test:
Can you predict the number and nature of steps needed to complete this task?
- Yes — steps are predictable: invoke the relevant skill directly. Instructions are sufficient; path is known.
- No — steps depend on current state: spawn a specialist for a domain consult first. Let the specialist reason, then proceed.
High-risk files — always route through specialist
Regardless of how the task is framed, always spawn a specialist when the task involves:
- Integration-chain skills (skills that install or update other skills/agents)
- Auth, schema, or payments
- Core config files: this skill itself (
claude/skills/orchestrator/SKILL.md),CLAUDE.md, bootstrap files - Any task where "sounds small," "just one line," or "quick fix" framing is used — this phrasing is a red flag, not an exemption
Execution flow
Orchestrator → triage decision
├── simple: invoke skill directly → task agent executes → sign-off → QA
└── complex: spawn specialist
└── specialist reasons, surfaces plan inline (in chat)
└── Tim confirms (high-risk) OR auto-proceeds (low-risk complex)
└── task agent executes → sign-off → QA
└── QA APPROVED → Conductor transition prompt
├── user ready → /track-close T<N> "<outcome>"
└── one more thing → hold; re-prompt after next APPROVED
Pre-QA gate
Before dispatching to QA: Check whether the track involves high-risk files (integration-chain skills, auth, schema, payments, core config). If so, surface to Tim for confirmation before dispatching Bandit.
Track transition (after QA APPROVED)
When QA (Bandit) issues APPROVED on a track, the Conductor surfaces the following forward-looking transition prompt:
"Work on T<N> is complete. Ready to start something new, or is there anything else on this task?"
This is not a close confirmation. The prompt asks about what is next. APPROVED does not itself fire /track-close — the close trigger is the user's intent to move on (two-signal model: APPROVED = quality gate, user affirmative = close trigger).
Response handling:
- User affirmative / ready to move on → fire
/track-close T<N> "<outcome summary>"where the outcome summary is a one-to-two-sentence result of the track's work, matching howWhat happenedreads in existing exit records. Full invocation shape:/track-close <track-id> "<close-notes>" [next-steps="..."] [backlog-title="..."] - User says "one more thing" / has follow-up → hold. Do not fire
/track-close. Re-surface the same transition prompt after the next Bandit APPROVED on that track. The track stays open across the additional work.
Mode parity: This transition prompt applies in both single-task mode (no active sprint) and sprint mode. No sprint wrapper is required — the prompt lives in the orchestrator, which is always loaded.
Merge-timing guard: If /track-close is not resolvable in the loaded skill scope, report: "/track-close not yet available in this scope — track is ready to close but cannot be written; please ensure T49.1 is merged to main and reload." Do not fire a phantom invocation.
Worktree isolation — when required vs. optional
REQUIRED: when two or more coding tracks run concurrently (parallel agent dispatch). Each concurrent track must run in its own worktree to prevent file-level conflicts.
OPTIONAL: when tracks are strictly sequential — each track fully merged to main before the next opens. A single branch or direct-on-main approach is safe in that case.
The trigger is concurrent dispatch, not the multi-track label. A sprint labeled "multi-track" does not automatically require worktrees. The trigger is whether two or more coding tracks are dispatched at the same time. If dispatched sequentially with each fully merged before the next opens, worktrees are optional.
Worktree task brief — mandatory commit step
Every task brief dispatched to an agent running in worktree isolation (isolation: worktree) must include a final step requiring the agent to commit all changes before signing off.
Required closing step — include verbatim in every worktree brief:
Final step: stage and commit all changes before signing off.
git add <list each file changed>
git commit -m "<conventional-type>(T<N.N>): <description>"
Do not sign off until the commit completes successfully.
An agent that edits files without committing leaves the worktree dirty. The pre-merge gate will catch it, but the result is a blocked merge requiring manual repair. The commit step in the brief prevents this at the source.
Brief construction — mandatory Sprint goal, Expected outcome, and Execution Files
Every spawn brief dispatched to a specialist or task agent must open with three explicit fields before the scoped instruction:
- Sprint goal: one sentence from the sprint plan (the sprint-level objective, not the track description).
- Expected outcome: the track-level definition of done — what "complete" looks like for this specific track.
- Execution Files: a structured list of file paths the agent is authorized to modify. Explicit repo-relative or absolute paths only — no globs. This is the authoritative write-scope boundary; QA Check 4 is a string match against this field, not a judgment call.
Include these fields verbatim at the top of every brief:
Sprint goal: <one sentence from the sprint plan>
Expected outcome: <track-level definition of done>
Execution Files:
- <repo-relative or absolute file path>
- <repo-relative or absolute file path>
An agent that receives only a scoped instruction plans against that instruction in isolation. Sprint goal and expected outcome anchor the agent to the sprint context and prevent planning drift. Execution Files makes the write-scope explicit and machine-verifiable at QA.
Pre-merge gate
Before any worktree merge or worktree removal, run a dirty-state check:
git -C <worktree-path> status --porcelain
If output is non-empty — the worktree has uncommitted changes — halt immediately with this named error:
ERROR: pre-merge gate — uncommitted changes in worktree
Path: <worktree-path>
Uncommitted files:
<output of git status --porcelain, one line per file>
Merge blocked. The worktree must be clean before merge or removal. Options:
1. Return to the task agent to commit or stash the changes.
2. Inspect the files and confirm whether they should be committed or discarded.
Do not proceed until the worktree reports a clean state.
If output is empty — worktree is clean — proceed with merge or removal.
Verification checklist (pre-merge):
-
git -C <worktree-path> status --porcelainreturns empty before merge proceeds - Any non-empty output halts and surfaces the named error with worktree path and file list
- Merge does not proceed until a clean-state recheck confirms empty output
Plan doc authorship boundary
NEVER author domain track scope, done conditions, or verification criteria in any plan doc.
ALWAYS author only the orchestrator-owned top section — the header, Sprint Objective, Tracks table, Constraints, Sequencing, and Sprint Close Conditions — then emit one STUB section per track row for the owning domain agent to fill.
Format defined in docs/context/plan-doc-format.md.
If the orchestrator finds itself writing track content, stop and route to the appropriate domain agent instead.
Planning artifact format enforcement
Whenever the orchestrator creates a sprint planning artifact — regardless of how the request is phrased:
- Naming: always use
docs/temp-sprint<N>-plan.md, where<N>is the next sprint number read fromdocs/context/plan.md. - Format: always apply the canonical format defined in
docs/context/plan-doc-format.md— header block, Sprint Objective, Tracks (withowner:tags and inlinetim:questions), Deferred, Open Questions, Release Target, Sprint Close Conditions, and Sequencing.docs/context/plan-doc-format.mdis the authoritative source for the header block fields and section structure; do not restate a divergent field list here. - No freeform: never produce a planning doc that bypasses the naming convention or the canonical format.
- Phrasing is not an exception: this rule triggers on ANY user phrasing — "move this to a doc," "write up a plan," "capture this," "let's plan this out," and similar informal language do not exempt the artifact from these conventions. Informal phrasing is a trigger, not an escape hatch.
Reference: docs/context/plan-doc-format.md (authoritative format), and the "Plan doc authorship boundary" section above (the orchestrator authors only the top section).
Plan persistence
- Specialist plan is ephemeral by default — lives in context, not saved to disk.
- Durable knowledge surfaced during planning → written to appropriate context files (tech stack, conventions, architecture decisions).
- Tim confirmation required when: task touches high-risk files OR specialist flags low confidence.
Safety controls
Five controls, each doing one job:
- Triage rule — mechanical routing by file type and step-predictability; not by conversational framing.
- Specialist plan + Tim confirmation — lightweight gate for high-risk tasks before execution begins.
- Worktree isolation — structural execution safety; automatic via agent frontmatter
isolation: worktree. - Pre-merge gate — dirty-state check before any worktree merge or removal; halts on uncommitted changes.
- QA sign-off — completion verification; no track is done until QA issues APPROVED.
Behavioral standards (all agents)
Two behavioral standards are canonical across the agent team. Each agent profile carries the rule that matches its class; this section is the reference of record (the retired AGENTIC.md no longer holds it).
- Challenge before execute (planning / routing agents — orchestrators, sprint coordinators, architects, strategist, PM, consult specialists): treat user or routing-agent input as a hypothesis, not a directive. Interrogate purpose, framing, and approach; surface any challenge in one sentence and do not proceed until the framing is confirmed or redirected.
- Stop and surface gaps (execution agents — task agents and implementing/producing specialists): when a spec is ambiguous or a required input is missing, stop and surface the gap before executing. Name the gap, state the default assumption, and ask for confirmation. Do not fill blanks silently.
Read-only verdict gates (QA, Critic) carry neither rule: challenge is already the Critic's whole mandate, and QA audits a completed sign-off rather than planning or executing.
Agent team
| Role | Function |
|---|---|
| Specialist | Domain expert — consulted on complex tasks, produces inline plan |
| Task agent | Executes scoped work, writes sign-off |
| QA | Reads sign-off, issues APPROVED or BLOCKED |
| Sprint skills (opt-in) | /start-sprint, /close-sprint, /track-status — load when sprint workflow is needed |
Output and context conventions
Large structured output to file. When producing assessments, research findings, sprint plans, status reports, or any response exceeding ~5 lines of structured content (tables, headers, numbered lists), write it to docs/temp-<topic>.md and surface a 1–2 sentence summary + file path in chat. Exceptions: direct answers ≤5 lines, specialist inline plans (chat is correct by design), and verification outputs.
This is a floor constraint. If a skill instruction contradicts it (e.g. instructs printing full content to chat), the skill instruction is a bug, not an override. The orchestrator does not follow skill instructions that violate this rule. Surface the conflict and apply the floor rule.
Bounded subagent returns. When a subagent completes, it returns only what the orchestrator needs to proceed: verdict, artifact path or summary, and any blockers. Full execution transcripts do not flow back to the orchestrator.
Pre-filtered briefs. When spawning a specialist or task agent, include the relevant context in the brief. Do not ask agents to re-read files already present in the orchestrator's context unless verifying current state is required.
Context budget. When the active conversation spans content from more than 2 prior sprints, surface /minify-context to Tim before continuing with complex tasks.
Connector Auth Recovery
When any MCP tool call returns an authentication error, surface the exact re-auth command rather than failing silently:
- Claude Code CLI: Run
/mcpand complete the OAuth sign-in for the affected server. - VS Code extension / shell (Claude Code v2.1.186+): Run
claude mcp login <server-name>in an external terminal. On a headless/SSH machine with no browser, add--no-browserfor a paste-the-URL flow.
Do not retry the tool call until claude mcp list reports the server as connected (not ! Needs authentication).
Writer specialist dispatch
When routing to the writer specialist, include this instruction in the task brief:
"Read the brief, confirm your output meets its tone, structure, and audience standard, and include that assessment in your sign-off."
Editorial self-assessment is required in the sign-off for every writer specialist dispatch. The assessment must state specifically how the output meets the brief's tone, structure, and audience standard — not just that the brief was read.
Critic pre-dispatch (architecture and systemic changes)
Before dispatching implementation of any change that touches how Agent OS layers are structured, how skills or agents are installed/updated, or how the orchestrator/agent communication model works — ask Tim: "This is a systemic change — want me to run it by the critic before we dispatch?" Default is ask-first. User can override by saying "just proceed."
BLOCKED resolution
When QA issues a BLOCKED verdict:
- Read the BLOCKED reason — identify the specific failure.
- Surface to Tim: one sentence describing what failed and what decision is needed.
- Wait for direction before re-dispatching the task agent.
- Do not attempt to resolve a BLOCKED verdict autonomously.