Skip to content

draft-release

draft-release #24

Workflow file for this run

name: draft-release
on:
workflow_dispatch:
inputs:
version_tag:
description: Semantic version tag for next release. If not provided, it will be determined based on conventional commmit history.
required: false
type: string
default: ''
push:
branches:
- release-draft
jobs:
draft-release:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0 # required to include tags
- uses: actions/setup-python@v4
with:
python-version: '3.11'
cache: 'pip'
- run: pip install cffconvert>=2.0.0
- name: Get Date
run: |
echo "DATE=$(date +"%Y-%m-%d")" >> "$GITHUB_ENV"
- name: Get current and next versions
id: semver
uses: ietf-tools/semver-action@v1
with:
token: ${{ github.token }}
branch: ${{ github.ref_name }}
- name: Set version variables
shell: python {0}
run: |
import os
import re
import warnings
convco_version = "${{ steps.semver.outputs.next }}"
if "${{ github.event_name }}" == 'workflow_dispatch' and "${{ github.event.inputs.version_tag }}":
next_version = "${{ github.event.inputs.version_tag }}"
if next_version != convco_version:
warnings.warn("Manual version ({next_version}) not equal to version determined by conventional commit history ({convco_version})")
else:
next_version = convco_version
with open(os.getenv("GITHUB_ENV"), 'a') as out_env:
out_env.write(f"NEXT_VERSION={next_version}")
current_version = "${{ steps.semver.outputs.current }}"
# assert semantic version pattern
semver_pattern = 'v(?P<major>0|[1-9]\d*)\.(?P<minor>0|[1-9]\d*)\.(?P<patch>0|[1-9]\d*)(?:-(?P<prerelease>(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+(?P<buildmetadata>[0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?'
next_semver = re.match(semver_pattern, next_version)
if not next_semver:
raise ValueError(f"Tag {next_version} does not match semantic versioning guidelines")
# assert next version is only 1 greater than current
current_semver = re.match(semver_pattern, current_version)
groups = ['major', 'minor', 'patch']
greater = sum([next_semver.group(grp) > current_semver.group(grp) for grp in groups])
equal = sum([next_semver.group(grp) == current_semver.group(grp) for grp in groups])
if not (greater == 1 and equal == 2):
raise ValueError(f"Next version must only increment one number at a time. Current version: {current_version}. Proposed next version: {next_version}")
- name: Get release notes & update changelog
shell: python {0}
run: |
import os
latest_version = "${{ steps.semver.outputs.current }}".strip('v')
next_version = "${{ env.NEXT_VERSION }}".strip('v')
changelog_lines = list()
next_release_lines = list()
for_next = True
with open("CHANGELOG.md", "r") as infile:
for line in infile:
if line.startswith('#') and 'development version' in line:
line = line.replace('development version', next_version)
elif latest_version in line:
for_next = False
changelog_lines.append(line)
if for_next:
next_release_lines.append(line)
with open(".github/latest-release.md", "w") as outfile:
outfile.write(''.join(next_release_lines))
with open('CHANGELOG.md', 'w') as outfile:
outfile.write(''.join(changelog_lines))
- name: Update citation & version files
shell: python {0}
run: |
from cffconvert.cli.create_citation import create_citation
from cffconvert.cli.validate_or_write_output import validate_or_write_output
citation = create_citation('CITATION.cff', None)
citation._implementation.cffobj['version'] = "${{ env.NEXT_VERSION }}"
citation._implementation.cffobj['date-released'] = "${{ env.DATE }}"
validate_or_write_output("CITATION.cff", 'cff', False, citation)
with open("VERSION", "w") as outfile:
version_strict = '${{ env.NEXT_VERSION }}'.strip('v')
outfile.write(f"{version_strict}\n")
- name: Commit & push to branch
run: |
git config --local user.name "github-actions[bot]"
git config --local user.email "41898282+github-actions[bot]@users.noreply.github.com"
git push origin --delete release-draft || echo "No release-draft branch to delete"
git switch -c release-draft || git switch release-draft
git merge --ff-only ${{ github.ref_name }}
git add CITATION.cff CHANGELOG.md VERSION
git commit -m 'chore: prepare release ${{ env.NEXT_VERSION }}'
git push --set-upstream origin release-draft
echo "COMMIT_HASH=$(git rev-parse HEAD)" >> "$GITHUB_ENV"
- name: Tag & draft release
uses: actions/create-release@v1
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
with:
tag_name: ${{ env.NEXT_VERSION }}
release_name: ${{ github.event.repository.name }} ${{ env.NEXT_VERSION }}
commitish: ${{ env.COMMIT_HASH }}
draft: true
body_path: .github/latest-release.md
- name: Next steps
run: |
echo "Next steps: Take a look at the changes in the release-draft branch and the release notes on the web. If everything is correct, publish the release. Otherwise, delete the release & tag and cut the release manually."