Skip to content

Release

Release #2

Workflow file for this run

name: Release
on:
workflow_dispatch:
# Needs write access to push the release commit, tag, and next-dev-version commit.
permissions:
contents: write
jobs:
release:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v7
- uses: actions/setup-java@v5
with:
distribution: temurin
java-version: '25'
cache: maven
# Writes ~/.m2/settings.xml with a `central` server whose credentials come from these
# env vars, and imports the GPG signing key used by the release profile.
server-id: central
server-username: CENTRAL_USERNAME
server-password: CENTRAL_PASSWORD
gpg-private-key: ${{ secrets.GPG_PRIVATE_KEY }}
gpg-passphrase: GPG_PASSPHRASE
# Derive the release version (strip -SNAPSHOT) and the next dev version (bump patch).
# e.g. 1.0.0-SNAPSHOT -> release 1.0.0 -> next 1.0.1-SNAPSHOT
- name: Compute versions
id: versions
run: |
CURRENT=$(./mvnw -B -q help:evaluate -Dexpression=project.version -DforceStdout)
RELEASE=${CURRENT%-SNAPSHOT}
IFS=. read -r MAJ MIN PAT <<< "$RELEASE"
NEXT="$MAJ.$MIN.$((PAT + 1))-SNAPSHOT"
echo "release=$RELEASE" >> "$GITHUB_OUTPUT"
echo "next=$NEXT" >> "$GITHUB_OUTPUT"
echo "Releasing $RELEASE, next dev version $NEXT"
# Set the fixed release version across the reactor (parent + all modules), then point the
# standalone examples' spring-notify.version property at it so the E2E gate resolves it.
# The examples are edited with sed, not Maven: versions:set-property would need to build the
# example's model, which imports notify-bom at its *current* version — not yet installed —
# so Maven can't parse the POM it is meant to edit. sed sidesteps that chicken-and-egg.
- name: Set release version
run: |
./mvnw -B -q versions:set -DnewVersion=${{ steps.versions.outputs.release }} -DgenerateBackupPoms=false
for pom in examples/*/pom.xml; do
sed -i "s|<spring-notify.version>.*</spring-notify.version>|<spring-notify.version>${{ steps.versions.outputs.release }}</spring-notify.version>|" "$pom"
done
# Install the fixed-version library into ~/.m2 so the standalone examples can resolve it.
# Tests are skipped here — CI already ran them; the examples below are the E2E gate.
- name: Install library
run: ./mvnw -B -T 1C install -DskipTests
# Pre-publish gate: build every standalone example, running its Testcontainers
# integration tests (Mailpit, mock APNs, …) against Docker. A failure fails the release.
- name: Verify examples end-to-end
run: |
for pom in examples/*/pom.xml; do
echo "::group::Verifying $pom"
./mvnw -B -f "$pom" verify
echo "::endgroup::"
done
# Build, sign, and publish to Maven Central via the `release` profile (sources + javadoc +
# GPG signatures + central-publishing plugin with autoPublish). Runs sequentially — the
# plugin aggregates the whole reactor into one bundle at the end. Tests skipped: CI + the
# examples gate above already covered them. A failure here fails the release before the
# version commit and tag are pushed, leaving the repository untouched.
- name: Publish to Maven Central
run: ./mvnw -B -DskipTests -P release deploy
env:
CENTRAL_USERNAME: ${{ secrets.CENTRAL_USERNAME }}
CENTRAL_PASSWORD: ${{ secrets.CENTRAL_PASSWORD }}
GPG_PASSPHRASE: ${{ secrets.GPG_PASSPHRASE }}
# Commit the release version, tag it, then bump to the next -SNAPSHOT dev version.
- name: Commit release, tag, and bump to next dev version
run: |
git config user.name "github-actions[bot]"
git config user.email "github-actions[bot]@users.noreply.github.com"
git commit -am "Release ${{ steps.versions.outputs.release }}"
git tag "v${{ steps.versions.outputs.release }}"
./mvnw -B -q versions:set -DnewVersion=${{ steps.versions.outputs.next }} -DgenerateBackupPoms=false
for pom in examples/*/pom.xml; do
sed -i "s|<spring-notify.version>.*</spring-notify.version>|<spring-notify.version>${{ steps.versions.outputs.next }}</spring-notify.version>|" "$pom"
done
git commit -am "Start next development iteration ${{ steps.versions.outputs.next }}"
git push origin HEAD "v${{ steps.versions.outputs.release }}"