1
- import { app } from 'electron' ;
1
+ import { BrowserWindow } from 'electron' ;
2
2
import { autoUpdater , UpdateInfo } from 'electron-updater' ;
3
- import log from 'electron-log' ;
4
3
import path = require( 'path' ) ;
5
4
import { setInterval } from 'timers' ;
6
-
5
+ import Logger , { LoggerWrapper } from '@joplin/utils/Logger' ;
6
+ import type ShimType from '@joplin/lib/shim' ;
7
7
8
8
export enum AutoUpdaterEvents {
9
9
CheckingForUpdate = 'checking-for-update' ,
@@ -24,48 +24,69 @@ export interface AutoUpdaterServiceInterface {
24
24
}
25
25
26
26
export default class AutoUpdaterService implements AutoUpdaterServiceInterface {
27
+ private window_ : BrowserWindow ;
28
+ private logger_ : LoggerWrapper ;
29
+ private initializedShim_ : typeof ShimType ;
30
+ private devMode_ : boolean ;
27
31
private updatePollInterval_ : ReturnType < typeof setInterval > | null = null ;
28
-
29
- public constructor ( ) {
32
+ private enableDevMode = true ; // force the updater to work in "dev" mode
33
+ private enableAutoDownload = false ; // automatically download an update when it is found
34
+ private autoInstallOnAppQuit = false ; // automatically install the downloaded update once the user closes the application
35
+ private includePreReleases_ = false ;
36
+ private allowDowngrade = false ;
37
+
38
+ public constructor ( mainWindow : BrowserWindow , logger : LoggerWrapper , initializedShim : typeof ShimType , devMode : boolean , includePreReleases : boolean ) {
39
+ this . window_ = mainWindow ;
40
+ this . logger_ = logger ;
41
+ this . initializedShim_ = initializedShim ;
42
+ this . devMode_ = devMode ;
43
+ this . includePreReleases_ = includePreReleases ;
30
44
this . configureAutoUpdater ( ) ;
31
45
}
32
46
33
47
public startPeriodicUpdateCheck = ( interval : number = defaultUpdateInterval ) : void => {
34
48
this . stopPeriodicUpdateCheck ( ) ;
35
- this . updatePollInterval_ = setInterval ( ( ) => {
49
+ this . updatePollInterval_ = this . initializedShim_ . setInterval ( ( ) => {
36
50
void this . checkForUpdates ( ) ;
37
51
} , interval ) ;
38
- setTimeout ( this . checkForUpdates , initialUpdateStartup ) ;
52
+ this . initializedShim_ . setTimeout ( this . checkForUpdates , initialUpdateStartup ) ;
39
53
} ;
40
54
41
55
public stopPeriodicUpdateCheck = ( ) : void => {
42
56
if ( this . updatePollInterval_ ) {
43
- clearInterval ( this . updatePollInterval_ ) ;
57
+ this . initializedShim_ . clearInterval ( this . updatePollInterval_ ) ;
44
58
this . updatePollInterval_ = null ;
45
59
}
46
60
} ;
47
61
48
62
public checkForUpdates = async ( ) : Promise < void > => {
49
63
try {
50
- await autoUpdater . checkForUpdates ( ) ; // Use async/await
64
+ if ( this . includePreReleases_ ) {
65
+ // If this is set to true, then it will compare the versions semantically and it will also look at tags, so we need to manually get the latest pre-release
66
+ this . logger_ . info ( 'To be implemented...' ) ;
67
+ } else {
68
+ await autoUpdater . checkForUpdates ( ) ;
69
+ }
51
70
} catch ( error ) {
52
- log . error ( 'Failed to check for updates:' , error ) ;
71
+ this . logger_ . error ( 'Failed to check for updates:' , error ) ;
53
72
if ( error . message . includes ( 'ERR_CONNECTION_REFUSED' ) ) {
54
- log . info ( 'Server is not reachable. Will try again later.' ) ;
73
+ this . logger_ . info ( 'Server is not reachable. Will try again later.' ) ;
55
74
}
56
75
}
57
76
} ;
58
77
59
78
private configureAutoUpdater = ( ) : void => {
60
- autoUpdater . logger = log ;
61
- log . transports . file . level = 'info' ;
62
- if ( this . electronIsDev ( ) ) {
63
- log . info ( 'Development mode: using dev-app-update.yml' ) ;
79
+ autoUpdater . logger = ( this . logger_ ) as Logger ;
80
+ if ( this . devMode_ ) {
81
+ this . logger_ . info ( 'Development mode: using dev-app-update.yml' ) ;
64
82
autoUpdater . updateConfigPath = path . join ( __dirname , 'dev-app-update.yml' ) ;
65
- autoUpdater . forceDevUpdateConfig = true ;
83
+ autoUpdater . forceDevUpdateConfig = this . enableDevMode ;
66
84
}
67
85
68
- autoUpdater . autoDownload = false ;
86
+ autoUpdater . autoDownload = this . enableAutoDownload ;
87
+ autoUpdater . autoInstallOnAppQuit = this . autoInstallOnAppQuit ;
88
+ autoUpdater . allowPrerelease = this . includePreReleases_ ;
89
+ autoUpdater . allowDowngrade = this . allowDowngrade ;
69
90
70
91
autoUpdater . on ( AutoUpdaterEvents . CheckingForUpdate , this . onCheckingForUpdate ) ;
71
92
autoUpdater . on ( AutoUpdaterEvents . UpdateNotAvailable , this . onUpdateNotAvailable ) ;
@@ -75,34 +96,36 @@ export default class AutoUpdaterService implements AutoUpdaterServiceInterface {
75
96
autoUpdater . on ( AutoUpdaterEvents . Error , this . onError ) ;
76
97
} ;
77
98
78
- private electronIsDev = ( ) : boolean => ! app . isPackaged ;
79
-
80
99
private onCheckingForUpdate = ( ) => {
81
- log . info ( 'Checking for update...' ) ;
100
+ this . logger_ . info ( 'Checking for update...' ) ;
82
101
} ;
83
102
84
103
private onUpdateNotAvailable = ( _info : UpdateInfo ) : void => {
85
- log . info ( 'Update not available.' ) ;
104
+ this . logger_ . info ( 'Update not available.' ) ;
86
105
} ;
87
106
88
107
private onUpdateAvailable = ( info : UpdateInfo ) : void => {
89
- log . info ( `Update available: ${ info . version } .` ) ;
108
+ this . logger_ . info ( `Update available: ${ info . version } .` ) ;
90
109
} ;
91
110
92
111
private onDownloadProgress = ( progressObj : { bytesPerSecond : number ; percent : number ; transferred : number ; total : number } ) : void => {
93
- log . info ( `Download progress... ${ progressObj . percent } % completed` ) ;
112
+ this . logger_ . info ( `Download progress... ${ progressObj . percent } % completed` ) ;
94
113
} ;
95
114
96
115
private onUpdateDownloaded = ( info : UpdateInfo ) : void => {
97
- log . info ( 'Update downloaded. It will be installed on restart .' ) ;
116
+ this . logger_ . info ( 'Update downloaded.' ) ;
98
117
void this . promptUserToUpdate ( info ) ;
99
118
} ;
100
119
101
120
private onError = ( error : Error ) : void => {
102
- log . error ( 'Error in auto-updater.' , error ) ;
121
+ this . logger_ . error ( 'Error in auto-updater.' , error ) ;
103
122
} ;
104
123
105
124
private promptUserToUpdate = async ( info : UpdateInfo ) : Promise < void > => {
106
- log . info ( `Update is available: ${ info . version } .` ) ;
125
+ this . window_ . webContents . send ( AutoUpdaterEvents . UpdateDownloaded , info ) ;
126
+ } ;
127
+
128
+ public updateApp = ( ) : void => {
129
+ autoUpdater . quitAndInstall ( false , true ) ;
107
130
} ;
108
131
}
0 commit comments