From esond
Review and consolidate Claude Code permission entries in settings.json files. Use this skill whenever the user wants to clean up, consolidate, review, audit, or prune their Claude Code permissions, or says things like "my allow list is huge", "too many permission entries", "the permissions file is a mess", "consolidate my permissions", or "look at settings.local.json". Also trigger proactively when the user mentions "permissions", "settings.local.json", "settings.json", "allow list", or complains about repeatedly approving similar commands — even if they don't literally ask to "consolidate".
How this skill is triggered — by the user, by Claude, or both
Slash command
/esond:permission-consolidatorThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
You help users clean up their Claude Code permission allow lists by finding entries
You help users clean up their Claude Code permission allow lists by finding entries that can be consolidated and flagging one-off entries that may be stale.
Claude Code settings files (typically settings.local.json in a project's .claude/
directory, or ~/.claude/settings.json globally) contain permission allow lists:
{
"permissions": {
"allow": [
"Bash(git add:*)",
"Bash(git commit:*)",
"Bash(git push:*)",
"WebFetch(domain:github.com)",
"mcp__github__pull_request_read"
]
}
}
Entries follow patterns:
Bash(command subcommand args:*) — shell commands with wildcard suffixesBash(command subcommand:specific-value) — shell commands with exact match (no wildcard)WebFetch(domain:example.com) — web fetch by domainWebSearch — bare tool namesmcp__server__tool_name — MCP tool permissionsIf the user provides a path, use it. Otherwise, look for settings files:
<project>/.claude/settings.local.json~/.claude/settings.jsonRead the file and extract permissions.allow. If the file doesn't exist, or
permissions.allow is missing or empty, say so and stop — there is nothing to
consolidate.
Strip the Bash( prefix and trailing ) from each Bash(...) entry to get the
inner command pattern, then group those inner patterns by command prefix
hierarchy. Build a tree using the stripped form (easier to read):
gh
├── gh pr create:*
├── gh pr view:*
├── gh pr review:*
├── gh api:*
└── gh run:*
A consolidation candidate exists when 2+ entries share a command prefix and could be replaced by a single broader entry. Work from the leaves inward:
gh pr create:*, gh pr view:*, gh pr review:* → gh pr:*gh pr:* + gh api:* + gh run:* → gh:*When you surface a candidate to the user or write it back to the file, re-wrap
it as a full permission entry — e.g., Bash(gh:*), not gh:*. The stripped
form is only for analysis and display inside the tree; anything the user
confirms ends up in permissions.allow as a valid Bash(...) string.
Present the most aggressive reasonable consolidation as the suggestion, but show the intermediate options too so the user can pick their comfort level.
Also look for redundant entries — e.g., if both Bash(dotnet:*) and
Bash(dotnet test:*) exist, the specific one is already covered by the broad one.
Identify entries that look like one-off commands or accidents:
Bash(yarn format:fix) instead of Bash(yarn format:*) — may be
intentionally narrow, or may be an oversightBash(...) entry with a 40-character commit SHA or a
GitHub node ID embedded in it) — these were almost certainly approved for a
single past invocation and won't match againBash(do gh:*), Bash(done))Bash(read hash:*), Bash(head:*)) — these were likely approved for a
one-time taskUse AskUserQuestion to walk through findings one at a time. For each item, clearly show what you found and what you propose.
For consolidation candidates, show:
For suspicious entries, show:
After walking through all findings, summarize the confirmed changes and apply them
to the file. Show a before/after diff of the allow array.
Bash(git add:*) + Bash(git commit:*) into Bash(git:*)
means Claude could also run git reset, git rebase, etc. without asking.
Always mention what additional access a consolidation grants so the user can
make an informed decision.WebFetch, WebSearch, mcp__*) don't typically need
consolidation — leave them alone unless the user asksdeny, ask, hooks, etc.)Creates, edits, and optimizes skills for Claude Code, including drafting, evaluating with test prompts, iterating on performance, and improving skill descriptions for better triggering accuracy.
npx claudepluginhub esond/claude-skills --plugin esond