160 lines
4.3 KiB
TypeScript
160 lines
4.3 KiB
TypeScript
// Copyright 2021 Signal Messenger, LLC
|
|
// SPDX-License-Identifier: AGPL-3.0-only
|
|
|
|
import { assert } from 'chai';
|
|
import { EventEmitter } from 'events';
|
|
import * as sinon from 'sinon';
|
|
|
|
import { waitForOnline } from '../../util/waitForOnline';
|
|
|
|
describe('waitForOnline', () => {
|
|
let sandbox: sinon.SinonSandbox;
|
|
|
|
beforeEach(() => {
|
|
sandbox = sinon.createSandbox();
|
|
});
|
|
|
|
afterEach(() => {
|
|
sandbox.restore();
|
|
});
|
|
|
|
function getFakeEmitter(): EventEmitter {
|
|
const result = new EventEmitter();
|
|
sinon.stub(result, 'on');
|
|
sinon.stub(result, 'off');
|
|
return result;
|
|
}
|
|
|
|
it("resolves immediately if you're online", async () => {
|
|
const fakeServer = { isOnline: () => true };
|
|
const fakeEvents = getFakeEmitter();
|
|
|
|
await waitForOnline({ server: fakeServer, events: fakeEvents });
|
|
|
|
sinon.assert.notCalled(fakeEvents.on as sinon.SinonStub);
|
|
sinon.assert.notCalled(fakeEvents.off as sinon.SinonStub);
|
|
});
|
|
|
|
it("if you're offline, resolves as soon as you're online (and cleans up listeners)", async () => {
|
|
const fakeServer = { isOnline: () => false };
|
|
const fakeEvents = getFakeEmitter();
|
|
|
|
(fakeEvents.on as sinon.SinonStub)
|
|
.withArgs('online')
|
|
.callsFake((_eventName: string, callback: () => void) => {
|
|
setTimeout(callback, 0);
|
|
});
|
|
|
|
let done = false;
|
|
const promise = (async () => {
|
|
await waitForOnline({ server: fakeServer, events: fakeEvents });
|
|
done = true;
|
|
})();
|
|
|
|
assert.isFalse(done);
|
|
|
|
await promise;
|
|
|
|
assert.isTrue(done);
|
|
sinon.assert.calledOnce(fakeEvents.on as sinon.SinonStub);
|
|
sinon.assert.calledOnce(fakeEvents.off as sinon.SinonStub);
|
|
});
|
|
|
|
it("resolves immediately if you're online when passed a timeout", async () => {
|
|
const fakeServer = { isOnline: () => true };
|
|
const fakeEvents = getFakeEmitter();
|
|
|
|
await waitForOnline({
|
|
server: fakeServer,
|
|
events: fakeEvents,
|
|
timeout: 1234,
|
|
});
|
|
|
|
sinon.assert.notCalled(fakeEvents.on as sinon.SinonStub);
|
|
sinon.assert.notCalled(fakeEvents.off as sinon.SinonStub);
|
|
});
|
|
|
|
it("resolves immediately if you're online even if passed a timeout of 0", async () => {
|
|
const fakeServer = { isOnline: () => true };
|
|
const fakeEvents = getFakeEmitter();
|
|
|
|
await waitForOnline({ server: fakeServer, events: fakeEvents, timeout: 0 });
|
|
|
|
sinon.assert.notCalled(fakeEvents.on as sinon.SinonStub);
|
|
sinon.assert.notCalled(fakeEvents.off as sinon.SinonStub);
|
|
});
|
|
|
|
it("if you're offline, resolves as soon as you're online if it happens before the timeout", async () => {
|
|
const clock = sandbox.useFakeTimers();
|
|
|
|
const fakeServer = { isOnline: () => false };
|
|
const fakeEvents = getFakeEmitter();
|
|
|
|
(fakeEvents.on as sinon.SinonStub)
|
|
.withArgs('online')
|
|
.callsFake((_eventName: string, callback: () => void) => {
|
|
setTimeout(callback, 1000);
|
|
});
|
|
|
|
let done = false;
|
|
void (async () => {
|
|
await waitForOnline({
|
|
server: fakeServer,
|
|
events: fakeEvents,
|
|
timeout: 9999,
|
|
});
|
|
done = true;
|
|
})();
|
|
|
|
await clock.tickAsync(600);
|
|
assert.isFalse(done);
|
|
|
|
await clock.tickAsync(500);
|
|
|
|
assert.isTrue(done);
|
|
});
|
|
|
|
it('rejects if too much time has passed, and cleans up listeners', async () => {
|
|
const clock = sandbox.useFakeTimers();
|
|
|
|
const fakeServer = { isOnline: () => false };
|
|
const fakeEvents = getFakeEmitter();
|
|
|
|
(fakeEvents.on as sinon.SinonStub)
|
|
.withArgs('online')
|
|
.callsFake((_eventName: string, callback: () => void) => {
|
|
setTimeout(callback, 9999);
|
|
});
|
|
|
|
const promise = waitForOnline({
|
|
server: fakeServer,
|
|
events: fakeEvents,
|
|
timeout: 100,
|
|
});
|
|
|
|
await clock.tickAsync(500);
|
|
|
|
await assert.isRejected(promise);
|
|
|
|
sinon.assert.calledOnce(fakeEvents.off as sinon.SinonStub);
|
|
});
|
|
|
|
it('rejects if offline and passed a timeout of 0', async () => {
|
|
const fakeServer = { isOnline: () => false };
|
|
const fakeEvents = getFakeEmitter();
|
|
|
|
(fakeEvents.on as sinon.SinonStub)
|
|
.withArgs('online')
|
|
.callsFake((_eventName: string, callback: () => void) => {
|
|
setTimeout(callback, 9999);
|
|
});
|
|
|
|
const promise = waitForOnline({
|
|
server: fakeServer,
|
|
events: fakeEvents,
|
|
timeout: 100,
|
|
});
|
|
|
|
await assert.isRejected(promise);
|
|
});
|
|
});
|