enh(CI): Automatic Release Workflow #58
Open
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Automatic Release Workflow
This PR introduces a
release
workflow that runs on the first day of every month, checks for changes onmaster
and, if so, creates a new release after approval.Tag Selection
The
verify
job selects a tag name with format%Y.%m.%d
(e.g.2025.08.01
), which always ends in01
since it runs on the first day of each month. If the tag is newer than the previous one and there are changes inmaster
, then the workflow generates a change summary and continues to therelease
job, which requests a review and awaits for approval.The examples below use format
%Y.%m.%d-%H
for faster (test) release cycles, but everything else is the same.Summary
The summary is generated with
git diff --histogram --stat $latest_tag..$release_commit
andgit log --no-merges $latest_tag..$release_commit
, so merge commits are not displayed.To prevent new commits from being integrated into the release without showing up on the summary, the
verify
job also provides therelease_commit
used.Release Summary
Checks
Each tag is checked to be newer using lexicographical order, which works for
%Y.%m.%d
. Just be aware of any additional text after the date. For example,2025.07.01-2
is considered newer than2025.07.01-10
.After that, the last commit on
master
is compared to the$latest_tag
, and the release is skipped if no change is reported.In both cases, skipping the relase is not considered a failure. The workflow just finishes early and no notification is sent anywhere.
Outdated Release
Release with No Changes
Manual Release
The job can also be triggered manually on Actions page, with an optional
release_tag
different from%Y.%m.%d
. You can also change the deployenvironment
for this manual run.Full Page
Workflow Review
Once
verify
completes with a non-emptyrelease_tag
, the workflow request reviews from defined members before starting therelease
job.The
release
job pins the release to exact$release_commit
provided byverify
, independently of how long the review process take. Once a release is verified, its commit is fixed. To include newer commits you must cancel and rerun the workflow.Release Verified, Awaiting Review
Review Notification Sent to Email
Review Page
Release Approved
Release Created
GitHub Environment
Important
This step requires manual configuration in the repository Settings.
The review system uses deploy environments on Github. The workflow doesn't actually use any information from the environment, but if the environment is configured with "Required reviewers", then it won't run by itself. Here I used
release
as the name of the environment.Environment Settings
Job Concurrency
To avoid multiple competing releases, I've set up a
concurrency
group
that disallows concurrent runs of therelease.yml
workflow. If a new workflow starts while the last one is still running, then the new one has priority and the other is cancelled. In practice, this should only happen if a release is left unapproved for more than a month.Unapproved Release
Release Creation
Once the
release
job is approved and runs, it creates a tag with the name$release_tag
provided byverify
, pointing to the pinned$release_commit
. It also creates a GitHub release with automatically generated release notes, which can be configured in a.github/release.yml
file. By default, the generated notes list all pull requests since the last release (which might be a lot for the first one here, you can create a first release to avoid this).Changelog Example
Implementation Notes
There's currently an issue (actions/checkout#1467) with
fetch_tags
on Git 2.48 (ubunut-latest
), which requires explicit fetching of the git history usingfetch-depth
andref
. I used the last 100 commits forfetch-depth
, which should be more than enough for a month. The workaround implemented here can be removed after the fix actions/checkout#2200 lands.