cd /news/ai-tools/show-hn-a-60-line-pretooluse-hook-th… · home topics ai-tools article
[ARTICLE · art-74788] src=github.com ↗ pub= topic=ai-tools verified=true sentiment=· neutral

Show HN: A 60-line PreToolUse hook that stops Claude Code from editing your .env

A developer released a 60-line PreToolUse hook that prevents Claude Code from editing protected files like .env, addressing the failure of prompt-based rules in CLAUDE.md to stop the AI from modifying sensitive files. The guard, part of the claude-code-survival-kr repository, runs before tool calls and blocks edits to paths listed in a protected.txt file, returning the reason on stderr so the model stops instead of retrying.

read2 min views1 publishedJul 27, 2026
Show HN: A 60-line PreToolUse hook that stops Claude Code from editing your .env
Image: source

CLAUDE.md

is advice. The model reads it, the conversation gets long, the rule loses priority, and it edits the file anyway.

That is not a prompting problem. No wording fixes it.

This is not advice. It runs before the tool call and refuses it.

Blocked by guard.py: .env
It matches the pattern '.env' listed in .claude/protected.txt.

The model never gets to write. It gets told why, and moves on.

mkdir -p .claude
curl -o .claude/guard.py        https://raw.githubusercontent.com/avenna01-ceo/claude-code-survival-kr/main/guard/guard.py
curl -o .claude/protected.txt   https://raw.githubusercontent.com/avenna01-ceo/claude-code-survival-kr/main/guard/protected.txt
curl -o .claude/settings.json   https://raw.githubusercontent.com/avenna01-ceo/claude-code-survival-kr/main/guard/settings.json

Already have a .claude/settings.json

? Merge this in instead of overwriting:

{
  "hooks": {
    "PreToolUse": [
      {
        "matcher": "Edit|Write|MultiEdit|NotebookEdit",
        "hooks": [{ "type": "command", "command": "python3 .claude/guard.py" }]
      }
    ]
  }
}

On Windows use python

instead of python3

.

Restart Claude Code. That's it — no dependencies, Python 3.8+.

Edit .claude/protected.txt

. One pattern per line.

.env
.env.*
*.pem
*.key
credentials.json

migrations/**
legacy/**

.claude/guard.py
.claude/protected.txt
.claude/settings.json

A bare filename matches anywhere in the tree, because that's what you mean when you type it. .env

blocks ./.env

and api/.env

both. dir/**

blocks everything under that directory.

Keep the last three lines. They are what stops the model from disabling its own guard when it gets stuck.

echo '{"tool_name":"Edit","tool_input":{"file_path":".env"},"cwd":"'"$PWD"'"}' | python3 .claude/guard.py; echo "exit=$?"

exit=2

means it's live. exit=0

on a protected path means the pattern didn't match.

Does

  • Blocks Edit

,Write

,MultiEdit

,NotebookEdit

on paths you list - Reads every path in a MultiEdit

batch, not just the first - Returns the reason on stderr, so the model stops instead of retrying

  • Fails open— if the hook itself errors, your work continues. A guard that breaks everything when it breaks is worse than no guard.

Doesn't

  • Doesn't block Bash

.rm -rf

still goes through. Gate that separately, or add aBash

matcher and inspect the command string. - Doesn't protect against a user who edits protected.txt

themselves. It's a guardrail, not a permission system.

Where it lives When it loses
CLAUDE.md
in the prompt context gets long, priority drops
hook
in your machine never — it isn't the model's decision

Rules are advisory. Hooks are enforcement. Use both: CLAUDE.md

for why, guard.py

for can't.

Part of claude-code-survival-kr — rules and prompts that stop AI from breaking working code. MIT.

── more in #ai-tools 4 stories · sorted by recency
── more on @claude code 3 stories trending now
sponsored brought to you by zahid.host 4,200+ EU-deployed projects
reading about agents? ship yours in a single git push.

Run your AI side-project on zahid.host

EU-based hosting, git-push deploys, automatic HTTPS, no cold starts. Free tier with a custom domain — perfect for shipping the agent you just read about.

$git push zahid main
Live at https://your-agent.zahid.host
Get free account → Pricing
from €0/mo · no card required
LIVE [news/show-hn-a-60-line-pr…] indexed:0 read:2min 2026-07-27 ·