TROISINH
Nâng cao & Tự động hoáHooks — Tự động hoá sự kiện

PreToolUse Hook: Chặn lệnh nguy hiểm trước khi AI thực thi

Chặn lệnh nguy hiểm như rm -rf và DROP TABLE trước khi Claude Code chạy. Ràng buộc cứng bảo vệ codebase khỏi AI hallucination và lỗi vô ý xóa production.

Định nghĩa

PreToolUse Hook là scripts chặn (interceptor) chạy ngay trước khi Claude Code gọi bất kỳ tool nào (Bash, Write, Edit), phân tích nội dung lệnh và trả về exit code 2 để phủ quyết (veto) các thao tác nguy hiểm như rm -rf / hay DROP TABLE. Nó hoạt động như "công tắc an toàn vật lý" bên ngoài vòng lặp suy nghĩ của LLM — đảm bảo rằng dù AI có bị hack hay hallucinate, hệ thống file và database vẫn an toàn.

Giải thích chi tiết

Vì sao cần chặn lệnh bên ngoài LLM?

LLM là hệ thống xác suất, không phải máy tính để bàn truyền thống. Claude đôi khi "nói nhảm" (hallucinate) ra lệnh xóa database khi đang cố fix bug, hoặc bị "jailbreak" qua prompt injection để thực thi mã độc. Các lời nhắc nhở như "hãy cẩn thận" trong CLAUDE.md chỉ là ràng buộc mềm — mô hình có thể quên hoặc bị thuyết phục bỏ qua.

PreToolUse đưa ràng buộc cứng (hard constraints) ra bên ngoài não AI. Dù Claude có bị hack hoặc điên loạn hoàn toàn, script kiểm tra bên ngoài vẫn chặn được lệnh rm -rf nhờ pattern matching. Đây là sự phân tách cơ chế (mechanism separation): LLM giữ vai trò "bộ não" lập kế hoạch, còn hook là "công tắc an toàn" kiểm soát động cơ.

Cơ chế hoạt động: Exit code 2

Khi Claude định chạy một tool, hook nhận metadata (tên tool, tham số) qua stdin hoặc biến môi trường. Script thực thi kiểm tra (regex, semantic analysis) và trả về:

  • Exit 0: Cho phép chạy
  • Exit 2: Phủ quyết (block) — theo Unix philosophy, exit 2 nghĩa là "misuse of command" (dùng sai lệnh), khác với exit 1 (lỗi chung)
  • Exit khác: Có thể chỉ ghi log cảnh báo mà không chặn

Khi bị chặn, Claude hiển thị stderr của hook để người dùng biết lý do. Điều này tạo ra kênh ngữ nghĩa rõ ràng: hook không phải đang crash (exit 1), mà đang chủ động thực thi quyền phủ quyết.

Giới hạn và bypass vectors

