Skip to content

chore(www,ci): drop unsupported mac builds from downloads, template release notes#732

Merged
softmarshmallow merged 5 commits into
mainfrom
worktree-downloads-and-release-notes
May 20, 2026
Merged

chore(www,ci): drop unsupported mac builds from downloads, template release notes#732
softmarshmallow merged 5 commits into
mainfrom
worktree-downloads-and-release-notes

Conversation

@softmarshmallow
Copy link
Copy Markdown
Member

@softmarshmallow softmarshmallow commented May 20, 2026

Two related cleanups now that macOS builds are arm64-only (#731).

Summary

1. Downloads page

The /downloads page advertised macOS Universal and macOS Intel builds that we no longer produce. Removed those references end-to-end:

  • downloads.ts — drop mac_dmg_x64 / mac_dmg_universal from the DownloadLinks interface and from both getLinks and getLinks_v001. Drop "universal" from the Arch union. Switch the per-platform default for "mac" from mac_dmg_universalmac_dmg_arm64.
  • page.tsx — remove the "macOS (Universal)" and "macOS (Intel-based Macs)" buttons. Keep "macOS (Apple Silicon)".

The legacy v0.0.1 release still has the universal/x64 dmg artifacts so any direct download links out there keep working; the page just doesn't surface them anymore. New releases won't include those artifacts.

2. Release notes templating

GitHub Releases have no built-in body template, and forge's publisher-github doesn't expose releaseNotes. New tags land with empty bodies unless templatized externally — which means the neat Markdown table currently on v0.0.1 would have to be re-authored by hand each release.

  • New file .github/release-notes/desktop.md — canonical body for desktop releases, with a {{version}} placeholder. Lives in .github/ because it's release-process content, not desktop app source.
  • New step Update release notes from template in .github/workflows/realease-desktop-app.yml. Runs once per release (gated to the macOS matrix row, which is the slowest job and so effectively the "end" of the release). Interpolates {{version}} from desktop/package.json and applies the body via gh release edit.

Test plan

  • CI workflow YAML parses (will surface immediately on push).
  • Editor typecheck clean (downloads.ts changes are interface tightening; no other files import mac_dmg_x64 or mac_dmg_universal per grep).
  • On the next real release, body lands as templated (will need a real workflow run to verify end-to-end).

Summary by CodeRabbit

  • New Features

    • Added Grida Desktop Technical Preview release notes covering nightly releases, platform packaging, supported builds, macOS auto-update cadence, and the “Restart to update” prompt.
    • Release notes for desktop builds are now published automatically when a desktop release is created.
  • Changes

    • macOS downloads and download UI now target Apple Silicon (arm64) only; Intel and Universal options removed.
    • Downloads page now fetches updated release links with caching and a fallback to legacy download info.

Review Change Stack

…elease notes

Two related cleanups now that macOS builds are arm64-only (PR #731):

**1. Downloads page — remove no-longer-built macOS variants.**

- `editor/app/(www)/(downloads)/downloads/downloads.ts`
  - Drop `mac_dmg_x64` and `mac_dmg_universal` from the DownloadLinks
    interface and from `getLinks` / `getLinks_v001`.
  - Drop `"universal"` from the Arch union; tighten the mac distro
    config to arm64 only.
  - Switch the per-platform default for `"mac"` from
    `mac_dmg_universal` → `mac_dmg_arm64`.
- `editor/app/(www)/(downloads)/downloads/page.tsx`
  - Remove the "macOS (Universal)" and "macOS (Intel-based Macs)"
    buttons. Keep "macOS (Apple Silicon)".

The v0.0.1 release still has the legacy universal/x64 dmg assets so
existing direct links keep working; the page just doesn't surface
them. New releases won't include those artifacts.

**2. Release notes templating.**

GitHub Releases have no built-in body template, and forge's
publisher-github doesn't expose `releaseNotes`. New releases land
with an empty body unless we templatize it ourselves.

- New file `.github/release-notes/desktop.md` — the canonical body
  for desktop releases, with a `{{version}}` placeholder. Lives in
  `.github/` because it's release-process content, not desktop app
  source.
- New step `Update release notes from template` in the macOS row of
  the release workflow. After publish creates the tag, the step
  interpolates the template and applies it via `gh release edit`.
  Runs once per release (gated to the macOS matrix row).
@vercel
Copy link
Copy Markdown

vercel Bot commented May 20, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
grida Ready Ready Preview, Comment May 20, 2026 4:09pm
6 Skipped Deployments
Project Deployment Actions Updated (UTC)
code Ignored Ignored May 20, 2026 4:09pm
docs Ignored Ignored Preview May 20, 2026 4:09pm
legacy Ignored Ignored May 20, 2026 4:09pm
backgrounds Skipped Skipped May 20, 2026 4:09pm
blog Skipped Skipped May 20, 2026 4:09pm
viewer Skipped Skipped May 20, 2026 4:09pm

Request Review

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 20, 2026

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 7a387654-6a9b-426d-ae89-b5c2d8e9a51b

📥 Commits

Reviewing files that changed from the base of the PR and between 56a5784 and 9843ce9.

📒 Files selected for processing (1)
  • editor/app/(www)/(downloads)/downloads/downloads.ts

Walkthrough

Aligns desktop downloads to macOS arm64-only: adds release notes and a workflow step, updates the download types and retrieval logic (including memoization), adds a cached page helper, prunes legacy static links, and updates the UI to show only Apple Silicon downloads.

Changes

macOS arm64-only downloads alignment

Layer / File(s) Summary
Release documentation and publication workflow
.github/release-notes/desktop.md, .github/workflows/realease-desktop-app.yml
Desktop technical preview release notes document introduces nightly releases and platform support details, with a new workflow step that renders and publishes these notes to the corresponding GitHub release.
Download data model type contract
editor/app/(www)/(downloads)/downloads/downloads.ts
DownloadLinks removes mac_dmg_x64 and mac_dmg_universal, Arch narrowed to "x64" | "arm64", and macOS distro mapping reduced to only arm64 for the dmg pattern.
Download data retrieval implementation
editor/app/(www)/(downloads)/downloads/downloads.ts
getLinks() and deprecated getLinks_v001() are updated to fetch and return only macOS arm64 assets; static constants/selection pruned and Fetcher.fetch() memoizes release assets.
Cached page helper for links resolution
editor/app/(www)/(downloads)/downloads/downloads.ts
Adds unstable_cache import, defines DownloadLinksForPage, and exports getLinksForPage(os) which wraps getLinks() with hourly revalidation and falls back to getLinks_v001() on failure.
Download UI consumer update
editor/app/(www)/(downloads)/downloads/page.tsx
DownloadsPage now uses getLinksForPage(os) and DownloadButtons renders only the Apple Silicon (arm64) macOS download button, removing Universal and Intel options.

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related PRs

  • gridaco/grida#731: Adjusts the desktop release workflow to publish only macOS arm64 artifacts, complementing this PR's model and UI changes.
🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 33.33% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately summarizes the main changes: dropping unsupported macOS builds (universal/x64) from downloads and adding templated release notes, which are the primary objectives of the PR.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch worktree-downloads-and-release-notes

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 ESLint

If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.

ESLint skipped: no ESLint configuration detected in root package.json. To enable, add eslint to devDependencies.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: deac3c2788

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

- name: Update release notes from template
# Runs once (only on the macOS row) after the release tag has been
# created by the publisher. Template at .github/release-notes/desktop.md.
if: ${{ matrix.os.name == 'macos-apple-silicon' && env.HAS_SIGNING == 'true' && env.HAS_NOTARIZE == 'true' }}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Run release-notes update even when mac signing is unavailable

The new release-notes step is conditioned on env.HAS_SIGNING == 'true' && env.HAS_NOTARIZE == 'true', so if Apple signing/notarization secrets are missing or temporarily unavailable, the Windows/Linux publish steps can still run and publish a release while this templating step is skipped. In that case the workflow reverts to empty/manual release bodies, which defeats the automation introduced here; this step should be gated only to a single matrix row (or another always-running path), not to mac signing availability.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good catch — applied in e207677. Re-gated the step to matrix.os.name == 'linux' (no signing-secret dependency, always runs). The release tag exists by the time linux's publish step finishes, so the body edit is safe.

Copy link
Copy Markdown

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: deac3c2788

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

- name: Update release notes from template
# Runs once (only on the macOS row) after the release tag has been
# created by the publisher. Template at .github/release-notes/desktop.md.
if: ${{ matrix.os.name == 'macos-apple-silicon' && env.HAS_SIGNING == 'true' && env.HAS_NOTARIZE == 'true' }}
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Run release-notes update even when mac signing is unavailable

The new release-notes step is conditioned on env.HAS_SIGNING == 'true' && env.HAS_NOTARIZE == 'true', so if Apple signing/notarization secrets are missing or temporarily unavailable, the Windows/Linux publish steps can still run and publish a release while this templating step is skipped. In that case the workflow reverts to empty/manual release bodies, which defeats the automation introduced here; this step should be gated only to a single matrix row (or another always-running path), not to mac signing availability.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good catch — applied in e207677. Re-gated the step to matrix.os.name == 'linux' (no signing-secret dependency, always runs). The release tag exists by the time linux's publish step finishes, so the body edit is safe. (duplicate thread — same fix applies)

The downloads page was using `getLinks_v001(os)`, which hardcoded every
asset URL to v0.0.1. Every new release would have left the page stuck
on the old version.

- Add `getLinksForPage(os)` that wraps `getLinks()` in Next.js
  `unstable_cache` with a 1h `revalidate`. Hits GitHub's
  unauthenticated /releases/latest endpoint at most once per hour per
  region, well under the 60 req/hr/IP limit. `unstable_cache` only
  memoizes successful resolutions; transient API blips self-heal on
  the next render.
- Add `pickDefault(os, links)` helper that derives the per-OS default
  button target from the dynamic links — mac→arm64, win→x64,
  linux→deb x64.
- Fall back to `getLinks_v001(os)` when the API is unreachable, so a
  GitHub outage doesn't break the page (stale URLs are better than
  no URLs).
- Mark `getLinks_v001` deprecated comment more clearly: static
  fallback only, prefer `getLinksForPage`.
- Switch `page.tsx` to call the new helper.
Two review fixes:

1. Address Codex P2 (gh#732 comments 3275230142 / 3275230335). The
   release-notes update step was gated on
   `env.HAS_SIGNING && env.HAS_NOTARIZE`, which meant that if Apple
   secrets were ever unavailable, linux/windows would still publish
   a release while the notes step silently skipped — defeating the
   automation. Re-gate to the linux row (which has no signing
   dependency and always runs). The release tag exists by the time
   linux's publish step finishes, so we can safely edit its body.

2. Apply oxfmt to the release-notes template — fixes a CI check
   failure on a trailing-space / `*not*` → `_not_` style nit.
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🧹 Nitpick comments (1)
editor/app/(www)/(downloads)/downloads/downloads.ts (1)

176-177: ⚡ Quick win

Add telemetry on fallback path.

The empty catch makes persistent API failures invisible while serving static v0.0.1 links. Add at least a warning/error log before fallback.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@editor/app/`(www)/(downloads)/downloads/downloads.ts around lines 176 - 177,
The empty catch swallowing errors around the dynamic links fetch should be
replaced with telemetry and logging before returning the fallback from
getLinks_v001(os); modify the catch in downloads.ts (the block that currently
does "catch { return getLinks_v001(os); }") to log a warning/error with the
caught error details (e.g., processLogger.warn/error or similar) and emit a
telemetry event/metric indicating the fallback was used (include context like
function name, os, and error.message) and then return getLinks_v001(os).
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@editor/app/`(www)/(downloads)/downloads/downloads.ts:
- Around line 158-160: getCachedLinks wraps getLinks but a cache miss still
triggers multiple GitHub API calls because getLinks calls
getLatestRelease/getAsset per asset; fix by ensuring getLinks only calls
getLatestRelease once and reuses that release data when resolving assets (or
memoize getAsset calls inside getLinks) so a single cache miss results in one
getLatestRelease and then local processing (use Promise.all on assets derived
from the single release object rather than calling getLatestRelease/getAsset
repeatedly). Update code references: unstable_cache(getCachedLinks), function
getLinks, helper getLatestRelease and getAsset to implement single-release fetch
and asset-level reuse/memoization.

---

Nitpick comments:
In `@editor/app/`(www)/(downloads)/downloads/downloads.ts:
- Around line 176-177: The empty catch swallowing errors around the dynamic
links fetch should be replaced with telemetry and logging before returning the
fallback from getLinks_v001(os); modify the catch in downloads.ts (the block
that currently does "catch { return getLinks_v001(os); }") to log a
warning/error with the caught error details (e.g., processLogger.warn/error or
similar) and emit a telemetry event/metric indicating the fallback was used
(include context like function name, os, and error.message) and then return
getLinks_v001(os).
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 23f51cb8-2861-422f-b24f-ba4855008add

📥 Commits

Reviewing files that changed from the base of the PR and between deac3c2 and 7e49c56.

📒 Files selected for processing (2)
  • editor/app/(www)/(downloads)/downloads/downloads.ts
  • editor/app/(www)/(downloads)/downloads/page.tsx

Comment thread editor/app/(www)/(downloads)/downloads/downloads.ts
Address CodeRabbit on PR #732:

1. Fetcher.fetch() was unconditional — each `getAsset` call re-hit the
   GitHub /releases/latest endpoint. With 6 assets to resolve per
   cache miss in getCachedLinks, that was 6 API calls against the
   60/hr/IP unauthenticated limit, not 1. Guard `fetch()` to return
   the cached release if already loaded. Within-render now caps at
   one API call; `unstable_cache` already caps cross-render.

2. The silent `catch { fallback }` masked persistent API failures
   (rate-limit, GitHub outage). Add `console.warn` with the caught
   error so the failure mode is visible in server logs.
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@editor/app/`(www)/(downloads)/downloads/downloads.ts:
- Around line 290-294: The memoization check using this.m_assets still allows
repeated GitHub retries when fetchRelease() fails because this.m_assets stays
null; update getLinks()/the fetchRelease() error path to set this.m_assets to a
stable sentinel (e.g., an empty array or a dedicated failure value) immediately
on failure so subsequent calls short-circuit and do not re-call
getAsset()/GitHub; ensure you only overwrite that sentinel with real assets on a
successful fetch so that getLinks(), getAsset(), and getCachedLinks() find the
memoized value even after errors.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 995a0eea-e11c-4712-86a8-9ca3a78133bd

📥 Commits

Reviewing files that changed from the base of the PR and between 7e49c56 and 56a5784.

📒 Files selected for processing (3)
  • .github/release-notes/desktop.md
  • .github/workflows/realease-desktop-app.yml
  • editor/app/(www)/(downloads)/downloads/downloads.ts
✅ Files skipped from review due to trivial changes (1)
  • .github/release-notes/desktop.md

Comment thread editor/app/(www)/(downloads)/downloads/downloads.ts
…er cache miss

CodeRabbit follow-up: previous commit only memoized successful
fetches. On API failure, m_assets stayed null, so each of the 6
sequential getAsset calls in getLinks() would retry the API — up
to 6 hits per failed cache miss.

Cache the failure as an empty array sentinel. The empty-array path
flows through getAssetsByPlatform's filter → returns [] →
getAsset's assert(length === 1) fails → caught → returns null.
Subsequent getAsset calls see the cached [] and bypass the API
entirely. Net: at most 1 API call per cache miss, regardless of
whether it succeeded.

A fresh Fetcher is created per render (per getLinks call), so the
error cache is per-render and transient failures self-heal on the
next request.
@vercel vercel Bot temporarily deployed to Preview – backgrounds May 20, 2026 16:07 Inactive
@vercel vercel Bot temporarily deployed to Preview – viewer May 20, 2026 16:07 Inactive
@vercel vercel Bot temporarily deployed to Preview – blog May 20, 2026 16:07 Inactive
@softmarshmallow softmarshmallow merged commit 4c7515b into main May 20, 2026
18 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant