本文目录导读:

- 代码质量检查(pre-commit)
- 性能与改进检测(pre-push)
- 测试覆盖率检查(post-checkout/commit)
- 安全与规范检查(pre-receive - 服务端)
- 智能改进建议(commit-msg)
- 部署改进监控(post-receive)
- 最佳实践集成脚本
- 使用建议
Git 钩子脚本可以通过检查代码质量、运行测试和验证规范来推动持续改进,以下是几种常见场景的实现方法和示例脚本:
代码质量检查(pre-commit)
#!/bin/bash
# .git/hooks/pre-commit
echo "🔍 运行代码质量检查..."
# 设置错误标志
ERROR=0
# 1. 检查暂存区中的修改文件
STAGED_FILES=$(git diff --cached --name-only --diff-filter=ACM)
# 2. 对不同的文件类型运行不同的检查
for FILE in $STAGED_FILES; do
if [[ $FILE == *.py ]]; then
# Python文件检查
if ! flake8 "$FILE" 2>/dev/null; then
echo "❌ Python语法/风格问题: $FILE"
ERROR=1
fi
if ! pylint "$FILE" --exit-zero 2>/dev/null; then
echo "⚠️ Python代码改进建议: $FILE"
fi
elif [[ $FILE == *.js || $FILE == *.ts ]]; then
# JavaScript/TypeScript检查
if ! eslint "$FILE" --quiet 2>/dev/null; then
echo "❌ JavaScript问题: $FILE"
ERROR=1
fi
elif [[ $FILE == *.md ]]; then
# Markdown检查
if ! markdownlint "$FILE" 2>/dev/null; then
echo "⚠️ Markdown格式可以改进: $FILE"
fi
fi
# 检查文件大小是否合理
SIZE=$(wc -c < "$FILE")
if [ $SIZE -gt 100000 ]; then
echo "⚠️ 文件过大 (>100KB): $FILE (${SIZE}字节)"
echo "建议拆分或优化"
fi
done
# 3. 检查是否包含调试代码
if grep -r "console.log\|debugger\|TODO\|FIXME\|HACK" --include="*.js" --include="*.py" . 2>/dev/null; then
echo "⚠️ 发现调试代码或待办事项"
ERROR=1
fi
if [ $ERROR -ne 0 ]; then
echo "❌ 提交被阻止,请修复上述问题"
exit 1
fi
echo "✅ 代码质量检查通过"
性能与改进检测(pre-push)
#!/bin/bash
# .git/hooks/pre-push
echo "📊 运行性能与持续改进检查..."
# 获取将要推送的分支信息
while read local_ref local_sha remote_ref remote_sha; do
if [ "$local_sha" = "0000000000000000000000000000000000000000" ]; then
echo "删除分支,跳过检查"
continue
fi
# 获取变更文件
CHANGED_FILES=$(git diff --name-only "$remote_sha".."$local_sha")
# 1. 检查重复代码(使用jscpd或其他工具)
if command -v jscpd &> /dev/null; then
DUPLICATES=$(jscpd --min-lines 5 --min-tokens 50 "$CHANGED_FILES" 2>/dev/null)
if [ -n "$DUPLICATES" ]; then
echo "❌ 发现重复代码:"
echo "$DUPLICATES"
exit 1
fi
fi
# 2. 检查复杂度过高
for FILE in $CHANGED_FILES; do
if [[ $FILE == *.py ]]; then
COMPLEXITY=$(radon cc "$FILE" -s 2>/dev/null | grep -oP '\([0-9]+\)' | grep -oP '[0-9]+')
if [ -n "$COMPLEXITY" ] && [ "$COMPLEXITY" -gt 15 ]; then
echo "⚠️ 代码复杂度高 ($COMPLEXITY): $FILE"
echo "建议重构以提高可维护性"
fi
fi
done
done
echo "✅ 性能检查通过"
exit 0
测试覆盖率检查(post-checkout/commit)
#!/bin/bash
# .git/hooks/post-commit
echo "📈 记录持续改进指标..."
# 获取当前分支名
BRANCH=$(git rev-parse --abbrev-ref HEAD)
# 记录提交统计
COMMIT_HASH=$(git rev-parse HEAD)
COMMIT_MESSAGE=$(git log -1 --pretty=%B)
DIFF_STATS=$(git diff --shortstat HEAD~1 HEAD 2>/dev/null)
# 计算代码变更指标
ADDED_LINES=$(echo "$DIFF_STATS" | grep -oP '\d+(?= insertion)' | head -1)
DELETED_LINES=$(echo "$DIFF_STATS" | grep -oP '\d+(?= deletion)' | head -1)
# 记录到改进日志
LOG_FILE=".git/improvement-log.json"
if [ ! -f "$LOG_FILE" ]; then
echo "[]" > "$LOG_FILE"
fi
# 更新改进日志
python3 -c "
import json, datetime
with open('$LOG_FILE', 'r') as f:
log = json.load(f)
log.append({
'timestamp': datetime.datetime.now().isoformat(),
'branch': '$BRANCH',
'hash': '$COMMIT_HASH',
'message': '''$COMMIT_MESSAGE''',
'added_lines': ${ADDED_LINES:-0},
'deleted_lines': ${DELETED_LINES:-0},
'net_change': $((${ADDED_LINES:-0} - ${DELETED_LINES:-0}))
})
with open('$LOG_FILE', 'w') as f:
json.dump(log, f, indent=2)
"
# 显示改进统计
echo "📊 本周改进统计:"
python3 -c "
import json
with open('$LOG_FILE', 'r') as f:
log = json.load(f)
total_added = sum([x['added_lines'] for x in log])
total_deleted = sum([x['deleted_lines'] for x in log])
print(f'新增代码行数: {total_added}')
print(f'删除代码行数: {total_deleted}')
print(f'净改进: {total_added - total_deleted}行')
"
安全与规范检查(pre-receive - 服务端)
#!/bin/bash
# .git/hooks/pre-receive (部署在远程仓库)
echo "🔒 服务端安全检查..."
while read oldrev newrev refname; do
# 跳过创建删除操作
if [ "$oldrev" = "0000000000000000000000000000000000000000" ] || \
[ "$newrev" = "0000000000000000000000000000000000000000" ]; then
continue
fi
# 获取变更文件
FILES=$(git diff --name-only "$oldrev".."$newrev")
# 1. 检查敏感信息
if echo "$FILES" | grep -E "\.env|password|secret|key|token" | grep -v "\.example" > /dev/null; then
echo "❌ 禁止提交包含敏感信息的文件!"
exit 1
fi
# 2. 检查二进制文件
for FILE in $FILES; do
if git show "$newrev:$FILE" | file - | grep -q "binary"; then
echo "❌ 禁止提交二进制文件: $FILE"
exit 1
fi
done
# 3. 检查许可证合规
if echo "$COMMIT_MESSAGE" | grep -qiE "\b(agpl|gpl|lgpl)\b"; then
echo "⚠️ 提交包含GPL许可证,请确认兼容性"
fi
done
echo "✅ 安全与规范检查通过"
exit 0
智能改进建议(commit-msg)
#!/bin/bash
# .git/hooks/commit-msg
echo "💡 提交信息改进建议..."
COMMIT_MSG_FILE="$1"
COMMIT_MSG=$(cat "$COMMIT_MSG_FILE")
# 1. 检查提交信息格式
if ! echo "$COMMIT_MSG" | grep -qE "^(feat|fix|docs|style|refactor|test|chore|perf|ci|build|revert)(\(.+\))?: .+"; then
echo "⚠️ 建议使用 Conventional Commits 格式:"
echo " feat: 新功能"
echo " fix: 修复Bug"
echo " docs: 文档更新"
echo " refactor: 重构"
echo " test: 测试相关"
echo " chore: 日常维护"
fi
# 2. 检查提交信息长度
HEADER_LENGTH=${#COMMIT_MSG}
if [ $HEADER_LENGTH -gt 72 ]; then
echo "⚠️ 提交信息超过72字符(当前${HEADER_LENGTH}字符)"
echo "建议缩短以提高可读性"
fi
# 3. 检查是否包含引用号
if echo "$COMMIT_MSG" | grep -qE "close|closes|closed|fix|fixes|fixed|resolve|resolves|resolved"; then
ISSUE_NUM=$(echo "$COMMIT_MSG" | grep -oP '#\d+')
if [ -n "$ISSUE_NUM" ]; then
echo "✅ 关联到问题: $ISSUE_NUM"
fi
fi
exit 0
部署改进监控(post-receive)
#!/bin/bash
# .git/hooks/post-receive
echo "🚀 部署后改进监控..."
while read oldrev newrev refname; do
# 记录部署事件
DEPLOY_LOG="/var/log/deploy-improvements.log"
echo "[$(date)] 部署更新:$refname" >> "$DEPLOY_LOG"
# 触发CI/CD检查
curl -X POST "https://ci.example.com/api/trigger" \
-H "Authorization: Bearer $CI_TOKEN" \
-d "branch=${refname##refs/heads/}&commit=$newrev"
# 记录性能指标
if [ -f "package.json" ]; then
npm test -- --coverage 2>/dev/null || true
fi
# 部署后健康检查
sleep 10
if curl -f "https://app.example.com/health"; then
echo "✅ 应用健康检查通过"
else
echo "⚠️ 应用健康检查失败,可能需要回滚"
# 可以在这里添加自动回滚逻辑
fi
done
echo "✅ 部署监控启动"
最佳实践集成脚本
创建一个统一的改进检查脚本:
#!/bin/bash
# .git/hooks/ci-improvement.sh
set -e
echo "🔄 运行持续改进检查..."
# 配置
MAX_COMPLEXITY=10
MAX_FILE_SIZE=100000 # 字节
MIN_COVERAGE=80 # 百分比
REQUIRED_FILES=("README.md" ".gitignore" "package.json")
# 1. 代码风格改进
improve_style() {
echo "1. 检查代码风格..."
if command -v prettier &> /dev/null; then
npx prettier --check "src/**/*.{js,ts,json,css}" 2>/dev/null
fi
if command -v black &> /dev/null; then
black --check --diff "**/*.py" 2>/dev/null
fi
}
# 2. 技术债务追踪
track_debt() {
echo "2. 追踪技术债务..."
# 查找TODO注释
TODO_COUNT=$(grep -r "TODO\|FIXME\|HACK\|XXX" --include="*.py" --include="*.js" . | wc -l)
echo " 当前待办事项: $TODO_COUNT"
# 记录到债务日志
echo "{\"date\":\"$(date +%Y-%m-%d)\",\"todos\":$TODO_COUNT}" >> .tech-debt.json
}
# 3. 依赖更新建议
check_dependencies() {
echo "3. 检查依赖更新..."
if [ -f "package.json" ]; then
OUTDATED=$(npm outdated --json 2>/dev/null || echo "{}")
if [ "$OUTDATED" != "{}" ]; then
echo " 发现过时的依赖包:"
echo "$OUTDATED" | python3 -c "
import json, sys
data = json.load(sys.stdin)
for pkg, info in data.get('package.json', data).items():
print(f' - {pkg}: {info[\"current\"]} -> {info[\"wanted\"]}')
"
fi
fi
}
# 4. 生成改进报告
generate_report() {
echo "4. 生成改进报告..."
REPORT_FILE=".improvement-report-$(date +%Y%m%d).md"
cat > "$REPORT_FILE" << EOF
# 持续改进报告
日期: $(date)
## 检查结果
### 代码质量
- 风格检查: ✅
- 复杂度检查: ✅
- 重复代码检查: ✅
### 测试覆盖
- 当前覆盖率: 需要运行测试获取
- 目标覆盖率: ${MIN_COVERAGE}%
### 技术债务
- TODO/FIXME数量: $(grep -r "TODO\|FIXME" --include="*.py" --include="*.js" . | wc -l)
- 待重构代码: 待分析
### 建议
1. 请定期更新依赖包
2. 考虑重构复杂度高的函数
3. 补充必要的文档和测试
EOF
echo "报告已生成: $REPORT_FILE"
}
# 主流程
improve_style
track_debt
check_dependencies
generate_report
echo "✅ 持续改进检查完成"
使用建议
-
启用hooks:
chmod +x .git/hooks/* git config core.hooksPath .git/hooks
-
配置改进阈值:
# 创建配置文件 cat > .githooks-config.json << EOF { "max_complexity": 10, "min_coverage": 80, "block_on_warnings": false, "enabled_checks": ["style", "security", "complexity"] } EOF -
集成到CI/CD:
# .gitlab-ci.yml improvement_check: script: - .git/hooks/ci-improvement.sh artifacts: paths: - .improvement-report-*.md
这些钩子脚本可以帮助团队:
- 自动发现代码质量问题
- 跟踪技术债务
- 推动持续改进
- 建立代码规范
- 提高代码质量
记得根据团队具体需求调整脚本,避免过于严格的检查影响开发效率。