PlusMagi's Blog By Pitt Phunsanit GIT,Shell Script วิธีตั้งค่า Git Pre-commit hook ด้วยเฟรมเวิร์ก pre-commit เพื่อรัน ShellCheck

วิธีตั้งค่า Git Pre-commit hook ด้วยเฟรมเวิร์ก pre-commit เพื่อรัน ShellCheck

การใช้เฟรมเวิร์ก pre-commit ช่วยให้การรัน ShellCheck เกิดขึ้นอัตโนมัติก่อนคำสั่ง git commit จะสำเร็จ ป้องกันไม่ให้โค้ดที่มีข้อผิดพลาดหลุดเข้าสู่ Repository ได้ตั้งแต่ต้นทาง


ขั้นตอนการติดตั้งและตั้งค่า

1. ติดตั้งเครื่องมือ pre-commit

ติดตั้งลงในเครื่องผ่าน Package Manager:

  • macOS (Homebrew)
    brew install pre-commit
  • Linux / ทั่วไป (ผ่าน pipx หรือ pip)
    pip install pre-commit

2. สร้างไฟล์ .pre-commit-config.yaml

สร้างไฟล์ชื่อ .pre-commit-config.yaml ไว้ที่ Root ของ Git Repository โดยระบุ Hook สำหรับ ShellCheck ดังนี้:

YAML

repos:
  - repo: https://github.com/koalaman/shellcheck-precommit
    rev: v0.10.0  # ระบุ Release tag ของ Hook (สามารถอัปเดตเป็นเวอร์ชันล่าสุดได้)
    hooks:
      - id: shellcheck
        # ส่ง arguments เพิ่มเติม (ถ้าต้องการ)
        args: ["--severity=warning"]

หมายเหตุเรื่อง Binary: Hook ของ koalaman/shellcheck-precommit เป็น Wrapper ที่จะเรียกใช้ไบนารี shellcheck ภายในเครื่อง ดังนั้นต้องติดตั้ง ShellCheck ลงในเครื่องไว้ด้วย (brew install shellcheck หรือ apt-get install shellcheck)

3. ติดตั้ง Hook ลงใน Git Hooks Directory

รันคำสั่งนี้เพียงครั้งเดียวที่ Root ของ Repository เพื่อให้ Git ผูกสคริปต์เข้ากับกระบวนการ commit

pre-commit install

ผลลัพธ์จะขึ้นข้อความยืนยัน

pre-commit installed at .git/hooks/pre-commit


การปรับแต่งขั้นสูงสำหรับโปรเจกต์ขนาดใหญ่

1. ให้อ่านไฟล์คอนฟิก .shellcheckrc เสมอ สามารถส่งแฟล็ก --rcfile หรือบังคับเชลล์เริ่มต้นได้ผ่านฟิลด์ args

repos:
  - repo: https://github.com/koalaman/shellcheck-precommit
    rev: v0.10.0
    hooks:
      - id: shellcheck
        args:
          - "--rcfile=.shellcheckrc"
          - "--severity=style"

2. การยกเว้นไดเรกทอรีที่ไม่ต้องการตรวจ (Exclude Paths) หากในโปรเจกต์มีโฟลเดอร์ภายนอก เช่น vendor/, node_modules/ หรือโฟลเดอร์ template สามารถใช้ Regular Expression กำหนด exclude ได้

repos:
  - repo: https://github.com/koalaman/shellcheck-precommit
    rev: v0.10.0
    hooks:
      - id: shellcheck
        exclude: ^(vendor/|third_party/|\.build/)

3. จัดการไฟล์ที่ไม่มีนามสกุล .sh (Executable Shell Scripts) ตามค่าเริ่มต้น Pre-commit จะตรวจสอบไฟล์ตามชนิดของระบบไฟล์ หากมีไฟล์สคริปต์ที่ไม่มีนามสกุล (เช่นไฟล์ CLI ในโฟลเดอร์ bin/) ให้ระบุ types: เพื่อให้ระบบตรวจสอบจาก Shebang บนหัวไฟล์

repos:
  - repo: https://github.com/koalaman/shellcheck-precommit
    rev: v0.10.0
    hooks:
      - id: shellcheck
        types: [shell]


คำสั่งที่ใช้งานเป็นประจำ

  • ทดสอบรันกับทุกไฟล์ในโปรเจกต์ทันที (โดยไม่ต้องแก้ไฟล์)
    pre-commit run --all-files
  • ทดสอบรันเฉพาะ ShellCheck Hook
    pre-commit run shellcheck --all-files
  • อัปเดตเวอร์ชันของ Hooks ทั้งหมดในไฟล์ config
    pre-commit autoupdate
  • ข้ามการตรวจชั่วคราวในกรณีฉุกเฉิน (Bypass)
    git commit -m "Emergency fix" --no-verify

เมื่อตั้งค่าเสร็จสิ้น ทุกครั้งที่มีการสั่ง git commit ShellCheck จะเข้าตรวจสอบเฉพาะไฟล์ Shell Script ที่มีการเปลี่ยนแปลง (Staged Files) หากพบปัญหา Git จะบล็อกการ Commit พร้อมแสดงหมายเลขบรรทัดและรหัส SC ทันที