Skip to content

release: V1.54.0

release: V1.54.0 #172

Workflow file for this run

name: Release
on:
push:
tags:
- 'V*'
permissions:
contents: read
jobs:
build:
name: Build
runs-on: ${{ matrix.os }}
timeout-minutes: 30
strategy:
matrix:
include:
- os: macos-latest
target: release-amd64
artifact_name: binaries-amd64
- os: macos-latest
target: release-arm64
artifact_name: binaries-arm64
steps:
- name: Checkout code
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
- name: Verify release tag matches source version
env:
RELEASE_TAG: ${{ github.ref_name }}
run: |
SOURCE_VERSION=$(sed -n 's/^VERSION="\([^"]*\)"$/\1/p' mole)
EXPECTED_TAG="V${SOURCE_VERSION}"
if [[ -z "$SOURCE_VERSION" || "$RELEASE_TAG" != "$EXPECTED_TAG" ]]; then
echo "Release tag ${RELEASE_TAG} does not match source ${EXPECTED_TAG}" >&2
exit 1
fi
- name: Set up Go
uses: actions/setup-go@b7ad1dad31e06c5925ef5d2fc7ad053ef454303e # v7.0.0
with:
go-version-file: go.mod
- name: Build Binaries
run: |
make ${{ matrix.target }}
ls -l bin/
./scripts/check_release_minos.sh
- name: Package binaries for Homebrew
run: |
cd bin
# Package binaries into tar.gz for Homebrew resource
if [[ "${{ matrix.target }}" == "release-arm64" ]]; then
tar -czf binaries-darwin-arm64.tar.gz analyze-darwin-arm64 status-darwin-arm64
ls -lh binaries-darwin-arm64.tar.gz
else
tar -czf binaries-darwin-amd64.tar.gz analyze-darwin-amd64 status-darwin-amd64
ls -lh binaries-darwin-amd64.tar.gz
fi
- name: Upload artifacts
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
with:
name: ${{ matrix.artifact_name }}
path: bin/*-darwin-*
retention-days: 1
release:
name: Publish Release
needs: build
runs-on: ubuntu-latest
timeout-minutes: 20
permissions:
contents: write
attestations: write
id-token: write
steps:
- name: Download all artifacts
uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1
with:
path: bin
pattern: binaries-*
merge-multiple: true
- name: Display structure of downloaded files
run: ls -R bin/
- name: Generate release checksums
run: |
cd bin
mapfile -t release_files < <(find . -maxdepth 1 -type f -printf '%P\n' | sort)
if [[ ${#release_files[@]} -eq 0 ]]; then
echo "No release assets found"
exit 1
fi
sha256sum "${release_files[@]}" > SHA256SUMS
cat SHA256SUMS
- name: Generate artifact attestation
uses: actions/attest-build-provenance@4d101475d8b20a2381f78447822ac1eab6504dd8 # v4.2.2
with:
subject-path: |
bin/analyze-darwin-*
bin/status-darwin-*
bin/binaries-darwin-*.tar.gz
bin/SHA256SUMS
- name: Create Release
uses: softprops/action-gh-release@efb35369e0ad2afab669f228072c1b0d510eae64 # v3.0.3
if: startsWith(github.ref, 'refs/tags/')
with:
name: ${{ github.ref_name }}
files: bin/*
generate_release_notes: false
draft: false
prerelease: false
update-homebrew-core:
name: Update Homebrew Core
runs-on: ubuntu-latest
timeout-minutes: 15
needs: release
steps:
- name: Checkout code
uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1
- name: Extract version from tag
id: tag_version
run: |
TAG=${GITHUB_REF#refs/tags/}
VERSION=${TAG#V}
echo "tag=$TAG" >> $GITHUB_OUTPUT
echo "version=$VERSION" >> $GITHUB_OUTPUT
echo "Releasing version: $VERSION (tag: $TAG)"
- name: Update Homebrew formula (Official Core)
id: official_core
env:
GH_TOKEN: ${{ secrets.HOMEBREW_GITHUB_API_TOKEN }}
TAG: ${{ steps.tag_version.outputs.tag }}
VERSION: ${{ steps.tag_version.outputs.version }}
# mislav/bump-homebrew-formula-action@v4.1 fatals on the GitHub tarball
# HEAD's HTTP 303 redirect (upstream issue #340). Until that lands, do
# the bump by hand: sync our fork, edit Formula/m/mole.rb, push, and
# open the PR via gh while preserving the existing release gates.
run: |
set -euo pipefail
SOURCE_SHA=$(curl -fsSL "https://github.com/tw93/Mole/archive/refs/tags/${TAG}.tar.gz" | sha256sum | awk '{print $1}')
if [[ -z "$SOURCE_SHA" ]]; then
echo "Failed to resolve source tarball sha256"
exit 1
fi
export GIT_TERMINAL_PROMPT=0
REMOTE="https://x-access-token:${GH_TOKEN}@github.com/tw93/homebrew-core.git"
UPSTREAM="https://github.com/Homebrew/homebrew-core.git"
WORK_DIR=$(mktemp -d)
BRANCH="mole-${VERSION}"
git clone --depth=1 "$REMOTE" "$WORK_DIR"
cd "$WORK_DIR"
git config user.name "github-actions[bot]"
git config user.email "41898282+github-actions[bot]@users.noreply.github.com"
git remote add upstream "$UPSTREAM"
git fetch upstream main --depth=1
git reset --hard upstream/main
git checkout -B "$BRANCH"
REMOTE_BRANCH_SHA=$(git ls-remote --heads origin "refs/heads/${BRANCH}" | awk 'NR == 1 { print $1 }')
# Only rewrite url and the source sha256 right after it. The bottle
# block stays untouched: Homebrew's check-bottle-block CI hook fails
# PRs that modify it because BrewTestBot rebuilds bottles after the
# url change lands.
if ! awk -v new_url="https://github.com/tw93/Mole/archive/refs/tags/${TAG}.tar.gz" \
-v new_sha="$SOURCE_SHA" '
BEGIN { url_done = 0; sha_done = 0; url_matches = 0; sha_matches = 0 }
/^ url "/ { url_matches++ }
/^ sha256 "/ { sha_matches++ }
!url_done && /^ url "/ { print " url \"" new_url "\""; url_done = 1; next }
url_done && !sha_done && /^ sha256 "/ { print " sha256 \"" new_sha "\""; sha_done = 1; next }
{ print }
END { if (url_matches != 1 || sha_matches != 1) exit 1 }
' Formula/m/mole.rb > Formula/m/mole.rb.new; then
echo "Expected exactly one source url and sha256 in the Homebrew formula" >&2
exit 1
fi
mv Formula/m/mole.rb.new Formula/m/mole.rb
if git diff --quiet -- Formula/m/mole.rb; then
echo "Formula already on ${VERSION}, nothing to push"
echo "core_status=published" >> "$GITHUB_OUTPUT"
echo "pr_url=https://formulae.brew.sh/formula/mole" >> "$GITHUB_OUTPUT"
exit 0
fi
if [[ -n "$REMOTE_BRANCH_SHA" ]]; then
echo "Homebrew release branch ${BRANCH} already exists; refusing to overwrite it." >&2
echo "Inspect the existing release PR and remove the branch only after resolving it, then rerun." >&2
exit 1
fi
git add Formula/m/mole.rb
git commit -m "mole ${VERSION}" -m "Automated release via GitHub Actions"
git push "--force-with-lease=refs/heads/${BRANCH}:" origin "$BRANCH"
# Homebrew closes PRs that omit its current template. Keep the full
# checklist, with unperformed local checks left unticked, so the PR
# remains honest and the template checker can validate it.
read -r -d '' PR_BODY <<'PR_BODY_EOF' || true
Release notes: https://github.com/tw93/Mole/releases/tag/__TAG__
-----
<!-- Do not tick a checkbox if you haven’t performed its action. Honesty is indispensable for a smooth review process. -->
<!-- Use [x] to mark item done before creation, or just click the checkboxes with device pointer after creation -->
<!-- In the following questions `<formula>` is the name of the formula you're editing. -->
- [ ] Have you followed the [guidelines for contributing](https://github.com/Homebrew/homebrew-core/blob/HEAD/CONTRIBUTING.md)?
- [x] Have you ensured that your commits follow the [commit style guide](https://docs.brew.sh/Formula-Cookbook#commit)?
- [ ] Have you checked that there aren't other open [pull requests](https://github.com/Homebrew/homebrew-core/pulls) for the same formula update/change?
- [ ] Have you built your formula locally with `HOMEBREW_NO_INSTALL_FROM_API=1 brew install --build-from-source <formula>`?
- [ ] Is your test running fine `brew test <formula>`?
- [ ] Does your build pass `brew audit --strict <formula>` (after doing `HOMEBREW_NO_INSTALL_FROM_API=1 brew install --build-from-source <formula>`)? If this is a new formula, does it pass `brew audit --new <formula>`?
The formula URL and checksum were generated by the Mole release workflow. Homebrew Core CI performs the platform builds, tests, and audit after the PR opens.
-----
- [ ] AI was used to generate or assist with generating this PR. *Please specify below how you used AI to help you, and what steps you have taken to manually verify the changes*.
-----
PR_BODY_EOF
PR_BODY="${PR_BODY//__TAG__/$TAG}"
PR_NUMBER=$(gh api \
"repos/Homebrew/homebrew-core/pulls?state=all&head=tw93:${BRANCH}" \
--jq '.[0].number // empty')
if [[ -z "$PR_NUMBER" ]]; then
PR_NUMBER=$(gh api --method POST repos/Homebrew/homebrew-core/pulls \
-f base=main \
-f head="tw93:${BRANCH}" \
-f title="mole ${VERSION}" \
--raw-field body="$PR_BODY" \
--jq '.number')
else
# Editing a template-closed PR triggers Homebrew's checker to
# reopen it automatically when the closer was its own bot.
gh api --method PATCH "repos/Homebrew/homebrew-core/pulls/${PR_NUMBER}" \
--raw-field body="$PR_BODY" > /dev/null
fi
PR_STATE=""
for _ in {1..12}; do
PR_STATE=$(gh api "repos/Homebrew/homebrew-core/pulls/${PR_NUMBER}" --jq '.state')
[[ "$PR_STATE" == "open" ]] && break
sleep 5
done
if [[ "$PR_STATE" != "open" ]]; then
echo "Homebrew Core PR #${PR_NUMBER} is not open after template validation" >&2
exit 1
fi
echo "pr_number=${PR_NUMBER}" >> "$GITHUB_OUTPUT"
echo "pr_url=https://github.com/Homebrew/homebrew-core/pull/${PR_NUMBER}" >> "$GITHUB_OUTPUT"
echo "core_status=pr-open" >> "$GITHUB_OUTPUT"
- name: Verify formula updates
env:
GH_TOKEN: ${{ secrets.HOMEBREW_GITHUB_API_TOKEN }}
run: |
CORE_STATUS="${{ steps.official_core.outputs.core_status }}"
PR_NUMBER="${{ steps.official_core.outputs.pr_number }}"
if [[ "$CORE_STATUS" == "pr-open" ]]; then
PR_STATE=$(gh api "repos/Homebrew/homebrew-core/pulls/${PR_NUMBER}" --jq '.state')
if [[ "$PR_STATE" != "open" ]]; then
echo "Homebrew Core PR #${PR_NUMBER} is not open" >&2
exit 1
fi
elif [[ "$CORE_STATUS" != "published" ]]; then
echo "Unknown Homebrew Core publication state: ${CORE_STATUS:-empty}" >&2
exit 1
fi
echo "✓ Homebrew Core formula update verified"
echo " Version: ${{ steps.tag_version.outputs.version }}"
echo " Tag: ${{ steps.tag_version.outputs.tag }}"
echo " Official core: ${{ steps.official_core.outputs.pr_url }}"