Skip to content
This repository was archived by the owner on Oct 25, 2024. It is now read-only.

Commit 64e2aaa

Browse files
committed
Refresh reconnection ticket before it expires. (#142)
1 parent 17057c5 commit 64e2aaa

File tree

1 file changed

+51
-10
lines changed

1 file changed

+51
-10
lines changed

src/sdk/conference/signaling.js

Lines changed: 51 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,12 @@
66
import Logger from '../base/logger.js';
77
import * as EventModule from '../base/event.js';
88
import {ConferenceError} from './error.js';
9+
import {Base64} from '../base/base64.js';
910

1011
'use strict';
1112

13+
const reconnectionAttempts = 10;
14+
1215
// eslint-disable-next-line require-jsdoc
1316
function handleResponse(status, data, resolve, reject) {
1417
if (status === 'ok' || status === 'success') {
@@ -20,15 +23,12 @@ function handleResponse(status, data, resolve, reject) {
2023
}
2124
}
2225

23-
const MAX_TRIALS = 5;
2426
/**
2527
* @class SioSignaling
2628
* @classdesc Socket.IO signaling channel for ConferenceClient. It is not recommended to directly access this class.
2729
* @memberof Owt.Conference
2830
* @extends Owt.Base.EventDispatcher
2931
* @constructor
30-
* @param {?Object } sioConfig Configuration for Socket.IO options.
31-
* @see https://socket.io/docs/client-api/#io-url-options
3232
*/
3333
export class SioSignaling extends EventModule.EventDispatcher {
3434
// eslint-disable-next-line require-jsdoc
@@ -38,6 +38,7 @@ export class SioSignaling extends EventModule.EventDispatcher {
3838
this._loggedIn = false;
3939
this._reconnectTimes = 0;
4040
this._reconnectionTicket = null;
41+
this._refreshReconnectionTicket = null;
4142
}
4243

4344
/**
@@ -55,7 +56,7 @@ export class SioSignaling extends EventModule.EventDispatcher {
5556
return new Promise((resolve, reject) => {
5657
const opts = {
5758
'reconnection': true,
58-
'reconnectionAttempts': MAX_TRIALS,
59+
'reconnectionAttempts': reconnectionAttempts,
5960
'force new connection': true,
6061
};
6162
this._socket = io(host, opts);
@@ -74,30 +75,31 @@ export class SioSignaling extends EventModule.EventDispatcher {
7475
this._reconnectTimes++;
7576
});
7677
this._socket.on('reconnect_failed', () => {
77-
if (this._reconnectTimes >= MAX_TRIALS) {
78+
if (this._reconnectTimes >= reconnectionAttempts) {
7879
this.dispatchEvent(new EventModule.OwtEvent('disconnect'));
7980
}
8081
});
8182
this._socket.on('drop', () => {
82-
this._reconnectTimes = MAX_TRIALS;
83+
this._reconnectTimes = reconnectionAttempts;
8384
});
8485
this._socket.on('disconnect', () => {
85-
if (this._reconnectTimes >= MAX_TRIALS) {
86+
this._clearReconnectionTask();
87+
if (this._reconnectTimes >= reconnectionAttempts) {
8688
this._loggedIn = false;
8789
this.dispatchEvent(new EventModule.OwtEvent('disconnect'));
8890
}
8991
});
9092
this._socket.emit('login', loginInfo, (status, data) => {
9193
if (status === 'ok') {
9294
this._loggedIn = true;
93-
this._reconnectionTicket = data.reconnectionTicket;
95+
this._onReconnectionTicket(data.reconnectionTicket);
9496
this._socket.on('connect', () => {
9597
// re-login with reconnection ticket.
9698
this._socket.emit('relogin', this._reconnectionTicket, (status,
9799
data) => {
98100
if (status === 'ok') {
99101
this._reconnectTimes = 0;
100-
this._reconnectionTicket = data;
102+
this._onReconnectionTicket(data);
101103
} else {
102104
this.dispatchEvent(new EventModule.OwtEvent('disconnect'));
103105
}
@@ -125,7 +127,7 @@ export class SioSignaling extends EventModule.EventDispatcher {
125127
return new Promise((resolve, reject) => {
126128
this._socket.emit('logout', (status, data) => {
127129
// Maximize the reconnect times to disable reconnection.
128-
this._reconnectTimes = MAX_TRIALS;
130+
this._reconnectTimes = reconnectionAttempts;
129131
this._socket.disconnect();
130132
handleResponse(status, data, resolve, reject);
131133
});
@@ -149,4 +151,43 @@ export class SioSignaling extends EventModule.EventDispatcher {
149151
});
150152
});
151153
}
154+
155+
/**
156+
* @function _onReconnectionTicket
157+
* @instance
158+
* @desc Parse reconnection ticket and schedule ticket refreshing.
159+
* @memberof Owt.Conference.SioSignaling
160+
* @private.
161+
*/
162+
_onReconnectionTicket(ticketString) {
163+
this._reconnectionTicket = ticketString;
164+
const ticket = JSON.parse(Base64.decodeBase64(ticketString));
165+
// Refresh ticket 1 min or 10 seconds before it expires.
166+
const now = Date.now();
167+
const millisecondsInOneMinute = 60 * 1000;
168+
const millisecondsInTenSeconds = 10 * 1000;
169+
if (ticket.notAfter <= now - millisecondsInTenSeconds) {
170+
Logger.warning('Reconnection ticket expires too soon.');
171+
return;
172+
}
173+
let refreshAfter = ticket.notAfter - now - millisecondsInOneMinute;
174+
if (refreshAfter < 0) {
175+
refreshAfter = ticket.notAfter - now - millisecondsInTenSeconds;
176+
}
177+
this._clearReconnectionTask();
178+
this._refreshReconnectionTicket = setTimeout(() => {
179+
this._socket.emit('refreshReconnectionTicket', (status, data) => {
180+
if (status !== 'ok') {
181+
Logger.warning('Failed to refresh reconnection ticket.');
182+
return;
183+
}
184+
this._onReconnectionTicket(data);
185+
});
186+
}, refreshAfter);
187+
}
188+
189+
_clearReconnectionTask() {
190+
clearTimeout(this._refreshReconnectionTicket);
191+
this._refreshReconnectionTicket = null;
192+
}
152193
}

0 commit comments

Comments
 (0)