Claude Code Tools Deep Dive #2 — EnterPlanMode: Why an Empty Schema Is a Design Choice In the second installment of the Claude Code Tools Deep Dive series, a developer examines EnterPlanMode, a tool that switches Claude Code into a planning mode with read-only exploration and a structured plan file. The design choice of an empty schema is highlighted as intentional, enforcing a workflow that prevents premature code changes and improves alignment between the AI and the user. This is the second post in my Claude Code Tools Deep Dive series. The previous post https://dev.to/ 94be737e156beb4d74df2/claude-code-tools-deep-dive-1-askuserquestion-4ck1 unpacked AskUserQuestion , a structured tool that lets users choose from concrete options. This time, we're looking at its sibling: EnterPlanMode . Before reading this post, it may help to read the series prelude https://dev.to/ 94be737e156beb4d74df2/claude-code-tools-deep-dive-0-how-the-tool-mechanism-actually-works-59p6 on how Claude Code's tool mechanism works. This article follows the same four-layer framework introduced there. Like AskUserQuestion, EnterPlanMode is a tool you may encounter almost every day. But its design is much heavier. It does not merely ask a question; it switches Claude into an entirely different mode of operation . EnterPlanMode is Claude Code's built-in entry point into planning mode . Its job is simple but forceful: move Claude from the default "think while writing" workflow into a planning workflow built around read-only exploration and solution design . Claude returns to implementation only after the user explicitly approves the plan. The core problem it solves is alignment between the AI and the user : Scenario: the user tells Claude, "Refactor this authentication module and replace JWT with session cookies." The request sounds clear, but it actually spans login routes, token-generation middleware, frontend storage, session-expiration policy, database schema decisions, and backward compatibility for existing API consumers. It is a multi-file, multi-decision, dependency-heavy change . Without a planning boundary, Claude has to infer an approach from the available context and start editing immediately: auth/middleware.ts and switch it to reading a session cookie. auth/routes.ts , remove JWT issuance, and replace it with req.session . frontend/api.ts and remove the Authorization header logic. models/user.ts and add a sessionId field.The user sees the diff and says: "I only wanted sessions for the web app. The backend services still need JWT. Why did you replace authentication for the entire API?" Several things went wrong: The core pain: "think while writing" lets Claude generate diffs before the approach is stable, while the user cannot see the full design until the end. Claude first declares that it wants to enter plan mode and asks for the user's approval. That transition is itself an interactive confirmation. If the user declines, Claude remains in the default mode. Claude's toolset becomes narrower: Claude physically cannot modify project files. Every exploration action is read-only. auth/middleware.ts .For example: This is exactly the clarification pattern discussed in the previous post. AskUserQuestion and EnterPlanMode are natural partners. Claude writes the complete proposal to a plan file: scope, affected files, migration steps, risks, and rollback strategy. This is a revisable, referenceable artifact—not a transient chat message. The user sees the complete plan and chooses what happens next: Not a single project file is modified before approval. The user's tokens, time, and attention are not spent implementing the wrong approach. | Anti-pattern pain | EnterPlanMode's solution | |---|---| | Directional error discovered five steps too late | No project files can be changed before ExitPlanMode approval | | Unclear decision boundaries | AskUserQuestion clarifies critical forks inside plan mode | | User cannot see the big picture | The plan file presents a complete proposal instead of scattered diffs | | Important side effects are not surfaced | The enforced explore → design → present sequence gives Claude time to reason through them | | High rollback cost | Exploration is read-only, so rejecting a plan requires no code rollback | The tool's official description contains an interesting rule: non-trivial implementation tasks should default to planning. This is a deliberately conservative bias. One phrase in the original description is especially revealing: "err on the side of planning." When uncertain, plan first. The default itself exposes the designers' preference: bias toward alignment over speed . EnterPlanMode AskUserQuestion carries signals across all four design layers. EnterPlanMode distributes them very differently: the name performs work that a schema might otherwise do. Enter is a verb that implies moving into a state—not fetching data or performing a one-off action. PlanMode names that state and forms a natural pair with ExitPlanMode .Consider a counterfactual design: SetMode mode: "plan" . The model might interpret that as setting a property and switch modes casually. The current name encodes a ceremonial state transition : entering is explicit, and exiting is explicit. Its semantics are much stronger than a parameterized SetMode. That is why the schema can be empty. The name has already locked down the meaning, so the schema does not need to rescue it. EnterPlanMode's description revolves around four questions: when to use it, when not to use it, how it divides work with neighboring tools, and what happens at runtime. Prefer using EnterPlanMode for implementation tasks unless they're simple. One sentence reshapes Claude's behavior. When uncertain, plan instead of immediately acting. The tool starts by moving the default setting toward caution. The "When to Use This Tool" section lists seven numbered cases, each with concrete signals. A representative example is: Multi-File Changes: The task will likely touch more than 2-3 files This supplies a quantified threshold instead of asking Claude to trust a subjective feeling. Intuition becomes an operational rule, reducing inconsistency around whether plan mode is warranted. If you would use AskUserQuestion to clarify the approach, use EnterPlanMode instead This turns a fuzzy boundary into a direct rule: AskUserQuestion handles isolated clarification, while approach-level forks call for plan mode. It prevents the anti-pattern of repeatedly asking disconnected questions and trying to assemble the answers into a plan afterward. Pure research/exploration tasks use the Agent tool with explore agent instead This defines another boundary: do not use EnterPlanMode for research that will not lead to implementation. Plan mode exists for planning before implementation. If implementation is not the goal, entering it is wasted motion; delegate the investigation to an explore agent instead. This tool REQUIRES user approval - they must consent to entering plan mode The AI cannot unilaterally change the workflow. The user guards the transition. This also explains why the tool accepts no arguments: the call itself is a request, not the execution of a parameterized operation. If unsure whether to use it, err on the side of planning - it's better to get alignment upfront than to redo work This is the description's statement of values : a round of alignment is cheaper than an incorrect implementation and rollback. The same philosophy appeared in AskUserQuestion. Claude Code's tool ecosystem consistently favors alignment. Users appreciate being consulted before significant changes are made to their codebase This sentence trains Claude's social intuition . Planning is not merely an efficiency mechanism; it respects the user's ownership of the codebase. The framing encourages Claude to treat consultation as good collaboration rather than an interruption. None. EnterPlanMode has no input fields. Its schema is the empty object {} , so this layer does not exist. Every behavioral signal moves up into the tool-level description. None. The input schema is empty: no fields, no types, and no constraints. Calling the tool is itself the intention to change state; there is no data to pass. That absence is a design signal in its own right: permission is enforced at the tool and runtime layers, not the parameter layer. Claude does not need to request individual permissions or specify a target mode. After Claude calls EnterPlanMode, the runtime automatically: Unlike AskUserQuestion, which ends after the answer arrives, plan mode is a persistent state . Together, the three tools form a complete decision pipeline: Encounter an unclear fork ↓ AskUserQuestion: clarify A vs. B ↓ EnterPlanMode: enter planning mode ├─ Explore with Grep / Read / Glob / Agent ├─ Clarify sub-decisions with AskUserQuestion as needed └─ Write the plan file ↓ ExitPlanMode: submit the plan ├─ User approves → return to default mode and implement ├─ User requests changes → revise in plan mode └─ User rejects → stop or change direction As discussed in the AskUserQuestion post, Claude should not use AskUserQuestion inside plan mode for the meta-question, "Is this plan OK?" The reason is temporal: the user cannot see the plan until ExitPlanMode presents it for approval. Asking whether an invisible plan is acceptable is meaningless. EnterPlanMode's elegance is not simply that it "makes the AI think before acting." It comes from an extremely uneven distribution of design signals : That reveals a deeper principle: an empty schema is itself a design choice. When a tool's meaning is "transition into a state," parameterizing it can weaken the meaning. SetMode invites casual switching. A zero-argument EnterPlanMode is a deliberate, ceremonial request. The next post will examine ExitPlanMode , the final stage of this three-tool decision pipeline, and unpack how "submit a plan for approval" is designed.