name: Release permissions: contents: write packages: write on: pull_request: push: tags: - "**[0-9]+.[0-9]+.[0-9]+*" jobs: ci: runs-on: ubuntu-24.04 outputs: tag: ${{ !github.event.pull_request && github.ref_name || '' }} publishing: ${{ !github.event.pull_request }} ort-version: ${{ steps.ort_version.outputs.value }} steps: - uses: actions/checkout@v4 with: submodules: recursive - name: Install Nix uses: DeterminateSystems/determinate-nix-action@v3 - uses: nix-community/cache-nix-action@v7 with: primary-key: nix-${{ runner.os }}-${{ hashFiles('**/*.nix', '**/flake.lock', 'Cargo.lock') }} restore-prefixes-first-match: nix-${{ runner.os }}- gc-max-store-size-linux: 5G - name: Read ORT version from flake id: ort_version run: echo "value=$(nix eval .#lib.ortVersion --raw)" >> "$GITHUB_OUTPUT" - name: Run nix flake check run: nix flake check --system x86_64-linux build-nix-artifacts: name: build (${{ matrix.triple }}) needs: [ci] if: ${{ needs.ci.outputs.publishing == 'true' }} strategy: fail-fast: false matrix: include: - runner: ubuntu-24.04 triple: x86_64-unknown-linux-gnu nix_package: minne-release cache_save: false - runner: macos-latest triple: aarch64-apple-darwin nix_package: minne-release cache_save: true - runner: ubuntu-24.04 triple: x86_64-pc-windows-msvc nix_package: minne-release-windows cache_save: false runs-on: ${{ matrix.runner }} steps: - uses: actions/checkout@v4 with: submodules: recursive - name: Install Nix uses: DeterminateSystems/determinate-nix-action@v3 - uses: nix-community/cache-nix-action@v7 with: primary-key: nix-${{ runner.os }}-${{ hashFiles('**/*.nix', '**/flake.lock', 'Cargo.lock') }} restore-prefixes-first-match: nix-${{ runner.os }}- gc-max-store-size-linux: 5G gc-max-store-size-darwin: 5G save: ${{ matrix.cache_save }} - name: Build release archive (Nix) run: nix build .#${{ matrix.nix_package }} -L --out-link minne-release - name: Stage artifact shell: bash run: | set -euo pipefail TRIPLE="${{ matrix.triple }}" if [[ "$TRIPLE" == *windows* ]]; then ARTIFACT="main-${TRIPLE}.zip" else ARTIFACT="main-${TRIPLE}.tar.xz" fi RELEASE="$(nix path-info ./minne-release)" cp "$RELEASE/${ARTIFACT}" "$ARTIFACT" if command -v sha256sum >/dev/null; then sha256sum "$ARTIFACT" > "${ARTIFACT}.sha256" else shasum -a 256 "$ARTIFACT" > "${ARTIFACT}.sha256" fi - name: Upload artifact uses: actions/upload-artifact@v4 with: name: release-${{ matrix.triple }} path: | main-${{ matrix.triple }}.* build_and_push_docker_image: name: Build and Push Docker Image (Nix) runs-on: ubuntu-24.04 needs: [ci] if: ${{ needs.ci.outputs.publishing == 'true' }} permissions: contents: read id-token: write packages: write actions: write steps: - uses: actions/checkout@v4 with: submodules: recursive - name: Install Nix uses: DeterminateSystems/determinate-nix-action@v3 - uses: nix-community/cache-nix-action@v7 with: primary-key: nix-${{ runner.os }}-${{ hashFiles('**/*.nix', '**/flake.lock', 'Cargo.lock') }} restore-prefixes-first-match: nix-${{ runner.os }}- gc-max-store-size-linux: 5G save: false - name: Build Docker image with Nix run: nix build .#dockerImage -L --show-trace - name: Log in to GitHub Container Registry uses: docker/login-action@v3 with: registry: ghcr.io username: ${{ github.actor }} password: ${{ secrets.GITHUB_TOKEN }} - name: Load and push Docker image env: IMAGE_NAME: ghcr.io/${{ github.repository }} IMAGE_TAG: ${{ needs.ci.outputs.tag }} run: | set -euo pipefail LOADED_IMAGE="$(docker load < result | awk '/Loaded image:/ {print $3; exit}')" if [ -z "$LOADED_IMAGE" ]; then echo "failed to load docker image from nix result" >&2 exit 1 fi docker tag "$LOADED_IMAGE" "$IMAGE_NAME:$IMAGE_TAG" docker tag "$LOADED_IMAGE" "$IMAGE_NAME:latest" docker push "$IMAGE_NAME:$IMAGE_TAG" docker push "$IMAGE_NAME:latest" release: name: Create GitHub Release needs: [ci, build-nix-artifacts, build_and_push_docker_image] if: ${{ needs.ci.outputs.publishing == 'true' }} runs-on: ubuntu-24.04 env: GH_TOKEN: ${{ secrets.GITHUB_TOKEN }} steps: - uses: actions/checkout@v4 with: submodules: recursive - name: Download release artifacts uses: actions/download-artifact@v4 with: pattern: release-* path: artifacts merge-multiple: true - name: Flatten artifacts run: find artifacts -type f -exec mv {} . \; - name: Prepare release notes env: VERSION: ${{ needs.ci.outputs.tag }} run: | set -euo pipefail if grep -q "^## ${VERSION} (" CHANGELOG.md; then awk -v ver="$VERSION" ' /^## / { if (found) exit; if ($0 ~ "^## " ver " \\(") found=1; next } found { print } ' CHANGELOG.md > "$RUNNER_TEMP/notes.txt" else awk ' /^## Unreleased/ { found=1; next } found && /^## [0-9]/ { exit } found { print } ' CHANGELOG.md > "$RUNNER_TEMP/notes.txt" fi if [ ! -s "$RUNNER_TEMP/notes.txt" ]; then echo "Release ${VERSION}" > "$RUNNER_TEMP/notes.txt" fi - name: Create GitHub Release env: TAG: ${{ needs.ci.outputs.tag }} PRERELEASE_FLAG: ${{ contains(needs.ci.outputs.tag, 'alpha') || contains(needs.ci.outputs.tag, 'beta') || contains(needs.ci.outputs.tag, 'rc') && '--prerelease' || '' }} run: | set -euo pipefail FILES=() for f in main-*; do [ -f "$f" ] || continue FILES+=("$f") done if [ "${#FILES[@]}" -eq 0 ]; then echo "no release artifacts found" >&2 ls -la exit 1 fi gh release create "$TAG" \ --target "${{ github.sha }}" \ --title "minne $TAG" \ --notes-file "$RUNNER_TEMP/notes.txt" \ $PRERELEASE_FLAG \ "${FILES[@]}"