前端程式碼規範與工程化實戰:ESLint + Prettier + Husky 全流程搭建
前端工程
為什麼你的團隊需要程式碼規範工程化
說兩個真實場景。
場景一:同事 A 用 2 空格縮排,同事 B 用 4 空格。每次 Code Review,80% 的 diff 是縮排和換行。評審人精力消耗在格式上,邏輯問題反而被忽略。
場景二:一個實習生提交了一段程式碼,npm run build 通過了,合併到主分支。第二天生產環境報錯:「typo in variable name」。如果有自動化檢查,這個提交根本過不了 pre-commit hook。
程式碼規範不是「條條框框約束人」,而是「用工具自動保證底線,讓人把精力放在真正有價值的決策上」。這篇文章基於我在三個團隊的實踐。
快速預覽:搭建完後的效果
git add .
git commit -m "feat: add user login"
# Husky 自動觸發 pre-commit hook
# → lint-staged 對暫存檔案執行 ESLint --fix + Prettier --write
# → commitlint 校驗 commit message 格式
# → 全部通過後才真正提交
ESLint Flat Config:告別 .eslintrc
2024 年底 ESLint 9.x 將 Flat Config 設為預設,舊的 .eslintrc.* 進入棄用週期。
Flat Config 基礎結構
// eslint.config.mjs
import js from '@eslint/js';
import tseslint from 'typescript-eslint';
import globals from 'globals';
export default tseslint.config(
js.configs.recommended,
...tseslint.configs.recommended,
{
languageOptions: {
globals: {
...globals.browser,
...globals.node,
},
parserOptions: {
project: './tsconfig.json',
},
},
},
{
rules: {
'@typescript-eslint/no-unused-vars': ['error', {
argsIgnorePattern: '^_',
varsIgnorePattern: '^_',
}],
'@typescript-eslint/no-explicit-any': 'warn',
'no-console': ['warn', { allow: ['warn', 'error'] }],
'prefer-const': 'error',
'no-var': 'error',
'eqeqeq': ['error', 'always'],
},
},
{
ignores: [
'dist/**',
'node_modules/**',
'.next/**',
'coverage/**',
],
}
);
為什麼遷移到 Flat Config
| 舊格式 (eslintrc) | 新格式 (Flat Config) | 說明 |
|---|---|---|
.eslintrc.js / .eslintrc.json |
eslint.config.mjs |
統一為單個檔案 |
extends 鏈式繼承 |
tseslint.config() 組合 |
函式組合替代繼承 |
overrides + 檔案匹配 |
配置物件中的 files |
更直觀的覆蓋規則 |
| 外掛用字串名稱 | import pluginX from '...' |
ESM 原生 import |
Prettier:格式化交給專業工具
// .prettierrc
{
"semi": true,
"singleQuote": true,
"trailingComma": "all",
"printWidth": 100,
"tabWidth": 2,
"arrowParens": "always",
"endOfLine": "lf",
"bracketSpacing": true
}
讓 ESLint 和 Prettier 和平共處:
// eslint.config.mjs
import prettier from 'eslint-config-prettier';
export default tseslint.config(
// ...前面的配置
prettier, // 放最後,確保覆蓋所有衝突規則
);
Husky + lint-staged:在提交前攔住問題
npm i -D husky lint-staged
npx husky init
// package.json
{
"lint-staged": {
"*.{ts,tsx,js,jsx}": [
"eslint --fix --max-warnings=0",
"prettier --write"
],
"*.{json,css,scss,md}": [
"prettier --write"
]
}
}
# .husky/pre-commit
npx lint-staged
commitlint:統一提交資訊格式
npm i -D @commitlint/cli @commitlint/config-conventional
// commitlint.config.mjs
export default {
extends: ['@commitlint/config-conventional'],
rules: {
'type-enum': [
2,
'always',
[
'feat', 'fix', 'docs', 'style',
'refactor', 'perf', 'test', 'chore',
'ci', 'revert',
],
],
'subject-case': [0],
},
};
正確的提交格式:
git commit -m "feat: add user authentication module"
git commit -m "fix: resolve token refresh race condition"
CI 流水線整合
# .github/workflows/lint.yml
name: Lint & Format Check
on:
pull_request:
branches: [main, develop]
jobs:
lint:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: 20
- name: Install dependencies
run: npm ci
- name: Run ESLint
run: npx eslint . --max-warnings=0
- name: Check formatting
run: npx prettier --check "src/**/*.{ts,tsx,js,jsx,json,css}"
- name: Type check
run: npx tsc --noEmit
遷移真實專案的經驗
第一步:先格式,後規則
# 1. 先用 Prettier 格式化整個專案
npx prettier --write "src/**/*.{ts,tsx}"
# 2. 提交格式化變更
git add .
git commit -m "style: format all files with Prettier"
# 3. 逐步開啟 ESLint 規則
第二步:漸進式收緊
// 第一期:只開 error 級別
{
rules: {
'@typescript-eslint/no-explicit-any': 'warn',
'no-console': 'off',
'@typescript-eslint/no-unused-vars': 'error',
},
}
常見坑與解決
坑 1:ESLint Flat Config 和 VSCode 外掛不相容
{
"eslint.useFlatConfig": true,
"eslint.options": {
"overrideConfigFile": "eslint.config.mjs"
}
}
坑 2:Windows 和 macOS 換行符打架
.prettierrc 中設 "endOfLine": "lf",再加 .gitattributes:
* text=auto eol=lf
相關工具
- JSON 格式化 — 校驗和格式化配置檔案
- 文字差異對比 — 對比格式化前後的程式碼差異
- Base64 編碼解碼 — 處理構建產物分析與對比
本站提供瀏覽器本地工具,免註冊即可試用 →
#ESLint#Prettier#代码规范#工程化#前端#教程