prepare-commit-msg 2.04 KB
#!/bin/sh
# ============================================
# Prepare-commit-msg Hook
# ============================================
#
# 功能:
# 1. 自动更新 CHANGELOG.md(包含在当前提交中)
#
# 关键特性:
# - 只在初始提交时执行,amend 时不会触发
# - 配合 post-commit 使用 amend --no-verify 完成流程
#
# 作者:Claude Code
# 日期:2026-02-28
# ============================================

# 颜色定义
RED='\033[0;31m'
GREEN='\033[0;32m'
BLUE='\033[0;34m'
YELLOW='\033[1;33m'
NC='\033[0m' # No Color

# 获取 commit message 文件
COMMIT_MSG_FILE=$1
COMMIT_SOURCE=$2  # commit 来源:message/template/merge/squash等

# 只在正常的 commit 时执行,跳过 merge/rebase/amend
# amend 时 COMMIT_SOURCE 为空
if [ "$COMMIT_SOURCE" = "message" ] || [ "$COMMIT_SOURCE" = "template" ] || [ "$COMMIT_SOURCE" = "" ]; then
  # 检查是否是 amend 操作(通过检查是否已有 commit)
  # 如果 HEAD 存在且不是初始提交,可能是 amend
  if git rev-parse HEAD >/dev/null 2>&1; then
    # 有 HEAD,检查是否是正在 amend
    # 简单的判断:如果已经有 commit 且当前没有在 rebase 等操作中
    # 这里我们允许继续,因为关键在于 post-commit 的 --no-verify
    :
  fi

  # 读取 commit message
  if [ -f "$COMMIT_MSG_FILE" ]; then
    COMMIT_MSG=$(cat "$COMMIT_MSG_FILE")

    # 只处理第一行(subject)
    FIRST_LINE=$(echo "$COMMIT_MSG" | head -n 1)

    # 解析 commit type
    COMMIT_TYPE=$(echo "$FIRST_LINE" | sed -E 's/^([a-z]+)\(.*/\1/')

    # 只对特定类型更新 CHANGELOG
    # 跳过: docs(changelog) 类型的提交,避免循环
    if echo "$FIRST_LINE" | grep -qE "^docs\(changelog\):"; then
      # 跳过
      :
    elif [ "$COMMIT_TYPE" = "feat" ] || [ "$COMMIT_TYPE" = "fix" ] || [ "$COMMIT_TYPE" = "refactor" ] || [ "$COMMIT_TYPE" = "perf" ]; then
      echo ""
      echo "📝 ${BLUE}更新 CHANGELOG...${NC}"

      # 调用 CHANGELOG 更新脚本
      bash scripts/changelog/update-changelog-prepare.sh "$COMMIT_MSG_FILE"
    fi
  fi
fi