@webex/plugin-meetings 3.10.0-next.9 → 3.10.0-webex-services-ready.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/breakouts/breakout.js +1 -1
- package/dist/breakouts/index.js +1 -1
- package/dist/constants.js +11 -3
- package/dist/constants.js.map +1 -1
- package/dist/hashTree/constants.js +20 -0
- package/dist/hashTree/constants.js.map +1 -0
- package/dist/hashTree/hashTree.js +515 -0
- package/dist/hashTree/hashTree.js.map +1 -0
- package/dist/hashTree/hashTreeParser.js +1266 -0
- package/dist/hashTree/hashTreeParser.js.map +1 -0
- package/dist/hashTree/types.js +21 -0
- package/dist/hashTree/types.js.map +1 -0
- package/dist/hashTree/utils.js +48 -0
- package/dist/hashTree/utils.js.map +1 -0
- package/dist/interpretation/index.js +1 -1
- package/dist/interpretation/siLanguage.js +1 -1
- package/dist/locus-info/index.js +511 -48
- package/dist/locus-info/index.js.map +1 -1
- package/dist/locus-info/types.js +7 -0
- package/dist/locus-info/types.js.map +1 -0
- package/dist/meeting/index.js +41 -15
- package/dist/meeting/index.js.map +1 -1
- package/dist/meeting/util.js +1 -0
- package/dist/meeting/util.js.map +1 -1
- package/dist/meetings/index.js +112 -70
- package/dist/meetings/index.js.map +1 -1
- package/dist/metrics/constants.js +3 -1
- package/dist/metrics/constants.js.map +1 -1
- package/dist/reachability/clusterReachability.js +44 -358
- package/dist/reachability/clusterReachability.js.map +1 -1
- package/dist/reachability/reachability.types.js +14 -1
- package/dist/reachability/reachability.types.js.map +1 -1
- package/dist/reachability/reachabilityPeerConnection.js +445 -0
- package/dist/reachability/reachabilityPeerConnection.js.map +1 -0
- package/dist/types/constants.d.ts +26 -21
- package/dist/types/hashTree/constants.d.ts +8 -0
- package/dist/types/hashTree/hashTree.d.ts +129 -0
- package/dist/types/hashTree/hashTreeParser.d.ts +260 -0
- package/dist/types/hashTree/types.d.ts +25 -0
- package/dist/types/hashTree/utils.d.ts +9 -0
- package/dist/types/locus-info/index.d.ts +91 -42
- package/dist/types/locus-info/types.d.ts +46 -0
- package/dist/types/meeting/index.d.ts +22 -9
- package/dist/types/meetings/index.d.ts +9 -2
- package/dist/types/metrics/constants.d.ts +2 -0
- package/dist/types/reachability/clusterReachability.d.ts +10 -88
- package/dist/types/reachability/reachability.types.d.ts +12 -1
- package/dist/types/reachability/reachabilityPeerConnection.d.ts +111 -0
- package/dist/webinar/index.js +1 -1
- package/package.json +22 -21
- package/src/constants.ts +13 -1
- package/src/hashTree/constants.ts +9 -0
- package/src/hashTree/hashTree.ts +463 -0
- package/src/hashTree/hashTreeParser.ts +1161 -0
- package/src/hashTree/types.ts +30 -0
- package/src/hashTree/utils.ts +42 -0
- package/src/locus-info/index.ts +556 -85
- package/src/locus-info/types.ts +48 -0
- package/src/meeting/index.ts +58 -26
- package/src/meeting/util.ts +1 -0
- package/src/meetings/index.ts +104 -51
- package/src/metrics/constants.ts +2 -0
- package/src/reachability/clusterReachability.ts +50 -347
- package/src/reachability/reachability.types.ts +15 -1
- package/src/reachability/reachabilityPeerConnection.ts +416 -0
- package/test/unit/spec/hashTree/hashTree.ts +655 -0
- package/test/unit/spec/hashTree/hashTreeParser.ts +1532 -0
- package/test/unit/spec/hashTree/utils.ts +103 -0
- package/test/unit/spec/locus-info/index.js +667 -1
- package/test/unit/spec/meeting/index.js +91 -20
- package/test/unit/spec/meeting/utils.js +77 -0
- package/test/unit/spec/meetings/index.js +71 -26
- package/test/unit/spec/reachability/clusterReachability.ts +281 -138
|
@@ -1,12 +1,13 @@
|
|
|
1
|
-
import {Defer} from '@webex/common';
|
|
2
|
-
|
|
3
|
-
import LoggerProxy from '../common/logs/logger-proxy';
|
|
4
1
|
import {ClusterNode} from './request';
|
|
5
|
-
import {convertStunUrlToTurn, convertStunUrlToTurnTls} from './util';
|
|
6
2
|
import EventsScope from '../common/events/events-scope';
|
|
7
3
|
|
|
8
|
-
import {
|
|
9
|
-
import {
|
|
4
|
+
import {Enum} from '../constants';
|
|
5
|
+
import {
|
|
6
|
+
ClusterReachabilityResult,
|
|
7
|
+
NatType,
|
|
8
|
+
ReachabilityPeerConnectionEvents,
|
|
9
|
+
} from './reachability.types';
|
|
10
|
+
import {ReachabilityPeerConnection} from './reachabilityPeerConnection';
|
|
10
11
|
|
|
11
12
|
// data for the Events.resultReady event
|
|
12
13
|
export type ResultEventData = {
|
|
@@ -36,17 +37,11 @@ export type Events = Enum<typeof Events>;
|
|
|
36
37
|
|
|
37
38
|
/**
|
|
38
39
|
* A class that handles reachability checks for a single cluster.
|
|
39
|
-
*
|
|
40
|
+
* Creates and orchestrates a ReachabilityPeerConnection instance.
|
|
41
|
+
* Listens to events and emits them to consumers.
|
|
40
42
|
*/
|
|
41
43
|
export class ClusterReachability extends EventsScope {
|
|
42
|
-
private
|
|
43
|
-
private numTcpUrls: number;
|
|
44
|
-
private numXTlsUrls: number;
|
|
45
|
-
private result: ClusterReachabilityResult;
|
|
46
|
-
private pc?: RTCPeerConnection;
|
|
47
|
-
private defer: Defer; // this defer is resolved once reachability checks for this cluster are completed
|
|
48
|
-
private startTimestamp: number;
|
|
49
|
-
private srflxIceCandidates: RTCIceCandidate[] = [];
|
|
44
|
+
private reachabilityPeerConnection: ReachabilityPeerConnection;
|
|
50
45
|
public readonly isVideoMesh: boolean;
|
|
51
46
|
public readonly name;
|
|
52
47
|
public readonly reachedSubnets: Set<string> = new Set();
|
|
@@ -60,374 +55,82 @@ export class ClusterReachability extends EventsScope {
|
|
|
60
55
|
super();
|
|
61
56
|
this.name = name;
|
|
62
57
|
this.isVideoMesh = clusterInfo.isVideoMesh;
|
|
63
|
-
this.numUdpUrls = clusterInfo.udp.length;
|
|
64
|
-
this.numTcpUrls = clusterInfo.tcp.length;
|
|
65
|
-
this.numXTlsUrls = clusterInfo.xtls.length;
|
|
66
|
-
|
|
67
|
-
this.pc = this.createPeerConnection(clusterInfo);
|
|
68
|
-
|
|
69
|
-
this.defer = new Defer();
|
|
70
|
-
this.result = {
|
|
71
|
-
udp: {
|
|
72
|
-
result: 'untested',
|
|
73
|
-
},
|
|
74
|
-
tcp: {
|
|
75
|
-
result: 'untested',
|
|
76
|
-
},
|
|
77
|
-
xtls: {
|
|
78
|
-
result: 'untested',
|
|
79
|
-
},
|
|
80
|
-
};
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
/**
|
|
84
|
-
* Gets total elapsed time, can be called only after start() is called
|
|
85
|
-
* @returns {Number} Milliseconds
|
|
86
|
-
*/
|
|
87
|
-
private getElapsedTime() {
|
|
88
|
-
return Math.round(performance.now() - this.startTimestamp);
|
|
89
|
-
}
|
|
90
|
-
|
|
91
|
-
/**
|
|
92
|
-
* Generate peerConnection config settings
|
|
93
|
-
* @param {ClusterNode} cluster
|
|
94
|
-
* @returns {RTCConfiguration} peerConnectionConfig
|
|
95
|
-
*/
|
|
96
|
-
private buildPeerConnectionConfig(cluster: ClusterNode): RTCConfiguration {
|
|
97
|
-
const udpIceServers = cluster.udp.map((url) => ({
|
|
98
|
-
username: '',
|
|
99
|
-
credential: '',
|
|
100
|
-
urls: [url],
|
|
101
|
-
}));
|
|
102
|
-
|
|
103
|
-
// STUN servers are contacted only using UDP, so in order to test TCP reachability
|
|
104
|
-
// we pretend that Linus is a TURN server, because we can explicitly say "transport=tcp" in TURN urls.
|
|
105
|
-
// We then check for relay candidates to know if TURN-TCP worked (see registerIceCandidateListener()).
|
|
106
|
-
const tcpIceServers = cluster.tcp.map((urlString: string) => {
|
|
107
|
-
return {
|
|
108
|
-
username: 'webexturnreachuser',
|
|
109
|
-
credential: 'webexturnreachpwd',
|
|
110
|
-
urls: [convertStunUrlToTurn(urlString, 'tcp')],
|
|
111
|
-
};
|
|
112
|
-
});
|
|
113
58
|
|
|
114
|
-
|
|
115
|
-
return {
|
|
116
|
-
username: 'webexturnreachuser',
|
|
117
|
-
credential: 'webexturnreachpwd',
|
|
118
|
-
urls: [convertStunUrlToTurnTls(urlString)],
|
|
119
|
-
};
|
|
120
|
-
});
|
|
59
|
+
this.reachabilityPeerConnection = new ReachabilityPeerConnection(name, clusterInfo);
|
|
121
60
|
|
|
122
|
-
|
|
123
|
-
iceServers: [...udpIceServers, ...tcpIceServers, ...turnTlsIceServers],
|
|
124
|
-
iceCandidatePoolSize: 0,
|
|
125
|
-
iceTransportPolicy: 'all',
|
|
126
|
-
};
|
|
61
|
+
this.setupReachabilityPeerConnectionEventListeners();
|
|
127
62
|
}
|
|
128
63
|
|
|
129
64
|
/**
|
|
130
|
-
*
|
|
131
|
-
* @param {ClusterNode} clusterInfo information about the media cluster
|
|
132
|
-
* @returns {RTCPeerConnection} peerConnection
|
|
133
|
-
*/
|
|
134
|
-
private createPeerConnection(clusterInfo: ClusterNode) {
|
|
135
|
-
try {
|
|
136
|
-
const config = this.buildPeerConnectionConfig(clusterInfo);
|
|
137
|
-
|
|
138
|
-
const peerConnection = new RTCPeerConnection(config);
|
|
139
|
-
|
|
140
|
-
return peerConnection;
|
|
141
|
-
} catch (peerConnectionError) {
|
|
142
|
-
LoggerProxy.logger.warn(
|
|
143
|
-
`Reachability:index#createPeerConnection --> Error creating peerConnection:`,
|
|
144
|
-
peerConnectionError
|
|
145
|
-
);
|
|
146
|
-
|
|
147
|
-
return undefined;
|
|
148
|
-
}
|
|
149
|
-
}
|
|
150
|
-
|
|
151
|
-
/**
|
|
152
|
-
* @returns {ClusterReachabilityResult} reachability result for this cluster
|
|
153
|
-
*/
|
|
154
|
-
getResult() {
|
|
155
|
-
return this.result;
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
/**
|
|
159
|
-
* Closes the peerConnection
|
|
160
|
-
*
|
|
161
|
-
* @returns {void}
|
|
162
|
-
*/
|
|
163
|
-
private closePeerConnection() {
|
|
164
|
-
if (this.pc) {
|
|
165
|
-
this.pc.onicecandidate = null;
|
|
166
|
-
this.pc.onicegatheringstatechange = null;
|
|
167
|
-
this.pc.close();
|
|
168
|
-
}
|
|
169
|
-
}
|
|
170
|
-
|
|
171
|
-
/**
|
|
172
|
-
* Resolves the defer, indicating that reachability checks for this cluster are completed
|
|
173
|
-
*
|
|
65
|
+
* Sets up event listeners for the ReachabilityPeerConnection instance
|
|
174
66
|
* @returns {void}
|
|
175
67
|
*/
|
|
176
|
-
private
|
|
177
|
-
this.
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
if (this.pc.connectionState !== CLOSED) {
|
|
189
|
-
this.closePeerConnection();
|
|
190
|
-
this.finishReachabilityCheck();
|
|
191
|
-
}
|
|
192
|
-
}
|
|
193
|
-
|
|
194
|
-
/**
|
|
195
|
-
* Adds public IP (client media IPs)
|
|
196
|
-
* @param {string} protocol
|
|
197
|
-
* @param {string} publicIP
|
|
198
|
-
* @returns {void}
|
|
199
|
-
*/
|
|
200
|
-
private addPublicIP(protocol: 'udp' | 'tcp' | 'xtls', publicIP?: string | null) {
|
|
201
|
-
const result = this.result[protocol];
|
|
202
|
-
|
|
203
|
-
if (publicIP) {
|
|
204
|
-
let ipAdded = false;
|
|
205
|
-
|
|
206
|
-
if (result.clientMediaIPs) {
|
|
207
|
-
if (!result.clientMediaIPs.includes(publicIP)) {
|
|
208
|
-
result.clientMediaIPs.push(publicIP);
|
|
209
|
-
ipAdded = true;
|
|
210
|
-
}
|
|
211
|
-
} else {
|
|
212
|
-
result.clientMediaIPs = [publicIP];
|
|
213
|
-
ipAdded = true;
|
|
214
|
-
}
|
|
68
|
+
private setupReachabilityPeerConnectionEventListeners() {
|
|
69
|
+
this.reachabilityPeerConnection.on(ReachabilityPeerConnectionEvents.resultReady, (data) => {
|
|
70
|
+
this.emit(
|
|
71
|
+
{
|
|
72
|
+
file: 'clusterReachability',
|
|
73
|
+
function: 'setupReachabilityPeerConnectionEventListeners',
|
|
74
|
+
},
|
|
75
|
+
Events.resultReady,
|
|
76
|
+
data
|
|
77
|
+
);
|
|
78
|
+
});
|
|
215
79
|
|
|
216
|
-
|
|
80
|
+
this.reachabilityPeerConnection.on(
|
|
81
|
+
ReachabilityPeerConnectionEvents.clientMediaIpsUpdated,
|
|
82
|
+
(data) => {
|
|
217
83
|
this.emit(
|
|
218
84
|
{
|
|
219
85
|
file: 'clusterReachability',
|
|
220
|
-
function: '
|
|
86
|
+
function: 'setupReachabilityPeerConnectionEventListeners',
|
|
221
87
|
},
|
|
222
88
|
Events.clientMediaIpsUpdated,
|
|
223
|
-
|
|
224
|
-
protocol,
|
|
225
|
-
clientMediaIPs: result.clientMediaIPs,
|
|
226
|
-
}
|
|
89
|
+
data
|
|
227
90
|
);
|
|
228
|
-
}
|
|
229
|
-
}
|
|
230
|
-
|
|
231
|
-
/**
|
|
232
|
-
* Registers a listener for the iceGatheringStateChange event
|
|
233
|
-
*
|
|
234
|
-
* @returns {void}
|
|
235
|
-
*/
|
|
236
|
-
private registerIceGatheringStateChangeListener() {
|
|
237
|
-
this.pc.onicegatheringstatechange = () => {
|
|
238
|
-
if (this.pc.iceGatheringState === ICE_GATHERING_STATE.COMPLETE) {
|
|
239
|
-
this.closePeerConnection();
|
|
240
|
-
this.finishReachabilityCheck();
|
|
241
|
-
}
|
|
242
|
-
};
|
|
243
|
-
}
|
|
244
|
-
|
|
245
|
-
/**
|
|
246
|
-
* Saves the latency in the result for the given protocol and marks it as reachable,
|
|
247
|
-
* emits the "resultReady" event if this is the first result for that protocol,
|
|
248
|
-
* emits the "clientMediaIpsUpdated" event if we already had a result and only found
|
|
249
|
-
* a new client IP
|
|
250
|
-
*
|
|
251
|
-
* @param {string} protocol
|
|
252
|
-
* @param {number} latency
|
|
253
|
-
* @param {string|null} [publicIp]
|
|
254
|
-
* @param {string|null} [serverIp]
|
|
255
|
-
* @returns {void}
|
|
256
|
-
*/
|
|
257
|
-
private saveResult(
|
|
258
|
-
protocol: 'udp' | 'tcp' | 'xtls',
|
|
259
|
-
latency: number,
|
|
260
|
-
publicIp?: string | null,
|
|
261
|
-
serverIp?: string | null
|
|
262
|
-
) {
|
|
263
|
-
const result = this.result[protocol];
|
|
264
|
-
|
|
265
|
-
if (result.latencyInMilliseconds === undefined) {
|
|
266
|
-
LoggerProxy.logger.log(
|
|
267
|
-
// @ts-ignore
|
|
268
|
-
`Reachability:index#saveResult --> Successfully reached ${this.name} over ${protocol}: ${latency}ms`
|
|
269
|
-
);
|
|
270
|
-
result.latencyInMilliseconds = latency;
|
|
271
|
-
result.result = 'reachable';
|
|
272
|
-
if (publicIp) {
|
|
273
|
-
result.clientMediaIPs = [publicIp];
|
|
274
91
|
}
|
|
92
|
+
);
|
|
275
93
|
|
|
94
|
+
this.reachabilityPeerConnection.on(ReachabilityPeerConnectionEvents.natTypeUpdated, (data) => {
|
|
276
95
|
this.emit(
|
|
277
96
|
{
|
|
278
97
|
file: 'clusterReachability',
|
|
279
|
-
function: '
|
|
98
|
+
function: 'setupReachabilityPeerConnectionEventListeners',
|
|
280
99
|
},
|
|
281
|
-
Events.
|
|
282
|
-
|
|
283
|
-
protocol,
|
|
284
|
-
...result,
|
|
285
|
-
}
|
|
100
|
+
Events.natTypeUpdated,
|
|
101
|
+
data
|
|
286
102
|
);
|
|
287
|
-
}
|
|
288
|
-
this.addPublicIP(protocol, publicIp);
|
|
289
|
-
}
|
|
290
|
-
|
|
291
|
-
if (serverIp) {
|
|
292
|
-
this.reachedSubnets.add(serverIp);
|
|
293
|
-
}
|
|
294
|
-
}
|
|
295
|
-
|
|
296
|
-
/**
|
|
297
|
-
* Determines NAT Type.
|
|
298
|
-
*
|
|
299
|
-
* @param {RTCIceCandidate} candidate
|
|
300
|
-
* @returns {void}
|
|
301
|
-
*/
|
|
302
|
-
private determineNatType(candidate: RTCIceCandidate) {
|
|
303
|
-
this.srflxIceCandidates.push(candidate);
|
|
304
|
-
|
|
305
|
-
if (this.srflxIceCandidates.length > 1) {
|
|
306
|
-
const portsFound: Record<string, Set<number>> = {};
|
|
307
|
-
|
|
308
|
-
this.srflxIceCandidates.forEach((c) => {
|
|
309
|
-
const key = `${c.address}:${c.relatedPort}`;
|
|
310
|
-
if (!portsFound[key]) {
|
|
311
|
-
portsFound[key] = new Set();
|
|
312
|
-
}
|
|
313
|
-
portsFound[key].add(c.port);
|
|
314
|
-
});
|
|
103
|
+
});
|
|
315
104
|
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
this.emit(
|
|
320
|
-
{
|
|
321
|
-
file: 'clusterReachability',
|
|
322
|
-
function: 'determineNatType',
|
|
323
|
-
},
|
|
324
|
-
Events.natTypeUpdated,
|
|
325
|
-
{
|
|
326
|
-
natType: NatType.SymmetricNat,
|
|
327
|
-
}
|
|
328
|
-
);
|
|
329
|
-
}
|
|
105
|
+
this.reachabilityPeerConnection.on(ReachabilityPeerConnectionEvents.reachedSubnets, (data) => {
|
|
106
|
+
data.subnets.forEach((subnet) => {
|
|
107
|
+
this.reachedSubnets.add(subnet);
|
|
330
108
|
});
|
|
331
|
-
}
|
|
109
|
+
});
|
|
332
110
|
}
|
|
333
111
|
|
|
334
112
|
/**
|
|
335
|
-
*
|
|
336
|
-
*
|
|
337
|
-
* @returns {void}
|
|
113
|
+
* @returns {ClusterReachabilityResult} reachability result for this cluster
|
|
338
114
|
*/
|
|
339
|
-
|
|
340
|
-
this.
|
|
341
|
-
const TURN_TLS_PORT = 443;
|
|
342
|
-
const CANDIDATE_TYPES = {
|
|
343
|
-
SERVER_REFLEXIVE: 'srflx',
|
|
344
|
-
RELAY: 'relay',
|
|
345
|
-
};
|
|
346
|
-
|
|
347
|
-
const latencyInMilliseconds = this.getElapsedTime();
|
|
348
|
-
|
|
349
|
-
if (e.candidate) {
|
|
350
|
-
if (e.candidate.type === CANDIDATE_TYPES.SERVER_REFLEXIVE) {
|
|
351
|
-
let serverIp = null;
|
|
352
|
-
if ('url' in e.candidate) {
|
|
353
|
-
const stunServerUrlRegex = /stun:([\d.]+):\d+/;
|
|
354
|
-
|
|
355
|
-
const match = (e.candidate as any).url.match(stunServerUrlRegex);
|
|
356
|
-
if (match) {
|
|
357
|
-
// eslint-disable-next-line prefer-destructuring
|
|
358
|
-
serverIp = match[1];
|
|
359
|
-
}
|
|
360
|
-
}
|
|
361
|
-
|
|
362
|
-
this.saveResult('udp', latencyInMilliseconds, e.candidate.address, serverIp);
|
|
363
|
-
|
|
364
|
-
this.determineNatType(e.candidate);
|
|
365
|
-
}
|
|
366
|
-
|
|
367
|
-
if (e.candidate.type === CANDIDATE_TYPES.RELAY) {
|
|
368
|
-
const protocol = e.candidate.port === TURN_TLS_PORT ? 'xtls' : 'tcp';
|
|
369
|
-
this.saveResult(protocol, latencyInMilliseconds, null, e.candidate.address);
|
|
370
|
-
}
|
|
371
|
-
}
|
|
372
|
-
};
|
|
115
|
+
getResult(): ClusterReachabilityResult {
|
|
116
|
+
return this.reachabilityPeerConnection.getResult();
|
|
373
117
|
}
|
|
374
118
|
|
|
375
119
|
/**
|
|
376
|
-
* Starts the process of doing UDP and
|
|
377
|
-
*
|
|
378
|
-
*
|
|
379
|
-
* @returns {Promise}
|
|
120
|
+
* Starts the process of doing UDP, TCP, and XTLS reachability checks on the media cluster.
|
|
121
|
+
* @returns {Promise<ClusterReachabilityResult>}
|
|
380
122
|
*/
|
|
381
123
|
async start(): Promise<ClusterReachabilityResult> {
|
|
382
|
-
|
|
383
|
-
LoggerProxy.logger.warn(
|
|
384
|
-
`Reachability:ClusterReachability#start --> Error: peerConnection is undefined`
|
|
385
|
-
);
|
|
386
|
-
|
|
387
|
-
return this.result;
|
|
388
|
-
}
|
|
389
|
-
|
|
390
|
-
// Initialize this.result as saying that nothing is reachable.
|
|
391
|
-
// It will get updated as we go along and successfully gather ICE candidates.
|
|
392
|
-
this.result.udp = {
|
|
393
|
-
result: this.numUdpUrls > 0 ? 'unreachable' : 'untested',
|
|
394
|
-
};
|
|
395
|
-
this.result.tcp = {
|
|
396
|
-
result: this.numTcpUrls > 0 ? 'unreachable' : 'untested',
|
|
397
|
-
};
|
|
398
|
-
this.result.xtls = {
|
|
399
|
-
result: this.numXTlsUrls > 0 ? 'unreachable' : 'untested',
|
|
400
|
-
};
|
|
401
|
-
|
|
402
|
-
try {
|
|
403
|
-
const offer = await this.pc.createOffer({offerToReceiveAudio: true});
|
|
404
|
-
|
|
405
|
-
this.startTimestamp = performance.now();
|
|
124
|
+
await this.reachabilityPeerConnection.start();
|
|
406
125
|
|
|
407
|
-
|
|
408
|
-
const gatherIceCandidatePromise = this.gatherIceCandidates();
|
|
409
|
-
|
|
410
|
-
// not awaiting the next call on purpose, because we're not sending the offer anywhere and there won't be any answer
|
|
411
|
-
// we just need to make this call to trigger the ICE gathering process
|
|
412
|
-
this.pc.setLocalDescription(offer);
|
|
413
|
-
|
|
414
|
-
await gatherIceCandidatePromise;
|
|
415
|
-
} catch (error) {
|
|
416
|
-
LoggerProxy.logger.warn(`Reachability:ClusterReachability#start --> Error: `, error);
|
|
417
|
-
}
|
|
418
|
-
|
|
419
|
-
return this.result;
|
|
126
|
+
return this.getResult();
|
|
420
127
|
}
|
|
421
128
|
|
|
422
129
|
/**
|
|
423
|
-
*
|
|
424
|
-
*
|
|
425
|
-
* @returns {Promise} promise that's resolved once reachability checks for this cluster are completed or timeout is reached
|
|
130
|
+
* Aborts the cluster reachability checks
|
|
131
|
+
* @returns {void}
|
|
426
132
|
*/
|
|
427
|
-
|
|
428
|
-
this.
|
|
429
|
-
this.registerIceCandidateListener();
|
|
430
|
-
|
|
431
|
-
return this.defer.promise;
|
|
133
|
+
public abort() {
|
|
134
|
+
this.reachabilityPeerConnection.abort();
|
|
432
135
|
}
|
|
433
136
|
}
|
|
@@ -1,4 +1,18 @@
|
|
|
1
|
-
import {IP_VERSION} from '../constants';
|
|
1
|
+
import {IP_VERSION, Enum} from '../constants';
|
|
2
|
+
|
|
3
|
+
export type Protocol = 'udp' | 'tcp' | 'xtls';
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Events emitted by ReachabilityPeerConnection
|
|
7
|
+
*/
|
|
8
|
+
export const ReachabilityPeerConnectionEvents = {
|
|
9
|
+
resultReady: 'resultReady', // emitted when successfully reached over a protocol
|
|
10
|
+
clientMediaIpsUpdated: 'clientMediaIpsUpdated', // emitted when new public IPs are found
|
|
11
|
+
natTypeUpdated: 'natTypeUpdated', // emitted when NAT type is determined
|
|
12
|
+
reachedSubnets: 'reachedSubnets', // emitted when server IP (subnet) is discovered
|
|
13
|
+
} as const;
|
|
14
|
+
|
|
15
|
+
export type ReachabilityPeerConnectionEvents = Enum<typeof ReachabilityPeerConnectionEvents>;
|
|
2
16
|
|
|
3
17
|
// result for a specific transport protocol (like udp or tcp)
|
|
4
18
|
export type TransportResult = {
|