update-changelog-prepare.sh
3.59 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
#!/bin/bash
# ============================================
# CHANGELOG 自动更新脚本(Prepare-commit-msg 版本)
# ============================================
#
# 功能:在 prepare-commit-msg 阶段更新 CHANGELOG.md,加入暂存区
# 配合 post-commit 的 amend --no-verify 完成流程
#
# 作者:Claude Code
# 日期:2026-02-28
# ============================================
set -e
# 颜色定义
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
NC='\033[0m' # No Color
# 参数
COMMIT_MSG_FILE=$1
CHANGELOG_FILE="CHANGELOG.md"
# 检查文件是否存在
if [ ! -f "$CHANGELOG_FILE" ]; then
echo " ${YELLOW}⚠️ CHANGELOG.md 不存在,跳过自动更新${NC}"
exit 0
fi
# 读取 commit message
COMMIT_MSG=$(cat "$COMMIT_MSG_FILE")
# 解析 commit message
# 格式: type(scope): subject
if ! echo "$COMMIT_MSG" | grep -qE "^([a-z]+)\(([a-z-]+)\): .{1,50}"; then
# 格式不匹配,跳过
exit 0
fi
# 提取信息
COMMIT_TYPE=$(echo "$COMMIT_MSG" | head -n 1 | sed -E 's/^([a-z]+)\(.*/\1/')
COMMIT_SCOPE=$(echo "$COMMIT_MSG" | head -n 1 | sed -E 's/^[a-z]+\(([a-z-]+)\).*/\1/')
COMMIT_SUBJECT=$(echo "$COMMIT_MSG" | head -n 1 | sed -E 's/^[a-z]+\([a-z-]+\): (.*)$/\1/')
# 类型映射到中文
case "$COMMIT_TYPE" in
feat)
CHANGE_TYPE="新增"
;;
fix)
CHANGE_TYPE="修复"
;;
docs)
CHANGE_TYPE="文档"
;;
style)
CHANGE_TYPE="样式"
;;
refactor)
CHANGE_TYPE="优化"
;;
perf)
CHANGE_TYPE="性能"
;;
test)
CHANGE_TYPE="测试"
;;
chore)
CHANGE_TYPE="配置"
;;
revert)
CHANGE_TYPE="回滚"
;;
*)
CHANGE_TYPE="其他"
;;
esac
# 获取当前日期和时间
TODAY=$(date +%Y-%m-%d)
NOW_TIME=$(date +%H:%M:%S)
# 获取暂存的变更文件(使用 git diff --cached)
CHANGED_FILES=$(git diff --cached --name-only | tr '\n' '\n' | sed 's/^/- \`/;s/$/`/' | sed '$d')
if [ -z "$CHANGED_FILES" ]; then
CHANGED_FILES="- \`无\`"
fi
# 生成 CHANGELOG 条目
CHANGELOG_ENTRY="### $NOW_TIME - $COMMIT_TYPE($COMMIT_SCOPE): $COMMIT_SUBJECT
**影响文件**:
$CHANGED_FILES
**变更摘要**:
- $COMMIT_SUBJECT
---
"
# 检查今天是否已有条目
if grep -q "^## $TODAY" "$CHANGELOG_FILE"; then
# 今天已有条目,找到日期行号,在日期后追加
DATE_LINE=$(grep -n "^## $TODAY" "$CHANGELOG_FILE" | head -1 | cut -d: -f1)
# 创建临时文件
TEMP_FILE=$(mktemp)
# 读取日期行之前的内容
head -n $DATE_LINE "$CHANGELOG_FILE" > "$TEMP_FILE"
# 在日期后追加新条目
echo "$CHANGELOG_ENTRY" >> "$TEMP_FILE"
# 追加日期行之后的内容(从日期行+1开始)
tail -n +$((DATE_LINE + 1)) "$CHANGELOG_FILE" >> "$TEMP_FILE"
# 替换原文件
mv "$TEMP_FILE" "$CHANGELOG_FILE"
else
# 今天没有条目,创建新的日期部分
TEMP_FILE=$(mktemp)
# 新建日期标题和条目
echo "## $TODAY" > "$TEMP_FILE"
echo "" >> "$TEMP_FILE"
echo "$CHANGELOG_ENTRY" >> "$TEMP_FILE"
echo "" >> "$TEMP_FILE"
# 追加原文件内容
cat "$CHANGELOG_FILE" >> "$TEMP_FILE"
# 替换原文件
mv "$TEMP_FILE" "$CHANGELOG_FILE"
fi
# 将 CHANGELOG.md 加入暂存区
# 重要:这里只是加入暂存区,实际包含在提交中由 post-commit 的 amend 完成
git add "$CHANGELOG_FILE"
echo " ${GREEN}✅ CHANGELOG.md 已自动更新${NC}"
echo " ${BLUE} 类型: $CHANGE_TYPE${NC}"
echo " ${BLUE} 范围: $COMMIT_SCOPE${NC}"
echo " ${BLUE} 描述: $COMMIT_SUBJECT${NC}"