name: Update
on:
workflow_dispatch:
push:
branches: [main]
permissions:
actions: write
contents: write
pull-requests: write
concurrency:
group: update-${{ github.ref }}
cancel-in-progress: true
jobs:
update:
runs-on: ubuntu-latest
timeout-minutes: 15
if: >-
github.event_name == 'workflow_dispatch' ||
(
!startsWith(github.event.head_commit.message, 'chore') &&
!startsWith(github.event.head_commit.message, 'style') &&
!startsWith(github.event.head_commit.message, 'test') &&
!startsWith(github.event.head_commit.message, 'ci') &&
!startsWith(github.event.head_commit.message, 'lint') &&
!startsWith(github.event.head_commit.message, 'build') &&
!contains(github.event.head_commit.message, 'release-plz-')
)
steps:
- name: Clone repository
uses: actions/checkout@v6
with:
fetch-depth: 0
token: ${{ secrets.GITHUB_TOKEN }}
- name: Get Rust version
id: rust-version
run: |
RUST_VERSION=$(grep '^rust-version = ' Cargo.toml | sed 's/rust-version = "\(.*\)"/\1/')
echo "version=$RUST_VERSION" >> $GITHUB_OUTPUT
- name: Install Rust toolchain
uses: dtolnay/rust-toolchain@stable
with:
toolchain: ${{ steps.rust-version.outputs.version }}
- name: Install nightly Rust for formatting
uses: dtolnay/rust-toolchain@nightly
with:
components: rustfmt
- name: Cache Rust dependencies
uses: Swatinem/rust-cache@v2
with:
shared-key: msrv
- name: Format code with nightly
run: cargo +nightly fmt
- name: Install release-plz
uses: taiki-e/install-action@v2
with:
tool: release-plz
- name: Create release PR
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
release-plz release-pr --git-token "$GITHUB_TOKEN" || {
echo "::error::release-plz release-pr failed"
exit 1
}
- name: Trigger release PR checks
env:
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
PR_NUMBER=$(gh pr list \
--state open \
--base main \
--json number,headRefName,updatedAt \
--jq 'map(select(.headRefName | startswith("release-plz-"))) | sort_by(.updatedAt) | last | .number // empty')
if [[ -z "$PR_NUMBER" ]]; then
echo "No open release PR found; skipping explicit CI dispatch."
exit 0
fi
HEAD_REF=$(gh pr view "$PR_NUMBER" --json headRefName --jq '.headRefName')
HEAD_SHA=$(gh pr view "$PR_NUMBER" --json headRefOid --jq '.headRefOid')
echo "Dispatching CI for release PR #$PR_NUMBER ($HEAD_REF @ $HEAD_SHA)."
# Each dispatch is independent: one failing must not skip the others.
# A rename leaves the old workflow registered until GitHub catches up,
# so a dispatch can transiently resolve to a workflow that no longer
# exists on the ref — report it and keep going, then fail at the end.
dispatch_failed=0
dispatch() {
local workflow="$1"
shift
if ! gh workflow run "$workflow" --ref "$HEAD_REF" "$@"; then
echo "::warning::failed to dispatch $workflow for $HEAD_REF"
dispatch_failed=1
fi
}
dispatch ci.yml
dispatch criterion.yml
if (( dispatch_failed )); then
echo "::error::one or more CI dispatches failed for release PR #$PR_NUMBER"
exit 1
fi