Hiện tại (đầu 2025), PreToolUse chặn được Bash tool nhưng gặp vấn đề với Write/Edit operations — file operations dường như bypass pipeline tool-use chuẩn (GitHub issue #13744).

Ngoài ra, LLM có thể "lách" kiểm tra đơn giản bằng cách mã hóa lệnh: dùng Perl encoding, Python heredocs, hoặc base64 decode để ẩn rm -rf. Do đó, hook cần kiểm tra semantic (ý định) chứ không chỉ string matching. Đây là lý do tại sao PermissionRequest HookAgent Tools với allowlist/denylist là bổ sung quan trọng, không thay thế lần nhau.

Ví dụ thực tế

Chặn rm -rf và DROP TABLE trong dự án ngân hàng

Tạo file ~/.claude/hooks/pretooluse/block-dangerous.sh:

#!/bin/bash
# Đọc input từ stdin (JSON metadata về tool được gọi)
read -r input

# Kiểm tra các pattern nguy hiểm trong Bash commands
if echo "$input" | grep -qE 'rm\s+-rf\s+/|DROP\s+TABLE|DELETE\s+FROM.*WHERE.*='; then
    echo "BLOCKED: Lệnh nguy hiểm phát hiện!" >&2
    echo "Chi tiết: $input" >&2
    exit 2  # Phủ quyết cứng
fi

# Kiểm tra force push vào main (critical cho team Viettel, FPT, VNG)
if echo "$input" | grep -qE 'git\s+push\s+.*--force.*main|git\s+push\s+-f.*main'; then
    echo "BLOCKED: Force push vào main branch bị cấm!" >&2
    exit 2
fi

exit 0  # Cho phép chạy

Chmod để executable:

chmod +x ~/.claude/hooks/pretooluse/block-dangerous.sh

Khi Claude cố gõ rm -rf /tmp/test, hook sẽ chặn ngay lập tức, hiển thị lỗi đỏ trước khi một byte nào bị xóa. Điều này đặc biệt quan trọng khi làm việc với database Oracle hoặc SQL Server của các dự án tài chính Việt Nam, nơi một lệnh DROP TABLE sai mục tiêu có thể xóa sổ lịch sử giao dịch VietQR.

Bảo vệ file cấu kỳ trong startup Việt Nam

Script kiểm tra trước khi ghi đè file .env, config/database.yml, hoặc các file chứa secret key của MoMo/ZaloPay API:

#!/bin/bash
read -r input

# Trích xuất file_path từ JSON (giả sử đơn giản bằng grep)
file_path=$(echo "$input" | grep -o '"file_path": "[^"]*"' | cut -d'"' -f4)

# Danh sách file cấm sửa trực tiếp - thêm file config riêng của dự án
PROTECTED_FILES=(".env" ".env.production" "config/master.key" "id_rsa" "firebase-service-account.json")

for protected in "${PROTECTED_FILES[@]}"; do
    if [[ "$file_path" == *"$protected"* ]]; then
        echo "CẢNH BÁO: Bạn đang cố sửa file nhạy cảm: $file_path" >&2
        echo "Hãy dùng \`--force\` nếu thực sự cần, hoặc liên hệ Tech Lead." >&2
        exit 2
    fi
done

exit 0

Điều này cực kỳ hữu ích trong team 5-10 người làm startup tại TP.HCM hoặc Hà Nội, khi junior dev dùng Claude Code có thể vô tình yêu cầu AI "giúp sửa config Shopee API" mà không biết đang đụng vào secret key production đang chạy live.

Giới hạn thư mục làm việc (Chroot safety)

Đảm bảo Claude không ra khỏi thư mục dự án, tránh sửa nhầm file hệ thống macOS hoặc Linux:

#!/bin/bash
read -r input

# Kiểm tra nếu command chứa đường dẫn ngoài ~/projects/ hoặc thư mục hiện tại
if echo "$input" | grep -qE '(\.\./|/etc/|/usr/bin|/home/[^/]+/\.ssh|/System/|C:\\Windows)'; then
    echo "BLOCKED: Thao tác ngoài scope dự án!" >&2
    exit 2
fi

exit 0

Ứng dụng

Developer cá nhân (Freelancer/Solo)

Bảo vệ khỏi "tay nhanh hơn não". Khi dùng Auto Mode để chạy batch refactoring, PreToolUse đóng vai trò "người bạn đồng hành cẩn trọng", ngăn bạn vô tình xóa nhầm thư mục node_modules của client Tiki hay drop database local đang chứa dữ liệu test quan trọng.

Team Lead trong doanh nghiệp

Thiết lập policy chung bằng cách commit hooks vào repo và yêu cầu team symlink vào ~/.claude/hooks/. Đảm bảo mọi thành viên đều có cùng rào cản an toàn khi dùng Claude Code cho doanh nghiệp, tránh lỗi "tay mới" gây thảm họa production cho hệ thống ngân hàng hoặc fintech.

DevOps và CI/CD

Kết hợp với Headless Mode (claude -p), PreToolUse đảm bảo các script tự động không bị AI "tưởng nhầm" và xóa file hệ thống. Hook tạo audit trail rõ ràng: mỗi lệnh bị chặn đều có log stderr để review sau, phù hợp cho các pipeline deploy của công ty hosting Việt Nam như MatBao hoặc PA Việt Nam.

So sánh

Đặc điểmPreToolUse HookPostToolUse HookManual Approval (Plan Mode)
Thời điểm chặnTrước khi chạySau khi chạyTrước khi chạy
Khả năng hoàn tácNgăn từ đầuChỉ phát hiện sau lỗiNgăn từ đầu
Tự động hóaHoàn toàn tự độngTự độngCần human-in-the-loop
Phù hợpLệnh nguy hiểm rõ ràngFormat code, loggingQuyết định kiến trúc phức tạp
Độ tin cậyCao (code-level)Trung bìnhCao (human judgment)

Kết luận: PreToolUse là lớp phòng thủ đầu tiên (fail-safe) cho các lệnh đã biết rõ là nguy hiểm (xóa file, sửa production config). Nó không thay thế Plan Mode (cho quyết định mang tính chiến lược) hay PostToolUse (cho việc dọn dẹp sau khi edit), mà bổ sung cho chúng tạo thành hệ thống defense-in-depth.

Bài viết liên quan

Cùng cụm

Đọc tiếp

On this page