Allow opt-out of built-in deferred tools via settings to reduce baseline context
Problem Statement
On Claude Code v2.1.123 with a Pro plan (200k cap), a fresh session has a baseline context usage of ~41k tokens before any real work begins. Of that, 20.2k (10.1%) comes from built-in deferred tools — TodoWrite, Cron*, Enter/ExitPlanMode, Enter/ExitWorktree, Monitor, NotebookEdit, PushNotification, RemoteTrigger, TaskOutput, TaskStop, WebFetch, WebSearch, AskUserQuestion. These are listed by name and short description in the system reminder so ToolSearch can discover them.
Listing them by default is a reasonable design choice for discoverability. The problem is there's no way to opt out of the ones I never use.
My workflow:
- Solo Delphi/Firebird development on Windows
- No notebook work →
NotebookEditunused - No scheduled tasks →
Cron*,RemoteTrigger,PushNotification,Monitor,TaskOutput,TaskStopunused - No worktree usage →
Enter/ExitWorktreeunused
That's ~10 tools I never invoke, each contributing to the 20.2k baseline. Combined with built-in MCP integrations (~21k more) and plugins (~10k), the working budget shrinks meaningfully — re-caching after the 5-minute prompt cache TTL costs more, and autocompact triggers earlier in long sessions.
This is distinct from #48680 (claude.ai marketplace MCP instruction blocks loading unconditionally) and #47645 (ToolSearch env var bug, closed as duplicate). Both cover MCP-side issues. This request is specifically about built-in tools shipped with the binary — there's no MCP config to remove and no extension to disable for these.
Proposed Solution
A ~/.claude/settings.json field to opt out of built-in deferred tools by name:
{
"disabledBuiltinTools": [
"CronCreate",
"CronDelete",
"CronList",
"Monitor",
"NotebookEdit",
"PushNotification",
"RemoteTrigger",
"TaskOutput",
"TaskStop"
]
}
Behavior:
- Listed tools are removed from the system reminder entirely (not just hidden from
ToolSearch) ToolSearchcannot discover them- Calling them returns the standard "tool not available" error
- Wildcards (
Cron*) optional but convenient - Default behavior unchanged — opt-in only
Alternative shape with allowlist mode:
{
"deferredTools": {
"mode": "allowlist",
"include": ["TodoWrite", "WebSearch", "WebFetch"]
}
}
Either shape works. The key requirement is that the tool's name and description are removed from the system reminder, not just deferred — that's what reduces baseline tokens.
Alternative Solutions
- Disabled the Chrome extension to drop the
Claude_in_ChromeMCP — works for that specific MCP, but doesn't help with built-in system tools. - Removed unused plugin marketplaces from
settings.json— saves ~500 tokens, marginal. - Set
CLAUDE_CODE_DISABLE_1M_CONTEXT=1to avoid the 1M tier — separate issue (#30033), but related theme of context inflation. /clear,/compact, end-session more frequently — manages active context but doesn't change the baseline floor.
None of these address the built-in tools surface. The only "workaround" today is to accept the 20k tax.
Priority
High - Significant impact on productivity
Feature Category
Configuration and settings
Use Case Example
Scenario: starting a long debugging session on a legacy Delphi codebase.
- Open Claude Code in the project directory.
/contextshows 41k baseline (20.2k from built-in deferred tools, of which I use onlyTodoWrite,WebSearch, andWebFetch).- Working budget after the 33k autocompact buffer is ~125k.
- After 30 minutes of active debugging, I'm near the autocompact threshold and lose conversational context I'd rather keep.
With disabledBuiltinTools configured to drop the ~10 tools I never use:
/contextshows ~21k baseline (50% reduction in deferred tools).- Working budget grows to ~145k.
- Autocompact triggers later or not at all in a typical session.
- Re-caching after the 5-minute TTL is cheaper because the cache prefix is smaller.
The same pattern helps users on Free/Pro plans with tighter caps, and users with many memory files or MCPs who are already close to limits.
Additional Context
Screenshot of /context on a fresh session (one greeting exchange) showing the 20.2k cost of built-in deferred system tools — see image attached below.
Related issues:
- #48680 — claude.ai marketplace MCP instructions inject regardless of Tool Search (different mechanism)
- #47645 —
ToolSearchenv var ignored, MCP tools load eagerly (closed as duplicate) - #41809 — disabled MCP servers still appear in deferred list
- #38365 — feature request for lazy MCP initialization
- #44653 — Plan mode
ExitPlanModenot available viaToolSearch(evidence of edge cases in the deferred tools system) - #30033 — 1M context bug v2.1.63 (similar UX of silent context inflation)
Environment:
- Claude Code: v2.1.123
- Platform: Windows 11
- Plan: Pro
- Plugins: caveman, context-mode, skill-creator
- Note: Chrome extension was disabled before taking the screenshot, but
MCP tools (deferred)is still ~21k from other built-in MCPs (Claude_Preview,ccd_*,mcp-registry,scheduled-tasks, plugin MCPs).
Happy to provide repro logs, test a prototype, or refine the proposed schema if helpful.
<img width="1080" height="1860" alt="/context fresh session" src="https://github.com/user-attachments/assets/4dfc0e87-3cc1-4c92-9057-dff124e29dc8" />
6 Comments
Found 3 possible duplicate issues:
This issue will be automatically closed as a duplicate in 3 days.
🤖 Generated with Claude Code
The 3 candidates flagged are all related but cover different surfaces:
claude-developer-platform). Skills, not tools..claude/skills/). Skills, not tools.startDisabled). The MCP server angle is well-covered by that chain.This issue is specifically about the ~13 built-in deferred system tools shipped with the Claude Code binary and listed in the system reminder for
ToolSearch:TodoWrite,CronCreate,CronDelete,CronList,Enter/ExitPlanMode,Enter/ExitWorktree,Monitor,NotebookEdit,PushNotification,RemoteTrigger,TaskOutput,TaskStop,WebFetch,WebSearch,AskUserQuestion. There is no MCP server backing them, no plugin to disable, and no skill to toggle. The proposal is a programmaticsettings.jsonfield — not a UI — targeting that specific surface.The broader pattern across these issues (skills, MCPs, tools all inflating baseline context) suggests a consistent design opportunity: a single mental model for opting out of built-in capabilities —
disabledSkills,disabledMcpServers,disabledBuiltinTools. Same shape, three orthogonal surfaces. Each issue covers one.Happy to consolidate if reviewers prefer a single meta-issue.
+1 — this is the single highest-impact baseline reduction we currently can't touch.
On Opus 4.8 (1M context),
/contextshows ~12k tokens of System tools (deferred) — built-in tool names (Cron*,Monitor,NotebookEdit,PushNotification,RemoteTrigger,Task*) that our workflow never calls but pays for on every turn. There is no way to opt out today.The proposed
disabledBuiltinTools(or thedeferredTools: { mode: allowlist }variant) would remove these names from the system reminder entirely. In our setup that is ~10k tokens of pure baseline savings with zero functional loss. Would really appreciate seeing this prioritized.Closing for now — inactive for too long. Please open a new issue if this is still relevant.
According to the claude code docs%20is%20equivalent%20to%20Bash%20and%20matches%20all%20Bash%20commands.%20As%20a%20deny%20rule%2C%20both%20forms%20remove%20the%20tool%20from%20Claude%E2%80%99s%20context.) the tools can be removed from the context with:
And that seems to be working for me.
Another data point for this: heavy ToolSearch setups (many MCP servers,
ENABLE_TOOL_SEARCH=true) still pay a per-session round-trip for the built-ins that get used in virtually every session — TaskCreate/TaskGet/TaskList/TaskOutput/TaskStop/TaskUpdate, Monitor, SendMessage, EnterPlanMode/ExitPlanMode. Deferring those buys almost nothing (their schemas end up loaded every session anyway) and costs a first-use ToolSearch call each time.We now work around it with a SessionStart hook that injects additionalContext telling the model to batch-load them in one
ToolSearch("select:TaskCreate,TaskGet,...")call on its first turn. It works, but it spends model attention on plumbing. A nativealwaysLoad-style knob for built-ins (mirroring the per-serveralwaysLoadin.mcp.json) would remove the workaround.