From 58d807b89004339743052beb58564a6b8ce0a845 Mon Sep 17 00:00:00 2001 From: Thomas Kroll Date: Fri, 13 Nov 2026 11:57:51 +0100 Subject: [PATCH] Release: dry run before the tag; say when the release exists; check the CHANGELOG in CI README lists the dry run before the tag push, as tags cannot be moved. The dry run says when the tag or release already exists instead of "would create". CI gets a changelog job, part of required, that runs release-notes.sh for the plugin.json version. Fixes #140 Co-Authored-By: Claude Sonnet 5.5 --- .github/workflows/ci.yml | 16 ++++++++++++++-- .github/workflows/release.yml | 7 ++++++- CHANGELOG.md | 4 +++- README.md | 7 ++++--- 4 files changed, 27 insertions(+), 7 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index fe0014c..054443f 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -36,18 +36,30 @@ jobs: persist-credentials: false - run: shellcheck scripts/*.sh + # The version in plugin.json must have a non-empty CHANGELOG.md section (what the release needs). + changelog: + runs-on: ubuntu-24.04 + timeout-minutes: 5 + steps: + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 + with: + persist-credentials: false + - run: scripts/release-notes.sh HEAD "v$(jq -r .version plugin.json)" >/dev/null + # The one check the main ruleset requires. It passes only when every gate succeeded. required: name: required - needs: [qml, shellcheck] + needs: [qml, shellcheck, changelog] if: always() runs-on: ubuntu-24.04 timeout-minutes: 5 env: QML: ${{ needs.qml.result }} SHELLCHECK: ${{ needs.shellcheck.result }} + CHANGELOG: ${{ needs.changelog.result }} steps: - run: | - echo "qml=$QML shellcheck=$SHELLCHECK" + echo "qml=$QML shellcheck=$SHELLCHECK changelog=$CHANGELOG" test "$QML" = success test "$SHELLCHECK" = success + test "$CHANGELOG" = success diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 759863f..234cc7a 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -54,7 +54,12 @@ jobs: scripts/release-green.sh "$sha" scripts/release-notes.sh "$sha" "$TAG" > notes.md if [ "$GITHUB_EVENT_NAME" = workflow_dispatch ]; then - echo "Dry run: would create release $TAG on $sha with these notes, nothing created:" + if git rev-parse --verify --quiet "refs/tags/$TAG" >/dev/null || + gh release view "$TAG" >/dev/null 2>&1; then + echo "Dry run: the tag or a release $TAG already exists; a tag push would not create anything new. The checks passed for $sha; nothing created. Notes it would have:" + else + echo "Dry run: would create release $TAG on $sha with these notes, nothing created:" + fi else echo "Checks passed: release $TAG on $sha with these notes:" fi diff --git a/CHANGELOG.md b/CHANGELOG.md index 9b9e65f..2bb7e1b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -14,7 +14,9 @@ the change) are credited at the end of their line as `(#N, thanks @handle)`. `main` (#132). - A tag `vX.Y.Z` now creates the GitHub release by workflow. It first checks that the tag equals the `plugin.json` version, that the commit is on `main` and was green as a pull request, and that - `CHANGELOG.md` has a section for the version; the release notes are that section (#138). + `CHANGELOG.md` has a section for the version; the release notes are that section (#138). A dry run says when the + tag or release already exists. CI checks that the `plugin.json` version has a CHANGELOG section + (#140). ### Changed diff --git a/README.md b/README.md index 1f97912..b69a4c7 100644 --- a/README.md +++ b/README.md @@ -188,12 +188,13 @@ Tiny 2 Lite. 1. Land a commit "Release X.Y.Z" through a pull request: it sets `version` in `plugin.json` and turns the `## [Unreleased]` entries of `CHANGELOG.md` into a `## [X.Y.Z] - date` section. -2. Push the signed tag `vX.Y.Z` on that commit. The Release workflow creates the GitHub release, +2. Dry run: run the Release workflow by hand with that commit and the version; it runs the checks + and prints the release it would create, and creates nothing. Do this before the tag: tags `v*` + cannot be moved or deleted in this repository, so a tag on a bad release commit burns the version. +3. Push the signed tag `vX.Y.Z` on that commit. The Release workflow creates the GitHub release, with that CHANGELOG section as notes, after it has checked that the tag equals the `plugin.json` version, that the commit is on `main` and was green as a pull request, and that the section exists. If a check fails, no release is created. -3. Dry run: run the Release workflow by hand with a commit and a version; it runs the checks and - prints the release it would create. ## License