D2.1 through D2.4 designed tools, their failure contracts, their distribution, and the wiring of external MCP servers. This chapter steps back to the tools an agent already has on the first turn — the fixed built-in roster — and the permission machinery that decides whether any given one actually fires. The exam angle is recognition: the exact roster, the read-versus-write execution split, the six modes, the evaluation order, and one high-value trap where a developer thinks they have locked an agent down and have not.
The built-in tool roster
Every agent starts with a fixed roster of built-in tools — the SDK ships roughly fourteen of them, in six categories, identical to those that power Claude Code.
[Official]
Agent SDK overview · AnthropicT1-official original How the agent loop works · AnthropicT1-official original The six that do the everyday work of reading and changing a codebase are Read, Write, Edit (file operations), Grep, Glob (search), and Bash (execution). The parity with Claude Code is explicit: “The SDK includes the same tools that power Claude Code,”
[Official]
How the agent loop works · AnthropicT1-official original and “Everything that makes Claude Code powerful is available in the SDK.”
[Official]
Agent SDK overview · AnthropicT1-official original Beyond this built-in set sit MCP server tools (Chapter D2.4) and your own custom tools; this chapter is about the built-ins every agent has from the start.
These names are exact — they appear verbatim in allowed_tools / allowedTools rules and as the tool_use.name block in messages, so Read is the tool and read is not.
[Official]
How the agent loop works · AnthropicT1-official original
Read-only and state-modifying tools run differently
The roster splits along a line that the runtime cares about: whether a tool reads state or changes it. Read-only tools — Read, Glob, Grep, and MCP tools marked read-only — can run concurrently; tools that modify state — Edit, Write, and Bash — run sequentially to avoid conflicts. Custom tools default to sequential execution and opt into parallelism by setting readOnlyHint in their annotations.
[Official]
How the agent loop works · AnthropicT1-official original
Gating the tools: six permission modes
Having a tool in the roster does not mean it fires. When the model requests a tool, the active permission mode is consulted, and there are six: default, acceptEdits, plan, dontAsk, bypassPermissions, and auto (TypeScript-only).
[Official]
Configure permissions · AnthropicT1-official original Two are worth memorizing for the exam because they change the tool surface directly: plan restricts the agent to read-only tools, so it explores and proposes a plan without editing source files; acceptEdits auto-approves file edits and filesystem commands (mkdir, touch, rm, rmdir, mv, cp, sed) — but only inside cwd plus additionalDirectories, and paths outside that scope, or protected paths, still prompt.
[Official]
Configure permissions · AnthropicT1-official original
Allow and deny rules — and the five-step order
Within a mode, allow and deny rules pre-approve or block specific tools and calls. A bare name and a scoped pattern behave differently: allowed_tools=["Read", "Grep"] auto-approves those tools; disallowed_tools=["Bash"] removes Bash from the request entirely, so the model never sees it; and disallowed_tools=["Bash(rm *)"] keeps Bash available but denies any rm * call — in every mode, including bypassPermissions.
[Official]
Configure permissions · AnthropicT1-official original All of this resolves through a fixed sequence: “When Claude requests a tool, the SDK checks permissions in this order: 1. Hooks. 2. Deny rules. 3. Permission mode. 4. Allow rules. 5. canUseTool callback.”
[Official]
Configure permissions · AnthropicT1-official original
The high-value trap lives in the gap between pre-approving and restricting. allowed_tools only pre-approves the tools you list; it does not filter everything else out. Set allowed_tools=["Read"] alongside permission_mode="bypassPermissions" and the agent “still approves every tool, including Bash, Write, and Edit.”
[Official]
Configure permissions · AnthropicT1-official original The allowlist was never a sandbox.
The day-to-day use of these tools — the muscle memory of Read, Edit, and Bash inside a working session — is the handbook’s territory (the Use book’s chapter on Claude Code’s toolset); this chapter is the architect’s exam angle on the roster and the permission surface that gates it.
Practice
Exercise solutions
C. allowed_tools pre-approves the tools you list; it never restricts the ones you omit. Paired with bypassPermissions, the configuration “still approves every tool, including Bash, Write, and Edit” — the allowlist is silently irrelevant (it sits at step 4 of the evaluation order, below the mode at step 3). A is the core misconception (treating the allowlist as a filter). B confuses this with acceptEdits, which is the mode that auto-approves filesystem commands — bypassPermissions approves everything, not just filesystem ops. D invents a conflict; the two settings combine without error, which is exactly why the trap is dangerous. The fix: drop bypassPermissions and use permission_mode="plan" (read-only tools only), or keep a stricter mode and add a deny rule such as disallowed_tools=["Write", "Edit", "Bash"] — deny rules block even under bypassPermissions. Reach for the allowlist to permit, and for the mode or a deny rule to forbid.
The three Read calls may run concurrently; the Edit must run on its own (sequentially). The deciding property is whether a tool is read-only or state-modifying: read-only tools (Read, Glob, Grep) can run in parallel because they cannot conflict, while state-modifying tools (Edit, Write, Bash) run sequentially to avoid clobbering each other. So the runtime can fan out the three reads at once, then run the single edit after.
(a) plan mode — it restricts the agent to read-only tools, so it can explore and propose changes but cannot edit any source file, with no allow/deny list to maintain. (b) acceptEdits — it auto-approves file edits and filesystem commands (mkdir/rmdir/mv/…) inside cwd plus additionalDirectories, while paths outside that scope (and protected paths) still prompt. plan forbids edits entirely; acceptEdits permits them but only within the working scope.
Exam essentials
- The roster is fixed and the names are exact —
Read,Write,Edit,Grep,Glob,Bashare the six core built-ins (of ~14), identical to Claude Code’s; they appear verbatim in allow/deny rules and astool_use.name, and a mis-cased name matches nothing. - Read vs write decides parallelism — read-only tools (
Read/Glob/Grep) run concurrently; state-modifying tools (Edit/Write/Bash) run sequentially; custom tools default to sequential and opt in viareadOnlyHint. Orthogonal to D2.3’sdisable_parallel_tool_use. - Six permission modes —
default,acceptEdits,plan,dontAsk,bypassPermissions,auto(TS).plan= read-only;acceptEdits= auto-approve edits + filesystem ops (mkdir/touch/rm/rmdir/mv/cp/sed) insidecwd/additionalDirectories, prompt outside. - Five-step evaluation order — Hooks → Deny rules → Permission mode → Allow rules →
canUseTool. Deny rules and hooks fire before the mode, so they bind even underbypassPermissions; allow rules fire after it, so the mode can override them. - The allowlist trap —
allowed_toolspre-approves, it does not restrict; withbypassPermissionsit approves everything regardless. Confine withplanmode or a deny rule, never with the allowlist alone.