nixcfg/config/opencode/skills/ask-claude/SKILL.md
Harald Hoyer 5d0e1fcdd6 docs(opencode): steer ask-claude skill toward repo access for reviews
Add a "Code review pattern" section that tells the opencode agent to give
claude read-only access to the repo (Read/Grep/Glob plus a narrow git
allowlist) instead of gathering a full `git diff` and piping it in. The
piped-diff form loses surrounding-file context, bloats the prompt, and
falls over on large branches. Also adds a matching entry to "Don'ts" and
caveats the existing pipe-stdin example.

Motivated by an opencode run that collected the entire branch diff as
stdin instead of pointing claude at the working tree.
2026-05-05 13:56:40 +02:00

7.6 KiB

name description
ask-claude Consult Claude (Anthropic's flagship model, Opus-class) as an oracle when you are uncertain, stuck, or facing a problem that needs deeper reasoning than your current model provides. Trigger when you would otherwise guess, when the user asks a hard architectural / design / debugging question, when you have produced two contradictory hypotheses, or when a code review needs a second opinion. Calling out to `claude` gives you results from a much more intelligent model — use it instead of guessing.

Ask Claude

Run claude -p "<prompt>" via the bash tool to get a one-shot answer from Claude. Claude is significantly more capable at reasoning, code review, and architectural judgment than smaller models — when you are not sure, ask.

When to use

  • You are uncertain between two approaches and want a second opinion.
  • The user asked a question whose answer you would otherwise guess.
  • You have a tricky bug, a subtle race condition, or a non-obvious design call.
  • You want a code review on a diff before reporting "done".
  • You need a careful read of a long document or a hairy stack trace.

Do not use it for trivial lookups (use web-search), simple file edits, or anything you are already confident about — calls cost money and time.

Basic invocation

claude -p "Your question here, with all relevant context inline."

The prompt should be self-contained — Claude starts with no memory of this conversation. Include the file paths, code snippets, error messages, and what you have already tried.

Piping context via stdin

For longer context (a file, a diff, log output), pipe it in:

cat path/to/file.rs | claude -p "Review this for race conditions; explain any you find."
git diff main...HEAD | claude -p "Spot bugs or risky changes in this diff."

Only pipe when the context is small and self-contained. For anything that spans multiple files, prefer giving Claude repo access (next section) so it can read surrounding code, not just the patch.

Code review pattern

For a review of the current branch / working tree, do not gather diffs yourself and stuff them into the prompt. Point Claude at the directory and let it run git and read files on its own — it sees more context (full files, history, neighbouring code) than a piped diff alone can provide, and it will only fetch what it actually needs.

Recommended invocation, run from the repo root:

claude -p --permission-mode dontAsk \
  --allowedTools "Read Grep Glob Bash(git diff:*) Bash(git log:*) Bash(git status:*) Bash(git show:*)" \
  "Review the changes on this branch vs main. Flag bugs, risky changes,
   and anything that violates the project's conventions. Read whatever
   files you need for context."

Why this is better than git diff … | claude -p:

  • Claude can open the full file around a hunk, not just the ±3 lines of context in the patch.
  • Claude can follow references — call sites, tests, related modules.
  • The prompt stays small, so the model spends its tokens on reasoning instead of re-reading a diff you already had on disk.
  • Works for large diffs that would otherwise blow the context window.

Use the piped form only for a tiny, self-contained snippet where extra repo context genuinely adds nothing.

Permissions

In -p mode there is no human to approve prompts, so anything not explicitly permitted is denied. Default behaviour: Claude can reason about the text you give it but cannot touch the filesystem, run shell commands, or hit the network. That is usually exactly what you want for an oracle call.

When Claude does need tool access, you control it with these flags:

--allowedTools / --disallowedTools

Whitelist or blacklist tools. Names are space- or comma-separated, and each entry can carry a permission spec in parentheses to narrow the scope.

# Read-only project access — the most common upgrade
claude -p --allowedTools "Read Grep Glob" "..."

# Allow only specific bash subcommands
claude -p --allowedTools "Read Grep Glob Bash(git diff:*) Bash(git log:*)" "..."

# Allow web fetches, but only to one domain
claude -p --allowedTools "WebFetch(domain:docs.python.org)" "..."

# Block one tool, allow the rest of the defaults
claude -p --disallowedTools "Bash" "..."

Spec syntax cheatsheet:

  • Bash — every shell command (broad; avoid).
  • Bash(git *) — any git invocation.
  • Bash(git diff:*)git diff and its sub-args only.
  • Read / Grep / Glob — usually safe to allow whole.
  • Edit(./src/**) / Write(./src/**) — directory-scoped writes.
  • WebFetch(domain:example.com) — pin web access to one host.

--tools

Coarser switch over the built-in toolset. Use --tools "" to disable everything built-in (only MCP tools and what --allowedTools adds), or --tools "Read,Edit,Bash" to pick a subset. --allowedTools then layers on top with finer-grained specs.

--permission-mode <mode>

Sets the default behaviour for anything not covered by allow/disallow:

Mode Effect
default prompt; in -p mode this means "deny" (no human present).
dontAsk silently deny anything not pre-allowed — clean for -p.
plan read-only planning; Claude proposes but cannot edit or run.
acceptEdits auto-accept file edits; still prompts for Bash etc.
auto model decides per-call; treat as semi-trusted.
bypassPermissions skip all checks. Equivalent to --dangerously-skip-permissions.
# Strict deny-by-default with an explicit allowlist (recommended for -p)
claude -p --permission-mode dontAsk \
  --allowedTools "Read Grep Glob" \
  "Audit error handling in src/auth/."

# Plan mode for a design review — Claude reads, thinks, won't touch anything
claude -p --permission-mode plan "Propose a refactor for X."

--add-dir

Without it Claude only sees the current working directory. Add others when the question spans repos:

claude -p --allowedTools "Read Grep Glob" \
  --add-dir ../other-repo --add-dir /etc/nixos \
  "Compare how both projects handle config loading."

--dangerously-skip-permissions

Bypasses all checks. Only use inside a sandbox with no network and no secrets mounted. For oracle-style calls there is essentially no reason to set this — if Claude needs to do destructive things, you should be doing them, not it.

Cost and model controls

These are not permissions but belong in the same risk-management box:

  • --model opus / --model sonnet — pick the tier. Opus for hard reasoning, Sonnet when speed/cost matters.
  • --output-format json — stable structured output for piping into jq.

Output

Default output is plain text on stdout, suitable for piping or for showing to the user. For machine-readable output use --output-format json and parse with jq.

Don'ts

  • Don't call claude -p in a loop or for trivial questions — it is expensive.
  • Don't pass the entire conversation history; distill the question first.
  • Don't gather a giant git diff and pipe it in for code review — give Claude read-only repo access (see "Code review pattern") and let it pull exactly the context it needs.
  • Don't ask Claude to "do" multi-step refactors with file writes — collect its recommendations and apply them yourself, so you stay in control.
  • Don't forget that Claude has no memory between calls — every invocation needs the full context.