You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
🤖 feat: add stable/nightly Electron update channels (#2430)
## Summary
Adds a user-selectable update channel (Stable / Nightly) to the Mux
Electron app. Users can switch channels from the About dialog; the
choice is persisted in `~/.mux/config.json` and takes effect immediately
at runtime.
## Background
The Electron app currently updates only from official GitHub Releases
("Stable"). This PR adds support for a "Nightly" channel that pulls
pre-release builds published from `main`. This gives users who want
bleeding-edge features an opt-in path without disrupting the default
stable experience.
## Implementation
### Config layer (`src/node/config.ts`)
- New `UpdateChannel` type (`"stable" | "nightly"`) with
`parseUpdateChannel()` validation.
- Persisted in config.json — only non-default values are written (stable
is the default, so the key is omitted when on stable).
### Desktop updater (`src/desktop/updater.ts`)
- `applyChannel()` configures `autoUpdater`: `allowPrerelease`,
`channel`, feed URL `releaseType`.
- `setChannel()` method with state guards (blocks switching during
download/install).
- Transient error filtering (404s, network timeouts) to avoid noisy
errors during manifest propagation.
### oRPC surface (`src/common/orpc/schemas/api.ts`,
`src/node/orpc/router.ts`)
- `update.getChannel` / `update.setChannel` endpoints with Zod-validated
`UpdateChannelSchema`.
### Frontend (`src/browser/components/About/AboutDialog.tsx`)
- Channel picker using standard `ToggleGroup` segmented control
(size="sm", matching other consumers).
- Race condition protection via `channelRequestTokenRef` counter.
- Channel state initialized to `null` until fetched, preventing layout
flicker.
- Local `pendingAction` state gives immediate click feedback (spinner +
disabled) for Check, Download, and Install buttons while waiting for the
backend status stream to catch up.
### Button press feedback (`src/browser/components/ui/button.tsx`)
- Added `active:scale-[0.98]` press animation and `transition-all` so
all buttons give tactile click feedback.
### CI: manifest naming (`scripts/set-package-version.js`)
- Detects prerelease suffix (e.g. `-nightly.N`) and sets
`build.publish.channel` in `package.json` so electron-builder generates
channel-specific manifests (`nightly.yml`, `nightly-mac.yml`) instead of
`latest.yml`.
## Validation
- All static checks pass locally (`make static-check`: typecheck, lint,
fmt, broken links).
- Updater test suite (`src/desktop/updater.test.ts`) covers channel
switching, state guards, and transient error handling.
## Risks
- **macOS code signing**: The manifest naming fix
(set-package-version.js) ensures electron-updater finds the correct
`nightly-mac.yml` manifest. Previously, the build produced
`latest-mac.yml` which caused signature validation failures when the
client expected `nightly-mac.yml`.
---
_Generated with `mux` • Model: `anthropic:claude-opus-4-6` • Thinking:
`xhigh` • Cost: `$26.04`_
<!-- mux-attribution: model=anthropic:claude-opus-4-6 thinking=xhigh
costs=26.04 -->
0 commit comments