From cc59bc9c6a0380573645e3cd49ed4f35bedb8e34 Mon Sep 17 00:00:00 2001 From: MarTrepodi Date: Thu, 22 Oct 2026 12:15:32 -0400 Subject: [PATCH] ci(ci): skip commits already on develop when linting release PRs A release PR into main carries every develop commit, and Commit Lint re-checked all of them. Dependabot's "Bump ..." subjects fail subject-case and are only exempt on PRs Dependabot opened, so the v2.6.0 release PR failed the required check on eight commits that had already passed it on their way into develop. On PRs into main, also exclude commits reachable from develop, which requires the same check. PRs into develop lint exactly as before. The fetch now names its refspecs with "+" so it updates refs that actions/checkout already created instead of relying on FETCH_HEAD. Co-Authored-By: Claude Opus 5.5 --- .github/workflows/commitlint.yml | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/.github/workflows/commitlint.yml b/.github/workflows/commitlint.yml index b3fead6..5b095b6 100644 --- a/.github/workflows/commitlint.yml +++ b/.github/workflows/commitlint.yml @@ -32,7 +32,8 @@ jobs: - name: Validate commits run: | set -euo pipefail - git fetch --no-tags --quiet origin main + git fetch --no-tags --quiet origin \ + +main:refs/remotes/origin/main +develop:refs/remotes/origin/develop base="${{ github.event.pull_request.base.sha }}" head="${{ github.event.pull_request.head.sha }}" # Lint only the commits this PR actually introduces: exclude merge @@ -40,7 +41,15 @@ jobs: # automated back-merge PRs re-introduce main's (sometimes # non-conventional squash) commits — those are already on main and are # not this PR's responsibility to police. - commits="$(git rev-list --no-merges --reverse "${base}..${head}" --not FETCH_HEAD)" + landed=(origin/main) + # A release PR into main carries every develop commit, and each one was + # already linted (or exempted, as Dependabot's are below) by the PR that + # landed it on develop. Without this, a release re-lints Dependabot's + # "Bump ..." subjects outside a Dependabot PR and fails subject-case. + if [ "${{ github.event.pull_request.base.ref }}" = "main" ]; then + landed+=(origin/develop) + fi + commits="$(git rev-list --no-merges --reverse "${base}..${head}" --not "${landed[@]}")" # Dependabot copies its subject casing from repo history rather than from # dependabot.yml, so its "chore(deps): Bump ..." can fail subject-case. Its own # commits are machine-generated and never reach the changelog, so skip them — @@ -49,7 +58,7 @@ jobs: if [ "${{ github.event.pull_request.user.login }}" = "dependabot[bot]" ]; then bot="49699333+dependabot[bot]@users.noreply.github.com" commits="$(git rev-list --no-merges --reverse --no-commit-header --format='%H %ae' \ - "${base}..${head}" --not FETCH_HEAD | awk -v bot="${bot}" '$2 != bot { print $1 }')" + "${base}..${head}" --not "${landed[@]}" | awk -v bot="${bot}" '$2 != bot { print $1 }')" echo "Dependabot PR: skipping commits authored by ${bot}." fi if [ -z "${commits}" ]; then