mirror of
https://github.com/amitwh/markdown-converter.git
synced 2026-08-02 18:10:18 +05:30
feat(updater): add UpdaterService wrapping electron-updater lifecycle
This commit is contained in:
@@ -0,0 +1,42 @@
|
|||||||
|
const { EventEmitter } = require('events');
|
||||||
|
const DEBOUNCE_MS = 60_000;
|
||||||
|
|
||||||
|
class UpdaterService extends EventEmitter {
|
||||||
|
constructor(autoUpdater) {
|
||||||
|
super();
|
||||||
|
this.autoUpdater = autoUpdater;
|
||||||
|
this.state = 'idle';
|
||||||
|
this.lastCheckAt = 0;
|
||||||
|
this._wire();
|
||||||
|
}
|
||||||
|
|
||||||
|
_wire() {
|
||||||
|
const au = this.autoUpdater;
|
||||||
|
au.on('checking-for-update', () => this._emit({ state: 'checking' }));
|
||||||
|
au.on('update-available', (info) => this._emit({ state: 'available', version: info.version }));
|
||||||
|
au.on('download-progress', (p) => this._emit({ state: 'downloading', percent: p.percent }));
|
||||||
|
au.on('update-downloaded', (info) => this._emit({ state: 'ready', version: info.version }));
|
||||||
|
au.on('update-not-available', () => this._emit({ state: 'idle' }));
|
||||||
|
au.on('error', (err) => {
|
||||||
|
const code = err && /ENOTFOUND|ETIMEDOUT|ECONNREFUSED/.test(err.message) ? 'NETWORK' : 'UNKNOWN';
|
||||||
|
this._emit({ state: 'error', code });
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
_emit(payload) {
|
||||||
|
this.state = payload.state;
|
||||||
|
this.emit('status', payload);
|
||||||
|
}
|
||||||
|
|
||||||
|
async check() {
|
||||||
|
if (Date.now() - this.lastCheckAt < DEBOUNCE_MS) return;
|
||||||
|
this.lastCheckAt = Date.now();
|
||||||
|
await this.autoUpdater.checkForUpdates();
|
||||||
|
}
|
||||||
|
|
||||||
|
install() {
|
||||||
|
this.autoUpdater.quitAndInstall();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
module.exports = { UpdaterService };
|
||||||
@@ -0,0 +1,60 @@
|
|||||||
|
const EventEmitter = require('events');
|
||||||
|
const { UpdaterService } = require('../../../../src/main/updater/updater-service');
|
||||||
|
|
||||||
|
describe('UpdaterService', () => {
|
||||||
|
let emitter;
|
||||||
|
let mockAutoUpdater;
|
||||||
|
let service;
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
emitter = new EventEmitter();
|
||||||
|
mockAutoUpdater = {
|
||||||
|
on: jest.fn((event, cb) => emitter.on(event, cb)),
|
||||||
|
checkForUpdates: jest.fn(),
|
||||||
|
downloadUpdate: jest.fn(),
|
||||||
|
quitAndInstall: jest.fn(),
|
||||||
|
feedConfig: jest.fn(),
|
||||||
|
};
|
||||||
|
service = new UpdaterService(mockAutoUpdater);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('starts in idle state', () => {
|
||||||
|
expect(service.state).toBe('idle');
|
||||||
|
});
|
||||||
|
|
||||||
|
test('check() emits checking then available on update', async () => {
|
||||||
|
const states = [];
|
||||||
|
service.on('status', (s) => states.push(s));
|
||||||
|
mockAutoUpdater.checkForUpdates.mockImplementation(() => {
|
||||||
|
emitter.emit('checking-for-update');
|
||||||
|
emitter.emit('update-available', { version: '5.0.2' });
|
||||||
|
});
|
||||||
|
await service.check();
|
||||||
|
expect(states).toEqual([
|
||||||
|
{ state: 'checking' },
|
||||||
|
{ state: 'available', version: '5.0.2' },
|
||||||
|
]);
|
||||||
|
});
|
||||||
|
|
||||||
|
test('check() emits error on network failure', async () => {
|
||||||
|
const states = [];
|
||||||
|
service.on('status', (s) => states.push(s));
|
||||||
|
mockAutoUpdater.checkForUpdates.mockImplementation(() => {
|
||||||
|
emitter.emit('checking-for-update');
|
||||||
|
emitter.emit('error', new Error('ENOTFOUND'));
|
||||||
|
});
|
||||||
|
await service.check();
|
||||||
|
expect(states[states.length - 1]).toEqual({ state: 'error', code: 'NETWORK' });
|
||||||
|
});
|
||||||
|
|
||||||
|
test('check() debounces second call within 60s', async () => {
|
||||||
|
service.lastCheckAt = Date.now();
|
||||||
|
await service.check();
|
||||||
|
expect(mockAutoUpdater.checkForUpdates).not.toHaveBeenCalled();
|
||||||
|
});
|
||||||
|
|
||||||
|
test('install() calls quitAndInstall on the autoUpdater', () => {
|
||||||
|
service.install();
|
||||||
|
expect(mockAutoUpdater.quitAndInstall).toHaveBeenCalled();
|
||||||
|
});
|
||||||
|
});
|
||||||
Reference in New Issue
Block a user