各位靓仔靓女们,晚上好!我是你们的老朋友,今晚咱们来聊聊 JavaScript
界的“二哈”—— Husky
。
别误会,此“二哈”非彼“二哈”,它可不是那种拆家捣蛋的宠物,而是 Git Hook
的好帮手,能让你的代码提交变得更加规范和可靠。简单来说,它就像一个尽职尽责的门卫,帮你把控代码质量的最后一道关卡。
一、Husky
是个啥?为什么要用它?
首先,我们得明白 Git Hook
是什么。Git Hook
就像 Git 的钩子函数,在特定的 Git 事件发生时(例如 commit
、push
等),会自动触发你预先设定的脚本。
但是,手动配置和管理 Git Hook
非常麻烦,容易出错,而且需要对每个开发者都进行设置。这时候,Husky
就闪亮登场了。
Husky
就像一个 Git Hook
管理器,它能:
- 简化
Git Hook
的配置: 用简单的npm
命令就能安装和配置,无需手动修改.git/hooks
目录。 - 项目级别配置:
Husky
的配置保存在package.json
文件中,跟随项目一起版本控制,保证团队成员使用相同的Hook
设置。 - 支持各种脚本语言: 你可以使用
JavaScript
、Shell
、Python
等任何你喜欢的脚本语言来编写Hook
脚本。 - 提高代码质量: 通过
Hook
脚本,你可以自动化地执行代码检查、单元测试、代码格式化等操作,从而避免低级错误和风格不一致的代码被提交。
举个例子,你可能希望在每次提交代码前,都自动运行 ESLint
来检查代码风格,或者运行 Jest
来进行单元测试。有了 Husky
,这些都能轻松实现。
二、如何安装和配置 Husky
?
-
安装
Husky
:首先,确保你的项目已经初始化了
npm
或yarn
。 然后,在你的项目根目录下运行以下命令:npm install husky --save-dev # 或者 yarn add husky --dev
-
启用
Git Hook
:安装完成后,你需要启用
Git Hook
。运行以下命令:npx husky install # 或者 yarn husky install
这会在你的项目根目录下创建一个
.husky
文件夹,用于存放Hook
脚本。 -
添加
Hook
脚本:现在,你可以添加你想要的
Hook
脚本了。Husky
支持的Hook
类型有很多,常用的包括:pre-commit
:在commit
之前运行。commit-msg
:在commit
消息编辑后运行。pre-push
:在push
之前运行。prepare-commit-msg
: 在commit
message 准备阶段运行
例如,如果你想在每次
commit
之前运行ESLint
检查代码风格,可以这样做:npx husky add .husky/pre-commit "npm run lint" # 或者 yarn husky add .husky/pre-commit "yarn lint"
这个命令会在
.husky/pre-commit
文件中创建一个脚本,内容是npm run lint
或yarn lint
。 假设你的package.json
文件中有如下配置:{ "scripts": { "lint": "eslint . --ext .js,.jsx,.ts,.tsx" } }
那么,每次你运行
git commit
命令时,Husky
都会自动执行eslint . --ext .js,.jsx,.ts,.tsx
命令来检查你的代码风格。 如果ESLint
发现了任何错误,commit
就会被阻止,直到你修复了错误为止。 -
简化配置方式(
Husky v6+
):Husky v6
引入了一种更简洁的配置方式,直接在package.json
文件中配置Hook
。 首先,在package.json
中添加husky
配置:{ "husky": { "hooks": { "pre-commit": "lint-staged" } }, "scripts": { "lint": "eslint . --ext .js,.jsx,.ts,.tsx", "format": "prettier --write ." }, "devDependencies": { "husky": "^6.0.0", "lint-staged": "^10.0.0", "eslint": "^7.0.0", "prettier": "^2.0.0" } }
然后,运行
npm install
或yarn install
安装依赖。这种方式更加清晰明了,方便管理和维护。
三、Husky
+ lint-staged
:黄金搭档
通常,我们不会对所有文件都进行代码检查和格式化,而是只关注那些被修改的文件。 这时候,lint-staged
就派上用场了。
lint-staged
是一个只对 Git
暂存区(stage
)中的文件执行 lint
命令的工具。 它可以显著提高 lint
的速度,避免对未修改的文件进行不必要的检查。
-
安装
lint-staged
:npm install lint-staged --save-dev # 或者 yarn add lint-staged --dev
-
配置
lint-staged
:在
package.json
文件中添加lint-staged
配置:{ "lint-staged": { "*.{js,jsx,ts,tsx}": [ "eslint --fix", "prettier --write", "git add" ] } }
这个配置表示,对所有
.js
、.jsx
、.ts
、.tsx
文件,先运行eslint --fix
来自动修复代码风格问题,然后运行prettier --write
来格式化代码,最后运行git add
将修改后的文件重新添加到暂存区。 -
将
lint-staged
集成到Husky
中:修改
husky
配置,将pre-commit
钩子指向lint-staged
:{ "husky": { "hooks": { "pre-commit": "lint-staged" } } }
现在,每次你运行
git commit
命令时,Husky
都会自动执行lint-staged
,只对暂存区中的文件进行代码检查和格式化。
四、一些进阶用法和注意事项
-
跳过
Hook
:有时候,你可能需要临时跳过
Hook
,例如当你需要提交一些未完成的代码时。 你可以使用git commit --no-verify
或git push --no-verify
命令来跳过Hook
。 -
自定义
Hook
脚本:你可以编写自己的
Hook
脚本来实现更复杂的功能。 例如,你可以编写一个Hook
脚本来检查commit
消息的格式,或者检查代码中是否包含敏感信息。举个例子,我们可以编写一个
commit-msg
钩子来检查commit
消息是否符合规范:#!/bin/sh COMMIT_MSG_FILE=$1 COMMIT_MSG=$(cat $COMMIT_MSG_FILE) # 检查 commit 消息是否以 "feat:", "fix:", "docs:", "style:", "refactor:", "test:", "chore:" 开头 if ! echo "$COMMIT_MSG" | grep -E "^(feat|fix|docs|style|refactor|test|chore)(([a-z]+))?:s.+"; then echo "Error: Commit message must start with feat:, fix:, docs:, style:, refactor:, test:, or chore: followed by a description." exit 1 fi exit 0
然后,将这个脚本添加到
.husky/commit-msg
文件中,并赋予执行权限:chmod +x .husky/commit-msg
现在,每次你提交代码时,
Husky
都会自动运行这个脚本来检查commit
消息的格式。 -
处理
Hook
失败:默认情况下,如果
Hook
脚本执行失败,commit
或push
操作会被阻止。 你可以使用husky.allowEmpty
配置来允许空的commit
,即使Hook
失败。{ "husky": { "hooks": { "pre-commit": "lint-staged", "commit-msg": "your-commit-msg-script" }, "allowEmpty": true } }
但通常不推荐这样做,因为这会降低代码质量的保证。
-
与 CI/CD 集成:
Husky
也可以与 CI/CD 工具集成,例如 Jenkins、Travis CI、GitHub Actions 等。 这样,你可以在每次构建或部署时,都自动运行Hook
脚本来检查代码质量。
五、一个完整的例子
假设我们有一个 React
项目,使用 ESLint
、Prettier
和 Jest
来进行代码检查、格式化和单元测试。 我们可以这样配置 Husky
:
-
安装依赖:
npm install husky lint-staged eslint prettier jest --save-dev # 或者 yarn add husky lint-staged eslint prettier jest --dev
-
配置
package.json
:{ "scripts": { "lint": "eslint . --ext .js,.jsx,.ts,.tsx", "format": "prettier --write .", "test": "jest", "prepare": "husky install" }, "husky": { "hooks": { "pre-commit": "lint-staged" } }, "lint-staged": { "*.{js,jsx,ts,tsx}": [ "eslint --fix", "prettier --write", "jest --findRelatedTests", "git add" ] }, "devDependencies": { "eslint": "^7.0.0", "prettier": "^2.0.0", "jest": "^26.0.0", "husky": "^6.0.0", "lint-staged": "^10.0.0" } }
注意:
prepare
脚本会在npm install
或yarn install
之后自动运行husky install
,这样可以确保在安装依赖后,Husky
能够正确地启用Git Hook
。 -
初始化
ESLint
和Prettier
:运行以下命令来初始化
ESLint
和Prettier
:npx eslint --init npx prettier --write .
根据提示选择合适的配置。
-
编写单元测试:
编写一些单元测试来测试你的代码。
现在,每次你运行 git commit
命令时,Husky
都会自动执行以下操作:
- 只对暂存区中的
.js
、.jsx
、.ts
、.tsx
文件进行代码检查和格式化。 - 运行
Jest
来测试与这些文件相关的单元测试。 - 如果一切顺利,
commit
就会成功。 否则,commit
会被阻止,直到你修复了错误为止。
六、Husky
的优点和缺点
优点 | 缺点 |
---|---|
提高代码质量 | 如果 Hook 脚本执行时间过长,会影响开发效率。 |
自动化代码检查和格式化 | 需要配置和维护 Hook 脚本。 |
强制团队成员遵循相同的代码风格 | 有些开发者可能不喜欢强制性的代码检查和格式化。 |
简化 Git Hook 的配置和管理 |
如果 Hook 脚本编写不当,可能会导致意外的错误。 |
可以与 CI/CD 工具集成,实现自动化代码质量控制 | 在某些情况下,Husky 可能会与其他的 Git Hook 工具冲突。 |
七、总结
Husky
是一个非常实用的 Git Hook
管理工具,可以帮助你提高代码质量、自动化代码检查和格式化,并强制团队成员遵循相同的代码风格。 配合 lint-staged
使用,可以显著提高 lint
的速度。
虽然 Husky
也有一些缺点,但总体来说,它的优点远大于缺点。 如果你还没有使用 Husky
,强烈建议你尝试一下,相信它会给你的开发工作带来很大的帮助。
好了,今天的讲座就到这里。 希望大家都能成为代码界的“猛男”和“靓女”,写出高质量的代码! 感谢大家的聆听! 记得点赞收藏加关注哦! 下次再见!