如何使用 Pre-commit Hook 搭配 Black 套件在Push到GitHub 前自動格式化程式碼

Yanwei Liu
6 min readJun 13, 2024

--

在軟體開發過程中,保持程式碼風格的一致性和可讀性非常重要。使用 pre-commit hook 搭配 Black 套件,可以在每次提交 (commit) 之前自動格式化你的 Python 程式碼,確保程式碼風格一致,減少團隊協作中的合併衝突。以下是詳細的步驟介紹,讓你能夠輕鬆設置這個流程。

前置條件

在開始之前,請確保你已經安裝了以下工具:

  • Python
  • Git
  • pip
  • virtualenv(可選,但建議使用)

步驟一:安裝 Black 和 pre-commit 套件

首先,安裝 Black 和 pre-commit 套件。打開你的終端並運行以下命令:

pip install black pre-commit

步驟二:創建和配置 pre-commit 配置文件

在你的專案根目錄下創建一個名為 .pre-commit-config.yaml 的配置文件,並添加以下內容:

repos:
- repo: https://github.com/psf/black
rev: 23.3.0 # 請確認使用最新的版本
hooks:
- id: black
language_version: python3.8 # 替換為你的 Python 版本

這個配置文件告訴 pre-commit 在提交前使用 Black 來格式化 Python 程式碼。

步驟三:初始化 pre-commit

在你的終端中運行以下命令,這會在你的 Git 專案中初始化 pre-commit:

pre-commit install

這個命令會在你的 Git 專案中設置 pre-commit hook。從現在開始,每次你進行 git commit 時,pre-commit 都會自動運行並使用 Black 格式化你的程式碼。

步驟四:測試你的設置

為了確保一切正常運行,你可以創建一個測試 Python 文件,並故意使用不一致的格式。然後嘗試提交這個文件:

git add test.py
git commit -m "Test pre-commit hook with Black"

如果一切正常,pre-commit 會在你提交之前自動格式化 test.py 文件。

額外提示

  • 更新 pre-commit 配置:當你需要更新 Black 或其他 pre-commit hook 時,可以修改 .pre-commit-config.yaml 文件,然後運行 pre-commit autoupdate 命令。
  • 跳過 pre-commit hook:如果有特殊情況需要跳過 pre-commit hook,可以在提交時使用 --no-verify 選項,例如 git commit --no-verify -m "Skipping hooks"

結論

透過使用 pre-commit hook 搭配 Black 套件,你可以確保在每次提交程式碼到 GitHub 之前,程式碼都已經過自動格式化。這不僅提高了程式碼的一致性,也能減少團隊協作中的合併衝突。按照以上步驟配置你的專案,讓你的開發流程更加順暢和高效。

pre-commit hook補充知識

Pre-commit hook 的運作方式是在你執行 git commit 命令時,先在提交(commit)之前自動執行特定的腳本(如格式化程式碼)。這些腳本在實際提交之前被執行,因此不會直接產生新的提交記錄,也不會單獨顯示在 git log 中。

以下是 pre-commit hook 的工作流程:

  1. 執行 git commit:當你執行 git commit 命令時,Git 會先觸發 pre-commit hook。
  2. 執行 hook 腳本:pre-commit 會運行配置好的腳本(例如,使用 Black 格式化程式碼)。
  3. 格式化程式碼:如果程式碼被 Black 格式化,pre-commit 會在本地修改這些文件。
  4. 取消提交:如果程式碼被修改,pre-commit 會取消當前的提交過程,並提示你程式碼已被修改。
  5. 重新添加變更並提交:你需要重新檢查被修改的文件,添加它們(git add),然後再次執行 git commit

具體流程範例

假設你有一個 example.py 文件,其內容需要被格式化:

  1. 執行 git commit
git add example.py 
git commit -m "Initial commit"

2. pre-commit 執行 Black:pre-commit 會運行 Black,並格式化 example.py 文件。

3. 取消提交並提示:pre-commit 會取消提交,並顯示一個提示,告訴你文件已被格式化。

black...........................................(no files to check) Skipped
- hook id: black
- exit code: 1

Files were modified by this hook.

4. 重新添加變更並提交

git add example.py
git commit -m "Initial commit"

這次提交會成功,因為文件已經被格式化。

注意事項

  • 提交記錄:由於 pre-commit 是在你提交之前運行的,它不會單獨產生提交記錄。因此,你的 Git 提交歷史中不會有來自 pre-commit hook 的單獨提交。
  • 多次提交嘗試:如果 pre-commit 修改了文件,你需要重新添加並再次提交,這樣你的提交記錄中就只會有一次提交,包含格式化後的程式碼。

總結

pre-commit hook 在你提交程式碼之前運行,確保程式碼符合設定的風格要求。當文件被格式化時,pre-commit 會取消當前的提交,你需要重新添加並提交格式化後的文件。這樣可以確保提交到 Git 的程式碼是一致且符合標準的,而不會額外產生新的提交記錄。

--

--