diff --git a/frontend/electron/main.js b/frontend/electron/main.js index 51eec73..2480201 100644 --- a/frontend/electron/main.js +++ b/frontend/electron/main.js @@ -745,23 +745,14 @@ function createMenu() { { label: 'Report Issue', click: () => { - shell.openExternal('https://github.com/Logikbug/prompd.app/issues') + shell.openExternal('https://github.com/Prompd/prompd-app/issues') } }, { type: 'separator' }, { label: 'Check for Updates', click: () => { - getAutoUpdater().checkForUpdatesAndNotify() - if (mainWindow) { - dialog.showMessageBox(mainWindow, { - type: 'info', - title: 'Checking for Updates', - message: 'Checking for updates...', - detail: 'You will be notified if an update is available.', - buttons: ['OK'] - }) - } + getAutoUpdater().checkForUpdates() } }, { type: 'separator' }, @@ -825,7 +816,7 @@ app.whenReady().then(() => { // Check for updates on startup (only in production) if (!process.env.ELECTRON_START_URL) { console.log('[Electron] Checking for updates...') - getAutoUpdater().checkForUpdatesAndNotify() + getAutoUpdater().checkForUpdates() } // Initialize GA4 analytics (opt-in, anonymous) @@ -2787,7 +2778,7 @@ ipcMain.handle('app:quit', async () => { app.quit() }) ipcMain.handle('app:checkForUpdates', async () => { try { const updater = getAutoUpdater() - updater.checkForUpdatesAndNotify() + updater.checkForUpdates() } catch (e) { console.warn('[Electron] Auto-updater check failed:', e.message) } diff --git a/frontend/package.json b/frontend/package.json index c84110a..3475526 100644 --- a/frontend/package.json +++ b/frontend/package.json @@ -1,6 +1,6 @@ { "name": "@prompd/app", - "version": "0.5.0-beta.3", + "version": "0.5.0-beta.5", "productName": "Prompd", "description": "AI prompt editor with package-based inheritance", "author": "Prompd LLC", @@ -110,6 +110,7 @@ "category": "Development" }, "nsis": { + "artifactName": "${productName}-Setup-${version}.${ext}", "guid": "app.prompd", "oneClick": false, "allowToChangeInstallationDirectory": true, diff --git a/frontend/public/licenses.json b/frontend/public/licenses.json index cdf36e2..ab875a4 100644 --- a/frontend/public/licenses.json +++ b/frontend/public/licenses.json @@ -154,7 +154,7 @@ "path": "C:\\git\\github\\Prompd\\prompd-app\\frontend\\node_modules\\@prompd\\scheduler\\node_modules\\@pkgjs\\parseargs", "licenseFile": "C:\\git\\github\\Prompd\\prompd-app\\frontend\\node_modules\\@prompd\\scheduler\\node_modules\\@pkgjs\\parseargs\\LICENSE" }, - "@prompd/app@0.5.0-beta.3": { + "@prompd/app@0.5.0-beta.5": { "licenses": "UNLICENSED", "private": true, "publisher": "Prompd LLC", diff --git a/frontend/scripts/afterPack.cjs b/frontend/scripts/afterPack.cjs index cfc96f7..e901ab1 100644 --- a/frontend/scripts/afterPack.cjs +++ b/frontend/scripts/afterPack.cjs @@ -4,7 +4,8 @@ * Runs after the app is packed but BEFORE installers are created. * Tasks: * 1. Verify @prompd/cli is installed from npm - * 2. Embed icon into Windows executable + * 2. Embed icon and product metadata into Windows executable + * (needed because signAndEditExecutable is false — no code signing cert) */ const { execSync } = require('child_process') @@ -93,12 +94,24 @@ module.exports = async function(context) { console.log('[afterPack] Using rcedit:', rceditPath) + const appInfo = context.packager.appInfo + const version = appInfo.version + try { - execSync(`"${rceditPath}" "${exePath}" --set-icon "${iconPath}"`, { - stdio: 'inherit' - }) + // Set icon + execSync(`"${rceditPath}" "${exePath}" --set-icon "${iconPath}"`, { stdio: 'inherit' }) console.log('[afterPack] Icon embedded successfully!') + + // Set product metadata so Task Manager shows "Prompd" instead of "Electron" + execSync(`"${rceditPath}" "${exePath}" --set-version-string "ProductName" "Prompd"`, { stdio: 'inherit' }) + execSync(`"${rceditPath}" "${exePath}" --set-version-string "FileDescription" "Prompd"`, { stdio: 'inherit' }) + execSync(`"${rceditPath}" "${exePath}" --set-version-string "CompanyName" "Prompd LLC"`, { stdio: 'inherit' }) + execSync(`"${rceditPath}" "${exePath}" --set-version-string "LegalCopyright" "Copyright Prompd LLC"`, { stdio: 'inherit' }) + execSync(`"${rceditPath}" "${exePath}" --set-version-string "OriginalFilename" "Prompd.exe"`, { stdio: 'inherit' }) + execSync(`"${rceditPath}" "${exePath}" --set-product-version "${version}"`, { stdio: 'inherit' }) + execSync(`"${rceditPath}" "${exePath}" --set-file-version "${version}"`, { stdio: 'inherit' }) + console.log('[afterPack] Product metadata embedded successfully!') } catch (error) { - console.error('[afterPack] ERROR: Failed to embed icon:', error.message) + console.error('[afterPack] ERROR: Failed to embed exe metadata:', error.message) } } \ No newline at end of file diff --git a/frontend/src/modules/App.tsx b/frontend/src/modules/App.tsx index 2ab2754..c6e4c5b 100644 --- a/frontend/src/modules/App.tsx +++ b/frontend/src/modules/App.tsx @@ -3757,6 +3757,28 @@ version: 1.0.0 } }, []) + // Auto-update notifications via toasts + useEffect(() => { + const api = window.electronAPI + if (!api?.isElectron) return + + const cleanups: (() => void)[] = [] + + cleanups.push(api.onUpdateAvailable((info) => { + addToast(`Version ${info.version} is available and downloading...`, 'update', 10000) + })) + + cleanups.push(api.onUpdateDownloaded((info) => { + addToast(`Version ${info.version} is ready to install`, 'update', 0, { + label: 'Restart & Update', + onClick: () => api.installUpdate(), + }) + })) + + return () => cleanups.forEach(fn => fn()) + }, [addToast]) + + // Add file to content reference field const addToContentField = useCallback((filePath: string, field: 'system' | 'assistant' | 'context' | 'user' | 'response', currentFilePath?: string) => { let pathToInsert = filePath diff --git a/frontend/src/modules/components/TitleBar.tsx b/frontend/src/modules/components/TitleBar.tsx index 04451ea..e10a485 100644 --- a/frontend/src/modules/components/TitleBar.tsx +++ b/frontend/src/modules/components/TitleBar.tsx @@ -149,7 +149,7 @@ function buildMenus(ms: MenuState): MenuDef[] { label: 'Help', items: [ { label: 'Documentation', action: () => api.openExternal('https://prompd.io/docs') }, - { label: 'Report Issue', action: () => api.openExternal('https://github.com/Logikbug/prompd.app/issues') }, + { label: 'Report Issue', action: () => api.openExternal('https://github.com/Prompd/prompd-app/issues') }, { type: 'separator' }, { label: 'Check for Updates', action: () => api.checkForUpdates() }, { type: 'separator' }, diff --git a/frontend/src/modules/components/ToastContainer.tsx b/frontend/src/modules/components/ToastContainer.tsx index 189f365..774879c 100644 --- a/frontend/src/modules/components/ToastContainer.tsx +++ b/frontend/src/modules/components/ToastContainer.tsx @@ -1,5 +1,5 @@ import { useUIStore, selectToasts } from '../../stores/uiStore' -import { X, CheckCircle, AlertCircle, AlertTriangle, Info } from 'lucide-react' +import { X, CheckCircle, AlertCircle, AlertTriangle, Info, Download } from 'lucide-react' /** * Toast notification container - renders all active toasts @@ -20,8 +20,20 @@ export function ToastContainer() { {toast.type === 'error' && } {toast.type === 'warning' && } {toast.type === 'info' && } + {toast.type === 'update' && } {toast.message} + {toast.action && ( + + )}