Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 33 additions & 7 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,18 +14,40 @@ on:
permissions:
contents: read # jobs that publish raise their own permissions

# macOS runners are severely constrained: macOS runs only on a push to main, plus the osx-arm64 AOT pack on a release
# (macOS AOT only compiles on macOS). A release runs no checks of its own beyond packing and the AOT smoke test:
# main-green requires main's run on the released commit to have passed.
jobs:
# A release ships a commit main has already proven: wait for main's push run of ci.yml on the released commit and stop
# unless it passed. Every job that runs on a release needs this one, directly or through another.
main-green:
if: github.event_name == 'release'
name: main is green
runs-on: ubuntu-latest
timeout-minutes: 70
permissions:
actions: read # read main's ci.yml runs
steps:
- uses: nullean/.github/actions/require-green-main@f9eb30d28e48b3f6b8ff1f4e7dae1d2b7b2d544b # v1.6.0

# On pull requests, only linux-x64 runs, to prove AOT still links without burning the full matrix
# on packages nobody sees. All five run on push, where the packages are actually uploaded.
# on packages nobody sees. All five run on a push to main and on a release, where the packages are actually
# uploaded; osx-arm64 is the one macOS job a release runs. workflow_dispatch runs the four that need no macOS.
aot-pack:
needs: main-green
# main-green is skipped on everything but a release, which would skip this job too without a status function.
if: ${{ !cancelled() && (github.event_name != 'release' || needs.main-green.result == 'success') }}
runs-on: ${{ matrix.runner }}
name: AOT pack (${{ matrix.rid }})
strategy:
fail-fast: false
matrix:
include: ${{ fromJSON(github.event_name == 'pull_request'
&& '[{"rid":"linux-x64","runner":"ubuntu-latest"}]'
|| '[{"rid":"linux-x64","runner":"ubuntu-latest"},{"rid":"linux-arm64","runner":"ubuntu-24.04-arm"},{"rid":"win-x64","runner":"windows-latest"},{"rid":"win-arm64","runner":"windows-11-arm"},{"rid":"osx-arm64","runner":"macos-latest"}]') }}
include: ${{ fromJSON(
(github.event_name == 'pull_request'
&& '[{"rid":"linux-x64","runner":"ubuntu-latest"}]')
|| ((github.event_name == 'push' || github.event_name == 'release')
&& '[{"rid":"linux-x64","runner":"ubuntu-latest"},{"rid":"linux-arm64","runner":"ubuntu-24.04-arm"},{"rid":"win-x64","runner":"windows-latest"},{"rid":"win-arm64","runner":"windows-11-arm"},{"rid":"osx-arm64","runner":"macos-latest"}]')
|| '[{"rid":"linux-x64","runner":"ubuntu-latest"},{"rid":"linux-arm64","runner":"ubuntu-24.04-arm"},{"rid":"win-x64","runner":"windows-latest"},{"rid":"win-arm64","runner":"windows-11-arm"}]') }}
steps:
- uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
with:
Expand Down Expand Up @@ -75,7 +97,10 @@ jobs:

build:
runs-on: ubuntu-latest
needs: aot-pack
needs: [main-green, aot-pack]
if: >-
${{ !cancelled() && needs.aot-pack.result == 'success'
&& (github.event_name != 'release' || needs.main-green.result == 'success') }}
permissions:
contents: write # append the public API changes to the release notes
packages: write # push to GitHub Packages and ghcr.io
Expand Down Expand Up @@ -113,9 +138,10 @@ jobs:
- run: ./build.sh generateapichanges -s
name: "Inspect public API changes"

# the tools are restored by the steps above
# the tools are restored by the steps above. Not on a release: main's run on this commit checked it.
- run: dotnet curb check .
name: Check formatting (curb)
if: github.event_name != 'release'

- name: publish to github package repository
if: github.event_name == 'push' && startswith(github.ref, 'refs/heads')
Expand Down Expand Up @@ -181,6 +207,6 @@ jobs:
gh release edit "$TAG" --repo "$GITHUB_REPOSITORY" --notes-file "$RUNNER_TEMP/notes.md"

zizmor:
uses: nullean/.github/.github/workflows/zizmor.yml@d850ce6eee9efa9f81b410d15fcd480409518d19 # v1.5.0
uses: nullean/.github/.github/workflows/zizmor.yml@e21d5f59405aa7078e51825cd4c407191e28562f # v1.6.1
permissions:
contents: read
12 changes: 12 additions & 0 deletions .github/workflows/create-major-tag.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,19 @@ concurrency:
cancel-in-progress: false

jobs:
# A release moves the major tag only for a commit main has already proven: wait for main's push run of ci.yml on the
# released commit and stop unless it passed.
main-green:
name: main is green
runs-on: ubuntu-latest
timeout-minutes: 70
permissions:
actions: read # read main's ci.yml runs
steps:
- uses: nullean/.github/actions/require-green-main@f9eb30d28e48b3f6b8ff1f4e7dae1d2b7b2d544b # v1.6.0

create-major-tag:
needs: main-green
permissions:
contents: write
runs-on: ubuntu-latest
Expand Down
6 changes: 4 additions & 2 deletions AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -36,8 +36,10 @@ build targets directly; CI calls it step by step, including `publishcontainers`,
## Releasing

release-drafter keeps a draft release up to date from the labels of merged pull requests. **Publishing the draft**
releases: it creates the tag, and `ci.yml` runs on it to build every RID's native-AOT package, push
`ghcr.io/nullean/release-notes` (tagged `latest` and the version) and push the packages to nuget.org. `mise run release`
releases: it creates the tag, and `ci.yml` runs on it. Its `main-green` job first waits for main's push run of `ci.yml` on
the released commit and fails unless it passed (macOS runs only on pushes to main, plus the osx-arm64 AOT pack on a
release); then it builds every RID's native-AOT package, pushes
`ghcr.io/nullean/release-notes` (tagged `latest` and the version) and pushes the packages to nuget.org. `mise run release`
shows the draft. The [releasing](.claude/skills/releasing/SKILL.md) and
[breaking-changes](.claude/skills/breaking-changes/SKILL.md) skills have the details. Every pull request carries exactly
one release label. This repository's own releases do not run the tool: release-drafter writes their notes.
Expand Down
Loading