如何对Pull Request合并提交的消息进行commitlint校验?
解决方案:校验Pull Request合并提交消息并阻止不合规合并
要实现对合并提交消息的校验并阻止不合规合并,你需要调整工作流的触发时机,同时通过GitHub API获取合并提交消息,再用commitlint进行校验。以下是具体实现方案:
调整后的工作流配置
on: pull_request: types: [opened, synchronize, edited, ready_for_review] merge_group: jobs: lint-commits: runs-on: ubuntu-latest steps: - uses: actions/checkout@v3 with: fetch-depth: 0 - uses: actions/setup-node@v3 with: node-version: 16 - run: npm install -g @commitlint/{cli,config-conventional} # 保留原有PR提交消息校验逻辑 - name: Lint PR commits run: commitlint --from ${{ github.event.pull_request.base.sha }} --to ${{ github.event.pull_request.head.sha }} --verbose # 获取合并提交消息 - name: Fetch merge commit message id: get-merge-msg uses: actions/github-script@v6 with: script: | let mergeMessage = ''; if (context.eventName === 'pull_request') { const pr = await github.rest.pulls.get({ owner: context.repo.owner, repo: context.repo.repo, pull_number: context.payload.pull_request.number }); // 若用户未自定义合并消息,使用PR标题+编号作为默认值校验 mergeMessage = pr.data.merge_commit_message || `${pr.data.title} (#${pr.data.number})`; } else if (context.eventName === 'merge_group') { const mergeGroup = await github.rest.repos.getMergeGroup({ owner: context.repo.owner, repo: context.repo.repo, merge_group_id: context.payload.merge_group.id }); mergeMessage = mergeGroup.data.head_commit.message; } core.setOutput('message', mergeMessage); # 校验合并提交消息 - name: Lint merge commit message run: commitlint --msg "${{ steps.get-merge-msg.outputs.message }}"
关键说明
触发时机调整
- 添加
pull_request的edited类型:当用户在浏览器修改合并提交消息时立即触发校验 - 添加
merge_group事件:适用于使用GitHub合并队列的场景,确保进入队列的合并消息合规 - 保留原有触发类型:覆盖PR创建、同步、标记为可审核等场景,确保默认合并消息也被校验
- 添加
合并消息获取逻辑
- 通过GitHub API直接获取PR的合并提交消息(含用户自定义内容或默认值)
- 针对合并队列场景,获取合并组的头部提交消息进行校验
强制校验生效
在仓库的分支保护规则中,将这个lint-commits工作流设置为必需状态检查,这样只有工作流通过时,才能执行合并操作。
替代思路(可选)
如果不想依赖GitHub API,也可以通过模拟本地合并生成合并提交消息:
# 模拟合并base分支和head分支,生成合并提交消息 git checkout ${{ github.event.pull_request.base.sha }} git merge --no-commit --no-ff ${{ github.event.pull_request.head.sha }} # 获取默认合并消息 MERGE_MESSAGE=$(git log --format=%B -1 HEAD) # 校验消息 commitlint --msg "$MERGE_MESSAGE"
这种方法的缺点是如果PR存在冲突,模拟合并会失败,因此推荐使用API获取消息的方案。
内容的提问来源于stack exchange,提问作者marlondecol
相关产品推荐
相关产品推荐

