@@ -11,75 +11,94 @@ let isWindowReady = false;
1111function setupAutoUpdater ( ) {
1212 // Configure auto-updater for proper restart behavior
1313 autoUpdater . autoDownload = false ;
14- autoUpdater . autoInstallOnAppQuit = true ; // Changed to true for proper restart
14+ autoUpdater . autoInstallOnAppQuit = true ;
1515 autoUpdater . allowPrerelease = false ;
1616
17- // Add update-not-available event for better feedback
18- autoUpdater . on ( 'update-not-available' , ( info ) => {
19- console . log ( 'No updates available' ) ;
20- mainWindow ?. webContents . send ( 'update-not-available' ) ;
17+ // Set logger for debug output
18+ autoUpdater . logger = {
19+ info : ( message ) => console . log ( '🔍 AutoUpdater Info:' , message ) ,
20+ warn : ( message ) => console . log ( '⚠️ AutoUpdater Warn:' , message ) ,
21+ error : ( message ) => console . log ( '❌ AutoUpdater Error:' , message ) ,
22+ debug : ( message ) => console . log ( '🐛 AutoUpdater Debug:' , message )
23+ } ;
24+
25+ console . log ( '🔄 Auto-updater configured:' , {
26+ autoDownload : autoUpdater . autoDownload ,
27+ autoInstallOnAppQuit : autoUpdater . autoInstallOnAppQuit ,
28+ allowPrerelease : autoUpdater . allowPrerelease ,
29+ currentVersion : app . getVersion ( )
30+ } ) ;
31+
32+ autoUpdater . on ( 'checking-for-update' , ( ) => {
33+ console . log ( '🔍 Checking for updates...' ) ;
34+ mainWindow ?. webContents . send ( 'checking-for-update' ) ;
2135 } ) ;
2236
2337 autoUpdater . on ( 'update-available' , ( info ) => {
24- console . log ( 'Update available:' , info . version ) ;
25- // Notify renderer that an update is available
38+ console . log ( '✅ Update available:' , info ) ;
2639 mainWindow ?. webContents . send ( 'update-available' , info ) ;
2740
28- // Ask user if they want to download
2941 dialog . showMessageBox ( mainWindow , {
3042 type : 'info' ,
3143 title : 'Update Available' ,
3244 message : `Version ${ info . version } is available! Would you like to download it now?` ,
45+ detail : `Release notes: ${ info . releaseName || 'Bug fixes and improvements' } ` ,
3346 buttons : [ 'Download' , 'Later' ] ,
3447 defaultId : 0 ,
3548 cancelId : 1
3649 } ) . then ( ( result ) => {
3750 if ( result . response === 0 ) {
38- console . log ( 'User chose to download update' ) ;
39- // Notify renderer that download is starting
51+ console . log ( '📥 User chose to download update' ) ;
4052 mainWindow ?. webContents . send ( 'download-started' ) ;
4153 autoUpdater . downloadUpdate ( ) ;
4254 } else {
43- console . log ( 'User chose to download later' ) ;
55+ console . log ( '⏰ User chose to download later' ) ;
4456 }
4557 } ) ;
4658 } ) ;
4759
60+ autoUpdater . on ( 'update-not-available' , ( info ) => {
61+ console . log ( 'ℹ️ No updates available:' , info ) ;
62+ mainWindow ?. webContents . send ( 'update-not-available' , info ) ;
63+ } ) ;
64+
4865 autoUpdater . on ( 'download-progress' , ( progressObj ) => {
49- console . log ( 'Download progress:' , progressObj . percent ) ;
50- // Send progress to renderer
66+ console . log ( '📊 Download progress:' , Math . round ( progressObj . percent ) + '%' ) ;
5167 mainWindow ?. webContents . send ( 'download-progress' , progressObj ) ;
5268 } ) ;
5369
5470 autoUpdater . on ( 'update-downloaded' , ( info ) => {
55- console . log ( 'Update downloaded:' , info . version ) ;
56- // Force a sync to ensure the event is processed
71+ console . log ( '🎉 Update downloaded and ready to install:' , info ) ;
5772 mainWindow ?. webContents . send ( 'update-downloaded' , info ) ;
5873
59- // Show restart dialog immediately
60- dialog . showMessageBox ( mainWindow , {
61- type : 'info' ,
62- title : 'Update Ready' ,
63- message : `Version ${ info . version } has been downloaded and is ready to install. Restart the application to apply the update?` ,
64- buttons : [ 'Restart Now' , 'Later' ] ,
65- defaultId : 0 ,
66- cancelId : 1
67- } ) . then ( ( result ) => {
68- if ( result . response === 0 ) {
69- console . log ( 'User chose to restart, calling quitAndInstall...' ) ;
70- // Use isSilent=false to show install progress, isForceRunAfter=true to restart
71- autoUpdater . quitAndInstall ( false , true ) ;
72- } else {
73- console . log ( 'User chose to restart later' ) ;
74- }
75- } ) ;
74+ // Force sync and show restart dialog
75+ setTimeout ( ( ) => {
76+ dialog . showMessageBox ( mainWindow , {
77+ type : 'info' ,
78+ title : 'Update Ready' ,
79+ message : `Version ${ info . version } has been downloaded and is ready to install.` ,
80+ detail : 'The application will restart to complete the update.' ,
81+ buttons : [ 'Restart Now' , 'Later' ] ,
82+ defaultId : 0 ,
83+ cancelId : 1
84+ } ) . then ( ( result ) => {
85+ if ( result . response === 0 ) {
86+ console . log ( '🔄 User chose to restart, calling quitAndInstall...' ) ;
87+ // isSilent = false (show install progress), isForceRunAfter = true (restart app)
88+ setImmediate ( ( ) => {
89+ autoUpdater . quitAndInstall ( false , true ) ;
90+ } ) ;
91+ } else {
92+ console . log ( '⏰ User chose to restart later' ) ;
93+ }
94+ } ) ;
95+ } , 100 ) ;
7696 } ) ;
7797
7898 autoUpdater . on ( 'error' , ( error ) => {
79- console . error ( 'Auto-updater error:' , error ) ;
99+ console . error ( '❌ Auto-updater error:' , error ) ;
80100 mainWindow ?. webContents . send ( 'update-error' , error . message ) ;
81101
82- // Show error to user
83102 dialog . showMessageBox ( mainWindow , {
84103 type : 'error' ,
85104 title : 'Update Error' ,
@@ -89,27 +108,6 @@ function setupAutoUpdater() {
89108 } ) ;
90109}
91110
92- // Check for updates function
93- function checkForUpdates ( ) {
94- autoUpdater . checkForUpdates ( ) . then ( result => {
95- if ( ! result ?. updateInfo ) {
96- dialog . showMessageBox ( mainWindow , {
97- type : 'info' ,
98- title : 'No Updates' ,
99- message : 'You are running the latest version of Enclosure Pro.' ,
100- buttons : [ 'OK' ]
101- } ) ;
102- }
103- } ) . catch ( error => {
104- dialog . showMessageBox ( mainWindow , {
105- type : 'error' ,
106- title : 'Update Check Failed' ,
107- message : `Failed to check for updates: ${ error . message } ` ,
108- buttons : [ 'OK' ]
109- } ) ;
110- } ) ;
111- }
112-
113111function createWindow ( ) {
114112 const isDevelopment = process . env . NODE_ENV === 'development' ;
115113
@@ -120,7 +118,7 @@ function createWindow() {
120118 preload : path . join ( __dirname , 'preload.js' ) ,
121119 nodeIntegration : false ,
122120 contextIsolation : true ,
123- devTools : isDevelopment ,
121+ devTools : true , // Enabled for production debugging
124122 } ,
125123 title : 'Enclosure Pro' ,
126124 icon : path . join ( __dirname , '../images/EnclosureProIcon.png' ) ,
@@ -135,6 +133,14 @@ function createWindow() {
135133 mainWindow . webContents . openDevTools ( ) ;
136134 }
137135
136+ // Add F12 shortcut to open DevTools (works in production too)
137+ mainWindow . webContents . on ( 'before-input-event' , ( event , input ) => {
138+ if ( input . key === 'F12' ) {
139+ mainWindow . webContents . toggleDevTools ( ) ;
140+ event . preventDefault ( ) ;
141+ }
142+ } ) ;
143+
138144 // Prevent window from closing, let renderer handle it
139145 mainWindow . on ( 'close' , ( e ) => {
140146 e . preventDefault ( ) ;
@@ -146,15 +152,12 @@ function createWindow() {
146152 mainWindow = null ;
147153 } ) ;
148154
149- // Always load from built files (standalone Electron app)
150155 mainWindow . loadFile ( path . join ( __dirname , '../dist/public/index.html' ) ) ;
151156
152- // When window is ready, check if there's a file to open
153157 mainWindow . webContents . once ( 'did-finish-load' , ( ) => {
154158 isWindowReady = true ;
155159
156160 if ( fileToOpen ) {
157- // Give React time to initialize
158161 setTimeout ( ( ) => {
159162 mainWindow . webContents . send ( 'file-open-request' , fileToOpen ) ;
160163 fileToOpen = null ;
@@ -181,12 +184,10 @@ if (!gotTheLock) {
181184 app . quit ( ) ;
182185} else {
183186 app . on ( 'second-instance' , ( event , commandLine , workingDirectory ) => {
184- // Someone tried to run a second instance, focus our window instead
185187 if ( mainWindow ) {
186188 if ( mainWindow . isMinimized ( ) ) mainWindow . restore ( ) ;
187189 mainWindow . focus ( ) ;
188190
189- // Check for file path in command line
190191 const filePath = getFilePathFromArgs ( commandLine ) ;
191192 if ( filePath ) {
192193 if ( isWindowReady ) {
@@ -200,21 +201,20 @@ if (!gotTheLock) {
200201}
201202
202203app . whenReady ( ) . then ( ( ) => {
203- // Check for file path in initial launch (Windows/Linux)
204204 const filePath = getFilePathFromArgs ( process . argv ) ;
205205 if ( filePath ) {
206206 fileToOpen = filePath ;
207207 }
208208
209209 createWindow ( ) ;
210210
211- // Check for updates 5 seconds after app starts with better logging
211+ // Check for updates 5 seconds after app starts
212212 setTimeout ( ( ) => {
213- console . log ( '🔍 Checking for updates...' ) ;
213+ console . log ( '🚀 App started, checking for updates...' ) ;
214214 autoUpdater . checkForUpdates ( ) . then ( result => {
215- console . log ( '✅ Update check completed :' , result ) ;
215+ console . log ( '✅ Initial update check result :' , result ) ;
216216 } ) . catch ( error => {
217- console . error ( '❌ Update check failed:' , error ) ;
217+ console . error ( '❌ Initial update check failed:' , error ) ;
218218 } ) ;
219219 } , 5000 ) ;
220220
@@ -226,23 +226,19 @@ app.whenReady().then(() => {
226226} ) ;
227227
228228app . on ( 'window-all-closed' , ( ) => {
229- // On macOS, quit the app when all windows are closed
230229 app . quit ( ) ;
231230} ) ;
232231
233232// Helper function to extract file path from command line arguments
234233function getFilePathFromArgs ( args ) {
235234 if ( process . platform === 'win32' ) {
236- // On Windows, look for .enc files in all arguments
237235 const potentialFiles = args . slice ( 1 ) . filter ( arg =>
238236 arg . endsWith ( '.enc' ) && ! arg . startsWith ( '--' )
239237 ) ;
240238 return potentialFiles [ 0 ] || null ;
241239 } else if ( process . platform === 'darwin' ) {
242- // macOS - we use the 'open-file' event instead
243240 return null ;
244241 } else {
245- // Linux - look for .enc files in arguments
246242 const fileArg = args . find ( arg => arg . endsWith ( '.enc' ) && ! arg . startsWith ( '-' ) ) ;
247243 return fileArg ;
248244 }
@@ -260,7 +256,6 @@ function getNextVersion(currentVersion) {
260256ipcMain . handle ( 'window:close' , ( ) => {
261257 if ( mainWindow ) {
262258 mainWindow . destroy ( ) ;
263- // After destroying the window, quit the app
264259 app . quit ( ) ;
265260 }
266261} ) ;
@@ -271,23 +266,24 @@ ipcMain.handle('app:get-version', () => {
271266} ) ;
272267
273268ipcMain . handle ( 'app:check-for-updates' , ( ) => {
269+ console . log ( '🔍 Manual update check via IPC' ) ;
274270 return autoUpdater . checkForUpdates ( ) ;
275271} ) ;
276272
277273ipcMain . handle ( 'app:restart-and-update' , ( ) => {
278- console . log ( 'Restarting and updating application...' ) ;
279- autoUpdater . quitAndInstall ( false , true ) ;
274+ console . log ( '🔄 Manual restart and update via IPC' ) ;
275+ setImmediate ( ( ) => {
276+ autoUpdater . quitAndInstall ( false , true ) ;
277+ } ) ;
280278} ) ;
281279
282- // Manual update check with better feedback
283280ipcMain . handle ( 'app:manual-check-updates' , async ( ) => {
284281 try {
285- console . log ( '🔍 Manual update check requested' ) ;
282+ console . log ( '🔍 Manual update check requested via IPC ' ) ;
286283 const result = await autoUpdater . checkForUpdates ( ) ;
287284 console . log ( '✅ Manual update check result:' , result ) ;
288285
289286 if ( ! result ?. updateInfo ) {
290- // No update available
291287 return {
292288 success : true ,
293289 updateAvailable : false ,
@@ -309,7 +305,7 @@ ipcMain.handle('app:manual-check-updates', async () => {
309305 }
310306} ) ;
311307
312- // TEST: Simulate update handler - FIXED WITH DYNAMIC VERSION
308+ // TEST: Simulate update handler
313309ipcMain . handle ( 'test:simulate-update' , ( ) => {
314310 console . log ( '🎭 test:simulate-update IPC handler called' ) ;
315311
@@ -318,13 +314,11 @@ ipcMain.handle('test:simulate-update', () => {
318314
319315 console . log ( `🔧 Simulating update from ${ currentVersion } to ${ nextVersion } ...` ) ;
320316
321- // Simulate update-available event with dynamic version
322317 mainWindow ?. webContents . send ( 'update-available' , {
323318 version : nextVersion ,
324319 releaseDate : new Date ( ) . toISOString ( )
325320 } ) ;
326321
327- // Show the update available dialog
328322 dialog . showMessageBox ( mainWindow , {
329323 type : 'info' ,
330324 title : 'TEST - Update Available' ,
@@ -336,7 +330,6 @@ ipcMain.handle('test:simulate-update', () => {
336330 if ( result . response === 0 ) {
337331 console . log ( '🔧 User chose to download update' ) ;
338332
339- // Simulate download progress
340333 let progress = 0 ;
341334 const interval = setInterval ( ( ) => {
342335 progress += 10 ;
@@ -353,13 +346,11 @@ ipcMain.handle('test:simulate-update', () => {
353346 clearInterval ( interval ) ;
354347 console . log ( '🔧 Download complete, simulating update downloaded' ) ;
355348
356- // Simulate update downloaded
357349 setTimeout ( ( ) => {
358350 mainWindow ?. webContents . send ( 'update-downloaded' , {
359351 version : nextVersion
360352 } ) ;
361353
362- // Show the restart dialog
363354 dialog . showMessageBox ( mainWindow , {
364355 type : 'info' ,
365356 title : 'TEST - Update Ready' ,
@@ -370,7 +361,6 @@ ipcMain.handle('test:simulate-update', () => {
370361 } ) . then ( ( restartResult ) => {
371362 if ( restartResult . response === 0 ) {
372363 console . log ( '🔧 User chose to restart (simulation only - no actual restart)' ) ;
373- // In simulation, we don't actually restart
374364 dialog . showMessageBox ( mainWindow , {
375365 type : 'info' ,
376366 title : 'TEST - Simulation Complete' ,
@@ -381,7 +371,7 @@ ipcMain.handle('test:simulate-update', () => {
381371 } ) ;
382372 } , 1000 ) ;
383373 }
384- } , 300 ) ; // Slower progress for better visibility
374+ } , 300 ) ;
385375 }
386376 } ) ;
387377
@@ -439,7 +429,6 @@ ipcMain.handle('file:read', async (event, { filePath }) => {
439429 }
440430} ) ;
441431
442- // IPC handler for opening files from double-click
443432ipcMain . handle ( 'file:open-external' , async ( event , filePath ) => {
444433 try {
445434 const content = await fs . readFile ( filePath , 'utf8' ) ;
0 commit comments