Skip to content

feat: Version the package with MinVer instead of a manual CI step #11

feat: Version the package with MinVer instead of a manual CI step

feat: Version the package with MinVer instead of a manual CI step #11

# Builds, verifies, and publishes to GitHub Packages.
#
# Verification is the point rather than a formality. What this repository ships is configuration, and
# configuration fails silently: a rule that cannot report looks exactly like a rule being obeyed,
# because the build is quiet either way. Both scripts below exist to make that noisy, and they run on
# pull requests as well as on main, because a rule that stopped reporting should not be discovered
# after it has merged.
name: build and publish
on:
push:
branches: [main]
tags: ['v*']
pull_request:
branches: [main]
workflow_dispatch:
# Only a version tag publishes. Pushes to main and pull requests build and verify and stop there,
# so merging is not the same act as releasing.
permissions:
contents: read
packages: write
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
jobs:
build:
runs-on: ubuntu-latest
timeout-minutes: 15
steps:
- uses: actions/checkout@v7
with:
# MinVer derives the version from git tags and the commit count above them, so it needs the
# actual history rather than actions/checkout's default shallow clone - which contains no
# tags to find.
fetch-depth: 0
- uses: actions/setup-dotnet@v6
with:
# 10, not 8. An analyser cannot reference a newer Roslyn than the compiler running it, and
# UsingLayoutAnalyser is the rule set most likely to be affected: on SDK 8 it answers
# CS9057 - a warning - and its rules are then silently absent. This is also what consumers
# build with, and testing on what people use beats testing on the oldest thing that works.
dotnet-version: '10.x'
# No NuGet.config and no secure file: every dependency is public on nuget.org. The Azure
# pipeline this replaced downloaded a secure NuGet.config it did not need.
#
# No -p:Version here: MinVer sets it from the git tag (and the commit count above one, off a
# tag), so nothing in the repository can disagree with what shipped.
- name: Build
run: dotnet build Nota.CodeAnalysis.sln --configuration Release
- name: Verify the rules report
run: ./Nota.CodeAnalysis.Verification/verify.sh
- name: Verify source encoding
run: ./Nota.CodeAnalysis.Verification/verify-encoding.sh
# The two checks above run inside the solution and cannot see whether the package delivers
# anything. This one packs, installs into a throwaway project, and compiles a file that breaks
# a rule from each analyser. It is the only check that fails when a package installs cleanly
# and does nothing, which has happened twice.
- name: Verify the package delivers the rules
run: ./Nota.CodeAnalysis.Verification/verify-package.sh
- name: Pack
run: dotnet pack Nota.CodeAnalysis.sln --configuration Release --no-build --output artifacts
# Kept even on a pull request, so a packaging mistake is visible without merging.
- name: Upload the package
uses: actions/upload-artifact@v7
with:
name: nupkg
path: artifacts/*.nupkg
# GITHUB_TOKEN rather than a personal access token: publishing to this repository's own package
# registry needs nothing else, which is the whole reason to be here rather than in Azure.
# --skip-duplicate so re-running a failed job is not itself an error; the registry keeps a
# version forever, and pushing the same one twice is worth ignoring rather than failing on.
- name: Publish to GitHub Packages
if: github.ref_type == 'tag'
run: >
dotnet nuget push artifacts/*.nupkg
--source https://nuget.pkg.github.com/Notalib/index.json
--api-key ${{ secrets.GITHUB_TOKEN }}
--skip-duplicate