AI News DailyTips한국어
← AI tool tips
Claude Code✓ Confirmed in official docsAdded Oct 16

How to rewrite a command with updatedInput in a Claude Code PreToolUse hook

A PreToolUse hook in Claude Code can do more than block a tool call: it can rewrite the arguments and let the call run. When the hook returns updatedInput, the tool runs with that input instead of what Claude sent. For example, you can turn pip install into uv pip install whenever Claude tries to run it.

  1. Register the hook in your project's .claude/settings.json. The if filter means the script only spawns for matching commands.
{
  "hooks": {
    "PreToolUse": [
      {
        "matcher": "Bash",
        "hooks": [
          {
            "type": "command",
            "if": "Bash(pip install *)",
            "command": "${CLAUDE_PROJECT_DIR}/.claude/hooks/pip-to-uv.sh"
          }
        ]
      }
    ]
  }
}
  1. Create .claude/hooks/pip-to-uv.sh and make it executable. It needs jq.
#!/bin/bash
# .claude/hooks/pip-to-uv.sh
jq '.tool_input
  | .command |= sub("^pip install"; "uv pip install")
  | {hookSpecificOutput: {
      hookEventName: "PreToolUse",
      permissionDecision: "ask",
      permissionDecisionReason: "Rewrote pip install to uv pip install",
      updatedInput: .
    }}'
chmod +x .claude/hooks/pip-to-uv.sh

updatedInput replaces the entire input object, which is why the script takes tool_input as is and only changes command, keeping fields like description and timeout. Permission rules are evaluated against the input your hook returns, not the input Claude sent. With permissionDecision set to "ask" you see and approve the rewritten command in the permission prompt; with "allow" it runs without asking (deny and ask rules still apply).

Since 2.1.300, released October 14, updatedInput from a hook is validated like Claude's own input: unknown keys are dropped, and input the tool rejects denies the call. A misspelled field can silently disappear, so run the hook once after changing it. In a PermissionRequest hook, updatedInput goes inside the decision object.

Get notified when a new tip lands

Tip alerts only go out in the app. Install it and turn notifications on.

Get the app

All tips →