From 1fc74e0bd29c45205e36dccf5a27b8140c70660f Mon Sep 17 00:00:00 2001 From: Arthurk12 Date: Thu, 15 Oct 2026 14:06:20 -0300 Subject: [PATCH] ci: bump manifest version and changelogs when cutting a tag The "Cut a new tag" workflow only bumps package.json and package-lock.json, so manifest.json carries no version and the plugin changelogs must be updated by hand, drifting from the tag. Set manifest.json's "version" (creating the field when missing) to the bumped version, and prepend an entry built from the commit subjects since the previous tag to CHANGELOG.md and debian/changelog when the plugin has them. Hand-written entries for the new version are kept untouched. Bump, manifest and changelogs land in a single commit, tagged as before. --- .github/workflows/publish-tag.yml | 112 ++++++++++++++++++++++++++++-- 1 file changed, 107 insertions(+), 5 deletions(-) diff --git a/.github/workflows/publish-tag.yml b/.github/workflows/publish-tag.yml index 4bf1b0d..912953b 100644 --- a/.github/workflows/publish-tag.yml +++ b/.github/workflows/publish-tag.yml @@ -1,4 +1,4 @@ -name: Cut a new tag (also auto updates package.json and package-lock.json) +name: Cut a new tag (also auto updates package.json, package-lock.json, manifest.json and changelogs) on: workflow_dispatch: @@ -11,10 +11,15 @@ on: jobs: bump-version: runs-on: ubuntu-latest + permissions: + contents: write steps: - name: Checkout repository uses: actions/checkout@v3 + with: + # Full history and tags are needed to list the commits since the last release + fetch-depth: 0 - name: Set up Node.js uses: actions/setup-node@v3 @@ -28,17 +33,114 @@ jobs: user_email="github-actions@github.com" fi echo "user_email=$user_email" >> $GITHUB_ENV - + - name: Configure Git with the triggering user's info run: | git config user.name "${{ github.actor }}" git config user.email "${{ github.actor_id }}+${{ github.actor }}@users.noreply.github.com" - - - name: Bump version and push tag + - name: Bump version in package.json and package-lock.json run: | + set -euo pipefail + npm install - npm version ${{ github.event.inputs.release_type }} -m "chore: bump version to %s" + npm version ${{ github.event.inputs.release_type }} --no-git-tag-version + + NEW_VERSION=$(node -p "require('./package.json').version") + PREVIOUS_TAG=$(git describe --tags --abbrev=0 2>/dev/null || true) + echo "New version is: $NEW_VERSION (previous tag: ${PREVIOUS_TAG:-none})" + + echo "NEW_VERSION=$NEW_VERSION" >> $GITHUB_ENV + echo "PREVIOUS_TAG=$PREVIOUS_TAG" >> $GITHUB_ENV + + - name: Set version in manifest.json + run: | + set -euo pipefail + + jq --arg v "$NEW_VERSION" '.version = $v' manifest.json > manifest.json.tmp + mv manifest.json.tmp manifest.json + + - name: Collect changes since the previous tag + run: | + set -euo pipefail + + RELEASE_NOTES="$RUNNER_TEMP/release-notes.txt" + git log --no-merges --format='%s' ${PREVIOUS_TAG:+"$PREVIOUS_TAG"..}HEAD \ + | { grep -v '^chore: bump version to' || true; } > "$RELEASE_NOTES" + if [ ! -s "$RELEASE_NOTES" ]; then + echo "chore: release v$NEW_VERSION" > "$RELEASE_NOTES" + fi + cat "$RELEASE_NOTES" + + echo "RELEASE_NOTES=$RELEASE_NOTES" >> $GITHUB_ENV + + - name: Update CHANGELOG.md + if: hashFiles('CHANGELOG.md') != '' + run: | + set -euo pipefail + + if grep -qE "^#+ v?${NEW_VERSION//./\\.}[[:space:]]*$" CHANGELOG.md; then + echo "CHANGELOG.md already has an entry for v$NEW_VERSION, leaving it untouched" + exit 0 + fi + + # Follow the heading level and bullet style already used by the file + HEADING=$(grep -m1 -oE '^#+ v?[0-9]' CHANGELOG.md | grep -oE '^#+' || echo '##') + BULLET=$(grep -m1 -oE '^[*-] ' CHANGELOG.md | cut -c1 || echo '*') + + ENTRY="$RUNNER_TEMP/changelog-entry.md" + { + echo "$HEADING v$NEW_VERSION" + echo + sed "s/^/$BULLET /" "$RELEASE_NOTES" + } > "$ENTRY" + + awk -v entry="$ENTRY" ' + function print_entry() { while ((getline line < entry) > 0) print line; print ""; inserted = 1 } + !inserted && /^#+ v?[0-9]/ { print_entry() } + { print } + END { if (!inserted) { print ""; print_entry() } } + ' CHANGELOG.md > CHANGELOG.md.tmp + mv CHANGELOG.md.tmp CHANGELOG.md + + - name: Update debian/changelog + if: hashFiles('debian/changelog') != '' + run: | + set -euo pipefail + + if head -n1 debian/changelog | grep -qF "($NEW_VERSION)"; then + echo "debian/changelog already has an entry for $NEW_VERSION, leaving it untouched" + exit 0 + fi + + PACKAGE=$(head -n1 debian/changelog | cut -d' ' -f1) + DISTRIBUTION=$(head -n1 debian/changelog | sed -E 's/^[^)]*\) ([^;]+);.*/\1/') + MAINTAINER=$(grep -m1 '^ -- ' debian/changelog | sed -E 's/^ -- (.*>).*/\1/') + + { + echo "$PACKAGE ($NEW_VERSION) $DISTRIBUTION; urgency=medium" + echo + sed 's/^/ * /' "$RELEASE_NOTES" + echo + echo " -- $MAINTAINER $(date -R)" + echo + cat debian/changelog + } > debian/changelog.tmp + mv debian/changelog.tmp debian/changelog + + - name: Commit, tag and push + run: | + set -euo pipefail + + git add package.json package-lock.json manifest.json + for changelog in CHANGELOG.md debian/changelog; do + if [ -f "$changelog" ]; then + git add "$changelog" + fi + done + + git commit -m "chore: bump version to $NEW_VERSION" + git tag -a "v$NEW_VERSION" -m "v$NEW_VERSION" git push --follow-tags env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}