Stabilize updater check/download flow and remove duplicate auto-download trigger#965
Stabilize updater check/download flow and remove duplicate auto-download trigger#965rabanspiegel wants to merge 7 commits intomainfrom
Conversation
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
Greptile SummaryThis PR stabilizes the updater check/download flow by addressing race conditions and duplicate triggers. The changes deduplicate concurrent update checks using a promise-based lock ( Key improvements:
Confidence Score: 4/5
|
| Filename | Overview |
|---|---|
| src/main/services/AutoUpdateService.ts | Added deduplication for concurrent checks, made download idempotent, prevented state clobbering from transient checking events, and added installing state |
| src/renderer/components/UpdateModal.tsx | Fixed duplicate auto-download by checking backend settings, now treats checking as a valid backend state to reflect, added installing UI state |
| src/renderer/hooks/useUpdater.ts | Added installing state to type union and event handling, improved error handling in install function |
| src/main/preload.ts | Added update:installing event channel to onUpdateEvent listener registration |
| src/renderer/components/UpdateCard.tsx | Added installing state UI rendering and disabled check button during install |
Flowchart
%%{init: {'theme': 'neutral'}}%%
flowchart TD
A[User Opens Update Modal] --> B{Backend State Check}
B -->|checking/downloading/downloaded/installing| C[Apply Backend State]
B -->|available| D[Reflect Available State]
B -->|other| E[Trigger Fresh Check]
E --> F{Check In Flight?}
F -->|Yes| G[Return Existing Promise]
F -->|No| H[Perform Check]
H --> I{Update Available?}
I -->|Yes| J[Set status=available]
I -->|No| K[Set status=idle]
J --> L{Modal Auto-Download Enabled?}
L -->|Backend autoDownload=true| M[Skip Modal Download]
L -->|Backend autoDownload=false| N[Trigger Download]
N --> O{Download Status?}
O -->|downloading/downloaded| P[Return Early - Idempotent]
O -->|checking with availableVersion| Q[Allow Download - Race Fix]
O -->|available| R[Start Download]
R --> S[Update Downloaded]
S --> T[User Clicks Install]
T --> U{Already Installing?}
U -->|Yes| V[Ignore Request]
U -->|No| W[Set status=installing]
W --> X[quitAndInstall]
style Q fill:#90EE90
style P fill:#90EE90
style G fill:#90EE90
style M fill:#90EE90
Last reviewed commit: 9ff91ca
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes and found 1 potential issue.
Bugbot Autofix is OFF. To automatically fix reported issues with Cloud Agents, enable Autofix in the Cursor dashboard.
| }); | ||
|
|
||
| autoUpdater.on('update-not-available', (info: UpdateInfo) => { | ||
| // A stale "not available" result from a concurrent check must not overwrite |
There was a problem hiding this comment.
Missing guard lets update-available clobber installing state
Medium Severity
The update-available handler unconditionally sets status = 'available', while the sibling handlers for checking-for-update, update-not-available, and error all guard against clobbering downloading/downloaded/installing states. If a check was initiated before an install began (e.g., a periodic check whose checkForUpdatesAndNotify was already in flight), the late-arriving update-available event will overwrite the installing state with available, defeating the new single-shot install guard and rollback timer.


Summary
Validation
Closes #966
Note
Medium Risk
Touches the app’s update lifecycle (check/download/install) and IPC-driven state transitions; failures could block updates or leave the UI in an incorrect state, though changes are localized to updater codepaths.
Overview
Improves updater robustness by deduping concurrent update checks and preventing transient
checking/not-available/errorevents from overwriting a knownavailable/downloading/downloaded/installing state, including more controlled user-visible error reporting.Makes update actions more resilient:
downloadUpdate()becomes idempotent and can proceed when an update version is already known even if a check is still running, andquitAndInstall()is single-shot with a timeout guard/rollback plus a newinstallingstatus broadcast from main to renderer.Updates renderer UX to handle
installingacrossuseUpdater,UpdateCard, andUpdateModal, and avoids modal-side duplicate auto-download by first reading backendautoDownloadsettings before triggering its own download behavior.Written by Cursor Bugbot for commit 1c0101f. This will update automatically on new commits. Configure here.