How to delegate work to specialized assistants with their own context windows — agent files, worktree isolation, persistent memory, and experimental agent teams.
Long sessions die of context pollution: every file read, every test log, every dead end lands in the one window you have. A subagent is a specialized assistant Claude Code delegates a task to — it gets its own context window, its own system prompt, and its own tool permissions, does the work with a clean slate, and hands back only the result.
That one move buys five things at once: context preservation, specialized expertise with higher success rates, reusability across projects and teams, flexible permissions per agent type, and parallel scale — multiple agents on different aspects simultaneously.
--- name: test-runner description: Use proactively to run tests and fix failures tools: Read, Edit, Bash # optional model: sonnet # optional --- You are a test automation expert. When you see code changes, run the tests. If they fail, fix them while preserving the original test intent.
| 1 · --agents '{…}' | CLI flag, JSON — session only, overrides every other source |
| 2 · .claude/agents/ | Project — commit to git, the whole team gets them |
| 3 · ~/.claude/agents/ | User — follows you across all projects |
| 4 · <plugin>/agents/ | Plugin — shipped via installed plugins, lowest priority |
tools: lists exact tools (omit = inherit all), patterns like Bash(npm:*) work, and Agent(worker, researcher) allowlists which subagents it may spawn (Task renamed to Agent in v2.1.63 — old refs still alias). disallowedTools: bans tools outright.
model: sonnet · opus · haiku · a full model ID · inherit. effort: low → max scales reasoning depth per agent.
skills: injects full skill content at startup — and since v2.1.133 subagents also discover the whole skill catalog via the Skill tool. mcpServers: attaches MCP servers.
permissionMode (default · acceptEdits · dontAsk · bypassPermissions · plan), maxTurns caps the loop, hooks: run scoped to this agent only, initialPrompt auto-submits a first turn when it runs as the main agent.
| general-purpose | Inherits your model, all tools — complex multi-step research and modification |
| Plan | Read, Glob, Grep, Bash — the researcher behind plan mode |
| Explore | Haiku, strictly read-only — fast codebase search at "quick", "medium", or "very thorough" depth |
| Bash | Terminal commands in a separate context window |
| statusline-setup | Sonnet — configures the status line display |
| Claude Code Guide | Haiku, read-only — answers questions about Claude Code itself |
Claude matches your request against each agent's description. Add "use PROACTIVELY" or "MUST BE USED" to the description to bid for automatic delegation.
"Use the test-runner subagent to fix failing tests" — name it in plain English and Claude routes the task there.
@"code-reviewer (agent)" — the @-mention bypasses delegation heuristics entirely. The named agent runs, full stop.
claude --agent code-reviewer (or "agent" in settings.json) runs the whole session as that agent. Main-thread honoring is scoped: mcpServers loads via --agent (v2.1.117+); permissionMode applies to built-in agents (v2.1.119+); tools only in --print mode (v2.1.119+).
> Use the code-analyzer agent to start reviewing the authentication module # returns agentId: "abc123" > Resume agent abc123 and now analyze the authorization logic as well
The conversation continues with full context preserved — long research across sessions, iterative refinement without starting over.
> First use the code-analyzer subagent
to find performance issues,
then use the optimizer subagent
to fix them
Sequenced delegation in one request — each subagent's findings become the input for the next, with the main agent coordinating.
| memory: user | ~/.claude/agent-memory/<name>/ — personal notes across all projects |
| memory: project | .claude/agent-memory/<name>/ — project knowledge, shared with the team |
| memory: local | .claude/agent-memory-local/<name>/ — project knowledge, never committed |
A background subagent runs while you keep working — set background: true in frontmatter to make an agent always run that way, or press Ctrl+B to background a task that's already running.
| Ctrl+B | Background the currently running subagent task |
| Ctrl+F (twice) | Kill all background agents — second press confirms |
| auto-deny | Background agents deny any permission that isn't pre-approved — they can't stop to ask you |
| CLAUDE_CODE_DISABLE_BACKGROUND_TASKS=1 | Environment variable disables background task support entirely |
The clean slate is the default — and usually the point. context: fork inverts it: the subagent inherits the parent's full conversation at the moment of forking, explores an alternative path, and reports back without disturbing the original. GA in v2.1.117; on external builds set CLAUDE_CODE_FORK_SUBAGENT=1.
| Explore an alternative implementation | fork — a clean slate would lose the work so far |
| Long research mid-conversation | fork — the existing context is the input |
| Independent specialized task | clean — history would only distract |
| Avoiding context pollution | clean — isolation is the whole goal |
Agent Teams (experimental, off by default, v2.1.32+) coordinate multiple full Claude Code instances: a team lead assigns work through a shared task list with automatic dependency tracking, and teammates message each other directly through a mailbox.
| Delegation | Subagent: parent waits for a result · Team: teammates execute independently |
| Context | Subagent: fresh per subtask, distilled back · Team: each keeps a persistent window |
| Communication | Subagent: results to parent only · Team: direct inter-agent messages via mailbox |
| Coordination | Subagent: parent-managed · Team: shared task list resolves dependencies itself |
| Resumption | Subagent: supported · Team: not supported with in-process teammates |
| Best for | Subagent: focused, well-defined subtasks · Team: parallel work that needs cross-talk |
Plugin-provided subagents may not declare hooks, mcpServers, or permissionMode — a plugin can't escalate privileges or smuggle in arbitrary commands through an agent file.
Subagents cannot spawn other subagents. To control delegation from the top, allowlist with Agent(worker, researcher) in the tools field — the allowlist governs what the spawning session may delegate to; only the named agents may be spawned.
Every run is logged at ~/.claude/projects/{project}/{sessionId}/subagents/agent-{agentId}.jsonl; context auto-compacts at ~95% capacity (override: CLAUDE_AUTOCOMPACT_PCT_OVERRIDE).
Subagent API calls carry x-claude-code-agent-id + x-claude-code-parent-agent-id headers, mirrored as OpenTelemetry span attributes — attribute spend per agent type, rebuild invocation trees, alert on runaways.
| code-reviewer | Read, Grep, Glob, Bash — quality + security review, severity-ranked findings |
| clean-code-reviewer | Same tools — Clean Code / SOLID enforcement with file:line fixes |
| secure-reviewer | Read, Grep only — security audit that physically cannot execute or modify |
| test-engineer | Read, Write, Bash, Grep — test suites targeting >80% coverage |
| debugger | Read, Edit, Bash, Grep, Glob — root-cause analysis, minimal fix, verify |
| performance-optimizer | Read, Edit, Bash, Grep, Glob — profile, fix the biggest bottleneck, re-measure |
| implementation-agent | Full toolset incl. Write — end-to-end feature implementation |
| documentation-writer | Read, Write, Grep — API docs, guides, architecture docs |
| data-scientist | Bash, Read, Write · model: sonnet — SQL + BigQuery analysis |
A subagent is a Markdown file: frontmatter sets the tools, model, and permissions; the body is the system prompt. The description decides when Claude delegates automatically. Of every feature so far, subagents are the only one with an isolated context window — and four fields extend it: memory persists knowledge, background unblocks your thread, isolation: worktree protects your tree, context: fork shares your history. When specialists need to talk to each other, that's agent teams.