(version: string)
| 801 | }; |
| 802 | |
| 803 | const promptInstallUpdate = async (version: string) => { |
| 804 | if (updateDialogOpen) return; |
| 805 | updateDialogOpen = true; |
| 806 | // oxlint-disable-next-line executor/no-try-catch-or-throw -- boundary: dialog wrapper guarantees the open flag clears |
| 807 | try { |
| 808 | const response = await dialog.showMessageBox({ |
| 809 | type: "info", |
| 810 | title: "Update ready", |
| 811 | message: `Executor ${version} is ready to install.`, |
| 812 | detail: "Restart now to apply the update, or keep working — we'll prompt again later.", |
| 813 | buttons: ["Restart now", "Later"], |
| 814 | defaultId: 0, |
| 815 | cancelId: 1, |
| 816 | }); |
| 817 | if (response.response === 0) { |
| 818 | // Stop the sidecar cleanly before Squirrel.Mac swaps the bundle. A |
| 819 | // supervised daemon is left running — it's independent of this bundle. |
| 820 | if (connection) { |
| 821 | await stopConnection(connection); |
| 822 | connection = null; |
| 823 | } |
| 824 | autoUpdater.quitAndInstall(false, true); |
| 825 | } |
| 826 | } finally { |
| 827 | updateDialogOpen = false; |
| 828 | } |
| 829 | }; |
| 830 | |
| 831 | // Re-check periodically so a long-running session picks up releases |
| 832 | // without requiring a quit + relaunch. The boot-time check still runs; |
no test coverage detected