# Auto-update workflow for the fai/homebrew-tap repo. # # Lives here as the canonical source of truth. The bootstrap # script (scripts/bootstrap-distribution-repos.sh in # fai/platform) seeds this file into the tap repo at # .forgejo/workflows/update.yml. Edit it here, run the # bootstrap script, the tap repo picks up the new version. # # What it does: # * Every 4 hours, fetches the latest release manifest for # fai/platform. # * If the version differs from the one currently in # Formula/fai.rb, rewrites the formula's version + sha256 # entries (macos-aarch64 + macos-x86_64) and commits. # * Workflow_dispatch trigger lets you force an update from # the Forgejo UI without waiting for the cron tick. # # Manifest contract: fai/platform's release.yml writes # .binaries.{macos-aarch64,macos-x86_64}.sha256 — see # crates/fai_hub/src/update.rs::ReleaseManifest for the # authoritative schema. name: Update Homebrew formula on: schedule: - cron: '0 */4 * * *' workflow_dispatch: {} jobs: update: name: Sync formula to latest platform release runs-on: ubuntu-latest steps: - name: Checkout via external URL run: | set -eu mkdir -p "$GITHUB_WORKSPACE" cd "$GITHUB_WORKSPACE" git init -q git remote add origin \ "https://x-access-token:${GITHUB_TOKEN}@git.flemming.ai/${GITHUB_REPOSITORY}.git" git fetch --depth=1 origin "$GITHUB_REF_NAME" git checkout -q FETCH_HEAD - name: Install jq + curl run: | apt-get update -qq apt-get install -y --no-install-recommends jq curl ca-certificates - name: Fetch latest manifest id: manifest run: | set -eu # Forgejo's releases API returns newest-first. REL=$(curl -fsSL \ "https://git.flemming.ai/api/v1/repos/fai/platform/releases?limit=1" \ | jq -r '.[0]') TAG=$(echo "$REL" | jq -r '.tag_name') VERSION="${TAG#v}" MANIFEST=$(curl -fsSL \ "https://git.flemming.ai/fai/platform/releases/download/${TAG}/manifest.json") MAC_ARM=$(echo "$MANIFEST" | jq -r '.binaries["macos-aarch64"].sha256 // empty') MAC_X64=$(echo "$MANIFEST" | jq -r '.binaries["macos-x86_64"].sha256 // empty') if [ -z "$MAC_ARM" ] || [ -z "$MAC_X64" ]; then echo "manifest for $TAG has no macOS entries yet — likely the local" echo "publish step hasn't run. Skipping update." echo "skip=true" >> "$GITHUB_OUTPUT" exit 0 fi echo "version=$VERSION" >> "$GITHUB_OUTPUT" echo "sha_aarch64=$MAC_ARM" >> "$GITHUB_OUTPUT" echo "sha_x86_64=$MAC_X64" >> "$GITHUB_OUTPUT" - name: Detect formula version id: current if: steps.manifest.outputs.skip != 'true' run: | CUR=$(grep -E '^\s*version\s+"' Formula/fai.rb \ | head -1 | sed -E 's/.*"([^"]+)".*/\1/') echo "version=$CUR" >> "$GITHUB_OUTPUT" - name: Rewrite Formula/fai.rb id: rewrite if: | steps.manifest.outputs.skip != 'true' && steps.manifest.outputs.version != steps.current.outputs.version env: NEW_VERSION: ${{ steps.manifest.outputs.version }} NEW_SHA_AARCH64: ${{ steps.manifest.outputs.sha_aarch64 }} NEW_SHA_X86_64: ${{ steps.manifest.outputs.sha_x86_64 }} run: | set -eu python3 - <<'PY' import os, re, pathlib p = pathlib.Path("Formula/fai.rb") src = p.read_text() new_version = os.environ["NEW_VERSION"] arm_sha = os.environ["NEW_SHA_AARCH64"] x64_sha = os.environ["NEW_SHA_X86_64"] # version line src = re.sub(r'(\bversion\s+)"[^"]+"', f'\\1"{new_version}"', src, count=1) # find the two sha256 lines, one in the arm branch, one in # the else branch. The formula's structure is fixed — # aarch64 block comes first. lines = src.splitlines() replaced = 0 for i, line in enumerate(lines): m = re.match(r'(\s*sha256\s+)"[^"]+"', line) if not m: continue sha = arm_sha if replaced == 0 else x64_sha lines[i] = f'{m.group(1)}"{sha}"' replaced += 1 if replaced == 2: break if replaced != 2: raise SystemExit(f"expected 2 sha256 lines, rewrote {replaced}") p.write_text("\n".join(lines) + "\n") PY echo "rewritten=true" >> "$GITHUB_OUTPUT" - name: Commit + push if: steps.rewrite.outputs.rewritten == 'true' env: NEW_VERSION: ${{ steps.manifest.outputs.version }} run: | set -eu git config user.email "platform@flemming.ai" git config user.name "fai-tap-bot" git add Formula/fai.rb git commit -s -m "chore: formula -> v${NEW_VERSION}" git push origin "HEAD:${GITHUB_REF_NAME}"