@webex/internal-plugin-mercury 3.8.1-web-workers-keepalive.1 → 3.9.0-multiple-llm.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/mercury.js +321 -132
- package/dist/mercury.js.map +1 -1
- package/dist/socket/socket-base.js +15 -0
- package/dist/socket/socket-base.js.map +1 -1
- package/package.json +18 -18
- package/src/mercury.js +279 -106
- package/src/socket/socket-base.js +13 -0
- package/test/unit/spec/mercury-events.js +20 -2
- package/test/unit/spec/mercury.js +53 -22
package/dist/mercury.js
CHANGED
|
@@ -1,5 +1,9 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
|
|
3
|
+
var _Array$from = require("@babel/runtime-corejs2/core-js/array/from");
|
|
4
|
+
var _Symbol = require("@babel/runtime-corejs2/core-js/symbol");
|
|
5
|
+
var _Symbol$iterator = require("@babel/runtime-corejs2/core-js/symbol/iterator");
|
|
6
|
+
var _Array$isArray = require("@babel/runtime-corejs2/core-js/array/is-array");
|
|
3
7
|
var _Object$keys2 = require("@babel/runtime-corejs2/core-js/object/keys");
|
|
4
8
|
var _Object$getOwnPropertySymbols = require("@babel/runtime-corejs2/core-js/object/get-own-property-symbols");
|
|
5
9
|
var _Object$getOwnPropertyDescriptor2 = require("@babel/runtime-corejs2/core-js/object/get-own-property-descriptor");
|
|
@@ -11,6 +15,7 @@ _Object$defineProperty(exports, "__esModule", {
|
|
|
11
15
|
value: true
|
|
12
16
|
});
|
|
13
17
|
exports.default = void 0;
|
|
18
|
+
var _map = _interopRequireDefault(require("@babel/runtime-corejs2/core-js/map"));
|
|
14
19
|
var _promise = _interopRequireDefault(require("@babel/runtime-corejs2/core-js/promise"));
|
|
15
20
|
var _keys = _interopRequireDefault(require("@babel/runtime-corejs2/core-js/object/keys"));
|
|
16
21
|
var _assign = _interopRequireDefault(require("@babel/runtime-corejs2/core-js/object/assign"));
|
|
@@ -34,10 +39,14 @@ var _dec, _dec2, _obj;
|
|
|
34
39
|
*/
|
|
35
40
|
function ownKeys(e, r) { var t = _Object$keys2(e); if (_Object$getOwnPropertySymbols) { var o = _Object$getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return _Object$getOwnPropertyDescriptor2(e, r).enumerable; })), t.push.apply(t, o); } return t; }
|
|
36
41
|
function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { (0, _defineProperty2.default)(e, r, t[r]); }) : _Object$getOwnPropertyDescriptors ? _Object$defineProperties(e, _Object$getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { _Object$defineProperty(e, r, _Object$getOwnPropertyDescriptor2(t, r)); }); } return e; }
|
|
42
|
+
function _createForOfIteratorHelper(o, allowArrayLike) { var it = typeof _Symbol !== "undefined" && o[_Symbol$iterator] || o["@@iterator"]; if (!it) { if (_Array$isArray(o) || (it = _unsupportedIterableToArray(o)) || allowArrayLike && o && typeof o.length === "number") { if (it) o = it; var i = 0; var F = function F() {}; return { s: F, n: function n() { if (i >= o.length) return { done: true }; return { done: false, value: o[i++] }; }, e: function e(_e) { throw _e; }, f: F }; } throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); } var normalCompletion = true, didErr = false, err; return { s: function s() { it = it.call(o); }, n: function n() { var step = it.next(); normalCompletion = step.done; return step; }, e: function e(_e2) { didErr = true; err = _e2; }, f: function f() { try { if (!normalCompletion && it.return != null) it.return(); } finally { if (didErr) throw err; } } }; }
|
|
43
|
+
function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return _Array$from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
|
|
44
|
+
function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) arr2[i] = arr[i]; return arr2; }
|
|
37
45
|
var normalReconnectReasons = ['idle', 'done (forced)', 'pong not received', 'pong mismatch'];
|
|
38
46
|
var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mercury#listen(): Use Mercury#connect() instead'), _dec2 = (0, _common.deprecated)('Mercury#stopListening(): Use Mercury#disconnect() instead'), (_obj = {
|
|
39
47
|
namespace: 'Mercury',
|
|
40
48
|
lastError: undefined,
|
|
49
|
+
defaultSessionId: 'mercury-default-session',
|
|
41
50
|
session: {
|
|
42
51
|
connected: {
|
|
43
52
|
default: false,
|
|
@@ -51,7 +60,18 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
51
60
|
default: false,
|
|
52
61
|
type: 'boolean'
|
|
53
62
|
},
|
|
54
|
-
|
|
63
|
+
sockets: {
|
|
64
|
+
default: function _default() {
|
|
65
|
+
return new _map.default();
|
|
66
|
+
},
|
|
67
|
+
type: 'object'
|
|
68
|
+
},
|
|
69
|
+
backoffCalls: {
|
|
70
|
+
default: function _default() {
|
|
71
|
+
return new _map.default();
|
|
72
|
+
},
|
|
73
|
+
type: 'object'
|
|
74
|
+
},
|
|
55
75
|
localClusterServiceUrls: 'object',
|
|
56
76
|
mercuryTimeOffset: {
|
|
57
77
|
default: undefined,
|
|
@@ -87,41 +107,159 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
87
107
|
getLastError: function getLastError() {
|
|
88
108
|
return this.lastError;
|
|
89
109
|
},
|
|
110
|
+
/**
|
|
111
|
+
* Get all active socket connections
|
|
112
|
+
* @returns {Map} Map of sessionId to socket instances
|
|
113
|
+
*/
|
|
114
|
+
getSockets: function getSockets() {
|
|
115
|
+
return this.sockets;
|
|
116
|
+
},
|
|
117
|
+
/**
|
|
118
|
+
* Get a specific socket by connection ID
|
|
119
|
+
* @param {string} sessionId - The connection identifier
|
|
120
|
+
* @returns {Socket|undefined} The socket instance or undefined if not found
|
|
121
|
+
*/
|
|
122
|
+
getSocket: function getSocket() {
|
|
123
|
+
var sessionId = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : this.defaultSessionId;
|
|
124
|
+
return this.sockets.get(sessionId);
|
|
125
|
+
},
|
|
126
|
+
/**
|
|
127
|
+
* Check if any sockets are connected
|
|
128
|
+
* @returns {boolean} True if at least one socket is connected
|
|
129
|
+
*/
|
|
130
|
+
hasConnectedSockets: function hasConnectedSockets() {
|
|
131
|
+
var _iterator = _createForOfIteratorHelper(this.sockets.values()),
|
|
132
|
+
_step;
|
|
133
|
+
try {
|
|
134
|
+
for (_iterator.s(); !(_step = _iterator.n()).done;) {
|
|
135
|
+
var socket = _step.value;
|
|
136
|
+
if (socket && socket.connected) {
|
|
137
|
+
return true;
|
|
138
|
+
}
|
|
139
|
+
}
|
|
140
|
+
} catch (err) {
|
|
141
|
+
_iterator.e(err);
|
|
142
|
+
} finally {
|
|
143
|
+
_iterator.f();
|
|
144
|
+
}
|
|
145
|
+
return false;
|
|
146
|
+
},
|
|
147
|
+
/**
|
|
148
|
+
* Check if any sockets are connecting
|
|
149
|
+
* @returns {boolean} True if at least one socket is connected
|
|
150
|
+
*/
|
|
151
|
+
hasConnectingSockets: function hasConnectingSockets() {
|
|
152
|
+
var _iterator2 = _createForOfIteratorHelper(this.sockets.values()),
|
|
153
|
+
_step2;
|
|
154
|
+
try {
|
|
155
|
+
for (_iterator2.s(); !(_step2 = _iterator2.n()).done;) {
|
|
156
|
+
var socket = _step2.value;
|
|
157
|
+
if (socket && socket.connecting) {
|
|
158
|
+
return true;
|
|
159
|
+
}
|
|
160
|
+
}
|
|
161
|
+
} catch (err) {
|
|
162
|
+
_iterator2.e(err);
|
|
163
|
+
} finally {
|
|
164
|
+
_iterator2.f();
|
|
165
|
+
}
|
|
166
|
+
return false;
|
|
167
|
+
},
|
|
168
|
+
// @oneFlight
|
|
90
169
|
connect: function connect(webSocketUrl) {
|
|
91
170
|
var _this2 = this;
|
|
92
|
-
|
|
93
|
-
|
|
171
|
+
var sessionId = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : this.defaultSessionId;
|
|
172
|
+
if (!this._connectPromises) this._connectPromises = new _map.default();
|
|
173
|
+
|
|
174
|
+
// First check if there's already a connection promise for this session
|
|
175
|
+
if (this._connectPromises.has(sessionId)) {
|
|
176
|
+
this.logger.info("".concat(this.namespace, ": connection ").concat(sessionId, " already in progress, returning existing promise"));
|
|
177
|
+
return this._connectPromises.get(sessionId);
|
|
178
|
+
}
|
|
179
|
+
var sessionSocket = this.sockets.get(sessionId);
|
|
180
|
+
if (sessionSocket !== null && sessionSocket !== void 0 && sessionSocket.connected || sessionSocket !== null && sessionSocket !== void 0 && sessionSocket.connecting) {
|
|
181
|
+
this.logger.info("".concat(this.namespace, ": connection ").concat(sessionId, " already connected, will not connect again"));
|
|
94
182
|
return _promise.default.resolve();
|
|
95
183
|
}
|
|
96
184
|
this.connecting = true;
|
|
97
|
-
this.logger.info("".concat(this.namespace, ": starting connection attempt"));
|
|
185
|
+
this.logger.info("".concat(this.namespace, ": starting connection attempt for ").concat(sessionId));
|
|
98
186
|
this.logger.info("".concat(this.namespace, ": debug_mercury_logging stack: "), new Error('debug_mercury_logging').stack);
|
|
99
|
-
|
|
100
|
-
_this2.logger.info("".concat(_this2.namespace, ": connecting"));
|
|
101
|
-
return _this2._connectWithBackoff(webSocketUrl);
|
|
187
|
+
var connectPromise = _promise.default.resolve(this.webex.internal.device.registered || this.webex.internal.device.register()).then(function () {
|
|
188
|
+
_this2.logger.info("".concat(_this2.namespace, ": connecting ").concat(sessionId));
|
|
189
|
+
return _this2._connectWithBackoff(webSocketUrl, sessionId);
|
|
190
|
+
}).finally(function () {
|
|
191
|
+
_this2._connectPromises.delete(sessionId);
|
|
102
192
|
});
|
|
193
|
+
this._connectPromises.set(sessionId, connectPromise);
|
|
194
|
+
return connectPromise;
|
|
103
195
|
},
|
|
104
196
|
logout: function logout() {
|
|
105
197
|
this.logger.info("".concat(this.namespace, ": logout() called"));
|
|
106
198
|
this.logger.info("".concat(this.namespace, ": debug_mercury_logging stack: "), new Error('debug_mercury_logging').stack);
|
|
107
|
-
return this.
|
|
199
|
+
return this.disconnectAll(this.config.beforeLogoutOptionsCloseReason && !normalReconnectReasons.includes(this.config.beforeLogoutOptionsCloseReason) ? {
|
|
108
200
|
code: 3050,
|
|
109
201
|
reason: this.config.beforeLogoutOptionsCloseReason
|
|
110
202
|
} : undefined);
|
|
111
203
|
},
|
|
204
|
+
// @oneFlight
|
|
112
205
|
disconnect: function disconnect(options) {
|
|
113
206
|
var _this3 = this;
|
|
207
|
+
var sessionId = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : this.defaultSessionId;
|
|
114
208
|
return new _promise.default(function (resolve) {
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
_this3.
|
|
209
|
+
var backoffCall = _this3.backoffCalls.get(sessionId);
|
|
210
|
+
if (backoffCall) {
|
|
211
|
+
_this3.logger.info("".concat(_this3.namespace, ": aborting connection ").concat(sessionId));
|
|
212
|
+
backoffCall.abort();
|
|
213
|
+
_this3.backoffCalls.delete(sessionId);
|
|
118
214
|
}
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
215
|
+
|
|
216
|
+
// Clean up any pending connection promises
|
|
217
|
+
if (_this3._connectPromises) {
|
|
218
|
+
_this3._connectPromises.delete(sessionId);
|
|
219
|
+
}
|
|
220
|
+
var sessionSocket = _this3.sockets.get(sessionId);
|
|
221
|
+
var suffix = sessionId === _this3.defaultSessionId ? '' : ":".concat(sessionId);
|
|
222
|
+
if (sessionSocket) {
|
|
223
|
+
sessionSocket.removeAllListeners('message');
|
|
224
|
+
sessionSocket.connecting = false;
|
|
225
|
+
sessionSocket.connected = false;
|
|
226
|
+
_this3.once(sessionId === _this3.defaultSessionId ? 'offline' : "offline".concat(suffix), resolve);
|
|
227
|
+
resolve(sessionSocket.close(options || undefined));
|
|
123
228
|
}
|
|
124
229
|
resolve();
|
|
230
|
+
|
|
231
|
+
// Update overall connected status
|
|
232
|
+
_this3.connected = _this3.hasConnectedSockets();
|
|
233
|
+
});
|
|
234
|
+
},
|
|
235
|
+
/**
|
|
236
|
+
* Disconnect all socket connections
|
|
237
|
+
* @param {object} options - Close options
|
|
238
|
+
* @returns {Promise} Promise that resolves when all connections are closed
|
|
239
|
+
*/
|
|
240
|
+
disconnectAll: function disconnectAll(options) {
|
|
241
|
+
var _this4 = this;
|
|
242
|
+
var disconnectPromises = [];
|
|
243
|
+
var _iterator3 = _createForOfIteratorHelper(this.sockets.keys()),
|
|
244
|
+
_step3;
|
|
245
|
+
try {
|
|
246
|
+
for (_iterator3.s(); !(_step3 = _iterator3.n()).done;) {
|
|
247
|
+
var sessionId = _step3.value;
|
|
248
|
+
disconnectPromises.push(this.disconnect(options, sessionId));
|
|
249
|
+
}
|
|
250
|
+
} catch (err) {
|
|
251
|
+
_iterator3.e(err);
|
|
252
|
+
} finally {
|
|
253
|
+
_iterator3.f();
|
|
254
|
+
}
|
|
255
|
+
return _promise.default.all(disconnectPromises).then(function () {
|
|
256
|
+
_this4.connected = false;
|
|
257
|
+
_this4.sockets.clear();
|
|
258
|
+
_this4.backoffCalls.clear();
|
|
259
|
+
// Clear connection promises to prevent stale promises
|
|
260
|
+
if (_this4._connectPromises) {
|
|
261
|
+
_this4._connectPromises.clear();
|
|
262
|
+
}
|
|
125
263
|
});
|
|
126
264
|
},
|
|
127
265
|
listen: function listen() {
|
|
@@ -145,19 +283,19 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
145
283
|
});
|
|
146
284
|
},
|
|
147
285
|
_prepareUrl: function _prepareUrl(webSocketUrl) {
|
|
148
|
-
var
|
|
286
|
+
var _this5 = this;
|
|
149
287
|
if (!webSocketUrl) {
|
|
150
288
|
webSocketUrl = this.webex.internal.device.webSocketUrl;
|
|
151
289
|
}
|
|
152
290
|
return this.webex.internal.feature.getFeature('developer', 'web-high-availability').then(function (haMessagingEnabled) {
|
|
153
291
|
if (haMessagingEnabled) {
|
|
154
|
-
return
|
|
292
|
+
return _this5.webex.internal.services.convertUrlToPriorityHostUrl(webSocketUrl);
|
|
155
293
|
}
|
|
156
294
|
return webSocketUrl;
|
|
157
295
|
}).then(function (wsUrl) {
|
|
158
296
|
webSocketUrl = wsUrl;
|
|
159
297
|
}).then(function () {
|
|
160
|
-
return
|
|
298
|
+
return _this5.webex.internal.feature.getFeature('developer', 'web-shared-mercury');
|
|
161
299
|
}).then(function (webSharedMercury) {
|
|
162
300
|
webSocketUrl = _url.default.parse(webSocketUrl, true);
|
|
163
301
|
(0, _assign.default)(webSocketUrl.query, {
|
|
@@ -172,104 +310,117 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
172
310
|
});
|
|
173
311
|
(0, _deleteProperty.default)(webSocketUrl.query, 'bufferStates');
|
|
174
312
|
}
|
|
175
|
-
if ((0, _lodash.get)(
|
|
313
|
+
if ((0, _lodash.get)(_this5, 'webex.config.device.ephemeral', false)) {
|
|
176
314
|
webSocketUrl.query.multipleConnections = true;
|
|
177
315
|
}
|
|
178
316
|
webSocketUrl.query.clientTimestamp = (0, _now.default)();
|
|
179
317
|
return _url.default.format(webSocketUrl);
|
|
180
318
|
});
|
|
181
319
|
},
|
|
182
|
-
_attemptConnection: function _attemptConnection(socketUrl, callback) {
|
|
183
|
-
var
|
|
320
|
+
_attemptConnection: function _attemptConnection(socketUrl, sessionId, callback) {
|
|
321
|
+
var _this6 = this;
|
|
184
322
|
var socket = new _socket.default();
|
|
323
|
+
socket.connecting = true;
|
|
185
324
|
var attemptWSUrl;
|
|
325
|
+
var suffix = sessionId === this.defaultSessionId ? '' : ":".concat(sessionId);
|
|
186
326
|
socket.on('close', function () {
|
|
187
|
-
|
|
327
|
+
for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {
|
|
328
|
+
args[_key] = arguments[_key];
|
|
329
|
+
}
|
|
330
|
+
return _this6._onclose.apply(_this6, [sessionId].concat(args));
|
|
188
331
|
});
|
|
189
332
|
socket.on('message', function () {
|
|
190
|
-
|
|
333
|
+
for (var _len2 = arguments.length, args = new Array(_len2), _key2 = 0; _key2 < _len2; _key2++) {
|
|
334
|
+
args[_key2] = arguments[_key2];
|
|
335
|
+
}
|
|
336
|
+
return _this6._onmessage.apply(_this6, [sessionId].concat(args));
|
|
191
337
|
});
|
|
192
338
|
socket.on('pong', function () {
|
|
193
|
-
|
|
339
|
+
for (var _len3 = arguments.length, args = new Array(_len3), _key3 = 0; _key3 < _len3; _key3++) {
|
|
340
|
+
args[_key3] = arguments[_key3];
|
|
341
|
+
}
|
|
342
|
+
return _this6._setTimeOffset.apply(_this6, [sessionId].concat(args));
|
|
194
343
|
});
|
|
195
344
|
socket.on('sequence-mismatch', function () {
|
|
196
|
-
for (var
|
|
197
|
-
args[
|
|
345
|
+
for (var _len4 = arguments.length, args = new Array(_len4), _key4 = 0; _key4 < _len4; _key4++) {
|
|
346
|
+
args[_key4] = arguments[_key4];
|
|
198
347
|
}
|
|
199
|
-
return
|
|
348
|
+
return _this6._emit.apply(_this6, ["sequence-mismatch".concat(suffix)].concat(args));
|
|
200
349
|
});
|
|
201
350
|
socket.on('ping-pong-latency', function () {
|
|
202
|
-
for (var
|
|
203
|
-
args[
|
|
351
|
+
for (var _len5 = arguments.length, args = new Array(_len5), _key5 = 0; _key5 < _len5; _key5++) {
|
|
352
|
+
args[_key5] = arguments[_key5];
|
|
204
353
|
}
|
|
205
|
-
return
|
|
354
|
+
return _this6._emit.apply(_this6, ["ping-pong-latency".concat(suffix)].concat(args));
|
|
206
355
|
});
|
|
207
356
|
_promise.default.all([this._prepareUrl(socketUrl), this.webex.credentials.getUserToken()]).then(function (_ref) {
|
|
208
357
|
var _ref2 = (0, _slicedToArray2.default)(_ref, 2),
|
|
209
358
|
webSocketUrl = _ref2[0],
|
|
210
359
|
token = _ref2[1];
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
360
|
+
var backoffCall = _this6.backoffCalls.get(sessionId);
|
|
361
|
+
if (!backoffCall) {
|
|
362
|
+
var msg = "".concat(_this6.namespace, ": prevent socket open when backoffCall no longer defined for ").concat(sessionId);
|
|
363
|
+
_this6.logger.info(msg);
|
|
214
364
|
return _promise.default.reject(new Error(msg));
|
|
215
365
|
}
|
|
216
366
|
attemptWSUrl = webSocketUrl;
|
|
217
367
|
var options = {
|
|
218
|
-
forceCloseDelay:
|
|
219
|
-
pingInterval:
|
|
220
|
-
pongTimeout:
|
|
368
|
+
forceCloseDelay: _this6.config.forceCloseDelay,
|
|
369
|
+
pingInterval: _this6.config.pingInterval,
|
|
370
|
+
pongTimeout: _this6.config.pongTimeout,
|
|
221
371
|
token: token.toString(),
|
|
222
|
-
trackingId: "".concat(
|
|
223
|
-
logger:
|
|
372
|
+
trackingId: "".concat(_this6.webex.sessionId, "_").concat(sessionId, "_").concat((0, _now.default)()),
|
|
373
|
+
logger: _this6.logger
|
|
224
374
|
};
|
|
225
375
|
|
|
226
376
|
// if the consumer has supplied request options use them
|
|
227
|
-
if (
|
|
228
|
-
|
|
229
|
-
options = _objectSpread(_objectSpread({}, options),
|
|
377
|
+
if (_this6.webex.config.defaultMercuryOptions) {
|
|
378
|
+
_this6.logger.info("".concat(_this6.namespace, ": setting custom options for ").concat(sessionId));
|
|
379
|
+
options = _objectSpread(_objectSpread({}, options), _this6.webex.config.defaultMercuryOptions);
|
|
230
380
|
}
|
|
231
381
|
|
|
232
382
|
// Set the socket before opening it. This allows a disconnect() to close
|
|
233
383
|
// the socket if it is in the process of being opened.
|
|
234
|
-
|
|
235
|
-
|
|
384
|
+
_this6.sockets.set(sessionId, socket);
|
|
385
|
+
_this6.socket = _this6.sockets.get(_this6.defaultSessionId) || socket;
|
|
386
|
+
_this6.logger.info("".concat(_this6.namespace, " connection url for ").concat(sessionId, ": ").concat(webSocketUrl));
|
|
236
387
|
return socket.open(webSocketUrl, options);
|
|
237
388
|
}).then(function () {
|
|
238
|
-
|
|
389
|
+
_this6.logger.info("".concat(_this6.namespace, ": connected to mercury, success, action: connected, sessionId: ").concat(sessionId, ", url: ").concat(attemptWSUrl));
|
|
239
390
|
callback();
|
|
240
|
-
return
|
|
391
|
+
return _this6.webex.internal.feature.getFeature('developer', 'web-high-availability').then(function (haMessagingEnabled) {
|
|
241
392
|
if (haMessagingEnabled) {
|
|
242
|
-
return
|
|
393
|
+
return _this6.webex.internal.device.refresh();
|
|
243
394
|
}
|
|
244
395
|
return _promise.default.resolve();
|
|
245
396
|
});
|
|
246
397
|
}).catch(function (reason) {
|
|
247
|
-
|
|
248
|
-
_this5.lastError = reason; // remember the last error
|
|
398
|
+
_this6.lastError = reason; // remember the last error
|
|
249
399
|
|
|
400
|
+
var backoffCall = _this6.backoffCalls.get(sessionId);
|
|
250
401
|
// Suppress connection errors that appear to be network related. This
|
|
251
402
|
// may end up suppressing metrics during outages, but we might not care
|
|
252
403
|
// (especially since many of our outages happen in a way that client
|
|
253
404
|
// metrics can't be trusted).
|
|
254
|
-
if (reason.code !== 1006 &&
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
retries:
|
|
405
|
+
if (reason.code !== 1006 && backoffCall && (backoffCall === null || backoffCall === void 0 ? void 0 : backoffCall.getNumRetries()) > 0) {
|
|
406
|
+
_this6._emit("connection_failed".concat(suffix), reason, {
|
|
407
|
+
sessionId: sessionId,
|
|
408
|
+
retries: backoffCall === null || backoffCall === void 0 ? void 0 : backoffCall.getNumRetries()
|
|
258
409
|
});
|
|
259
410
|
}
|
|
260
|
-
|
|
411
|
+
_this6.logger.info("".concat(_this6.namespace, ": connection attempt failed for ").concat(sessionId), reason, (backoffCall === null || backoffCall === void 0 ? void 0 : backoffCall.getNumRetries()) === 0 ? reason.stack : '');
|
|
261
412
|
// UnknownResponse is produced by IE for any 4XXX; treated it like a bad
|
|
262
413
|
// web socket url and let WDM handle the token checking
|
|
263
414
|
if (reason instanceof _errors.UnknownResponse) {
|
|
264
|
-
|
|
265
|
-
return
|
|
415
|
+
_this6.logger.info("".concat(_this6.namespace, ": received unknown response code for ").concat(sessionId, ", refreshing device registration"));
|
|
416
|
+
return _this6.webex.internal.device.refresh().then(function () {
|
|
266
417
|
return callback(reason);
|
|
267
418
|
});
|
|
268
419
|
}
|
|
269
420
|
// NotAuthorized implies expired token
|
|
270
421
|
if (reason instanceof _errors.NotAuthorized) {
|
|
271
|
-
|
|
272
|
-
return
|
|
422
|
+
_this6.logger.info("".concat(_this6.namespace, ": received authorization error for ").concat(sessionId, ", reauthorizing"));
|
|
423
|
+
return _this6.webex.credentials.refresh({
|
|
273
424
|
force: true
|
|
274
425
|
}).then(function () {
|
|
275
426
|
return callback(reason);
|
|
@@ -284,15 +435,15 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
284
435
|
// BadRequest implies current credentials are for a Service Account
|
|
285
436
|
// Forbidden implies current user is not entitle for Webex
|
|
286
437
|
if (reason instanceof _errors.BadRequest || reason instanceof _errors.Forbidden) {
|
|
287
|
-
|
|
288
|
-
|
|
438
|
+
_this6.logger.warn("".concat(_this6.namespace, ": received unrecoverable response from mercury for ").concat(sessionId));
|
|
439
|
+
backoffCall === null || backoffCall === void 0 ? void 0 : backoffCall.abort();
|
|
289
440
|
return callback(reason);
|
|
290
441
|
}
|
|
291
442
|
if (reason instanceof _errors.ConnectionError) {
|
|
292
|
-
return
|
|
443
|
+
return _this6.webex.internal.feature.getFeature('developer', 'web-high-availability').then(function (haMessagingEnabled) {
|
|
293
444
|
if (haMessagingEnabled) {
|
|
294
|
-
|
|
295
|
-
return
|
|
445
|
+
_this6.logger.info("".concat(_this6.namespace, ": received a generic connection error for ").concat(sessionId, ", will try to connect to another datacenter. failed, action: 'failed', url: ").concat(attemptWSUrl, " error: ").concat(reason.message));
|
|
446
|
+
return _this6.webex.internal.services.markFailedUrl(attemptWSUrl);
|
|
296
447
|
}
|
|
297
448
|
return null;
|
|
298
449
|
}).then(function () {
|
|
@@ -301,73 +452,96 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
301
452
|
}
|
|
302
453
|
return callback(reason);
|
|
303
454
|
}).catch(function (reason) {
|
|
304
|
-
|
|
455
|
+
_this6.logger.error("".concat(_this6.namespace, ": failed to handle connection failure for ").concat(sessionId), reason);
|
|
305
456
|
callback(reason);
|
|
306
457
|
});
|
|
307
458
|
},
|
|
308
|
-
_connectWithBackoff: function _connectWithBackoff(webSocketUrl) {
|
|
309
|
-
var
|
|
459
|
+
_connectWithBackoff: function _connectWithBackoff(webSocketUrl, sessionId) {
|
|
460
|
+
var _this7 = this;
|
|
310
461
|
return new _promise.default(function (resolve, reject) {
|
|
311
462
|
// eslint gets confused about whether or not call is actually used
|
|
312
463
|
// eslint-disable-next-line prefer-const
|
|
313
464
|
var call;
|
|
314
465
|
var onComplete = function onComplete(err) {
|
|
315
|
-
|
|
316
|
-
|
|
466
|
+
var sid = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : sessionId;
|
|
467
|
+
_this7.backoffCalls.delete(sid);
|
|
317
468
|
if (err) {
|
|
318
|
-
|
|
469
|
+
_this7.logger.info("".concat(_this7.namespace, ": failed to connect ").concat(sid, " after ").concat(call.getNumRetries(), " retries; log statement about next retry was inaccurate; ").concat(err));
|
|
319
470
|
return reject(err);
|
|
320
471
|
}
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
472
|
+
// Update overall connected status
|
|
473
|
+
var sessionSocket = _this7.sockets.get(sid);
|
|
474
|
+
if (sessionSocket) {
|
|
475
|
+
sessionSocket.connecting = false;
|
|
476
|
+
sessionSocket.connected = true;
|
|
477
|
+
}
|
|
478
|
+
// @ts-ignore
|
|
479
|
+
_this7.connecting = _this7.hasConnectingSockets();
|
|
480
|
+
_this7.connected = _this7.hasConnectedSockets();
|
|
481
|
+
_this7.hasEverConnected = true;
|
|
482
|
+
var suffix = sid === _this7.defaultSessionId ? '' : ":".concat(sid);
|
|
483
|
+
_this7._emit("online".concat(suffix), {
|
|
484
|
+
sessionId: sid
|
|
485
|
+
});
|
|
486
|
+
_this7.webex.internal.newMetrics.callDiagnosticMetrics.setMercuryConnectedStatus(true);
|
|
325
487
|
return resolve();
|
|
326
488
|
};
|
|
327
|
-
|
|
328
489
|
// eslint-disable-next-line prefer-reflect
|
|
329
490
|
call = _backoff.default.call(function (callback) {
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
},
|
|
491
|
+
_this7.logger.info("".concat(_this7.namespace, ": executing connection attempt ").concat(call.getNumRetries(), " for ").concat(sessionId));
|
|
492
|
+
_this7._attemptConnection(webSocketUrl, sessionId, callback);
|
|
493
|
+
}, function (err) {
|
|
494
|
+
return onComplete(err, sessionId);
|
|
495
|
+
});
|
|
333
496
|
call.setStrategy(new _backoff.default.ExponentialStrategy({
|
|
334
|
-
initialDelay:
|
|
335
|
-
maxDelay:
|
|
497
|
+
initialDelay: _this7.config.backoffTimeReset,
|
|
498
|
+
maxDelay: _this7.config.backoffTimeMax
|
|
336
499
|
}));
|
|
337
|
-
if (
|
|
338
|
-
call.failAfter(
|
|
339
|
-
} else if (
|
|
340
|
-
call.failAfter(
|
|
500
|
+
if (_this7.config.initialConnectionMaxRetries && !_this7.hasEverConnected) {
|
|
501
|
+
call.failAfter(_this7.config.initialConnectionMaxRetries);
|
|
502
|
+
} else if (_this7.config.maxRetries) {
|
|
503
|
+
call.failAfter(_this7.config.maxRetries);
|
|
341
504
|
}
|
|
505
|
+
|
|
506
|
+
// Store the call BEFORE setting up event handlers to prevent race conditions
|
|
507
|
+
_this7.backoffCalls.set(sessionId, call);
|
|
342
508
|
call.on('abort', function () {
|
|
343
|
-
|
|
344
|
-
reject(new Error(
|
|
509
|
+
_this7.logger.info("".concat(_this7.namespace, ": connection aborted for ").concat(sessionId));
|
|
510
|
+
reject(new Error("Mercury Connection Aborted for ".concat(sessionId)));
|
|
345
511
|
});
|
|
346
512
|
call.on('callback', function (err) {
|
|
347
513
|
if (err) {
|
|
348
514
|
var number = call.getNumRetries();
|
|
349
|
-
var delay = Math.min(call.strategy_.nextBackoffDelay_,
|
|
350
|
-
|
|
515
|
+
var delay = Math.min(call.strategy_.nextBackoffDelay_, _this7.config.backoffTimeMax);
|
|
516
|
+
_this7.logger.info("".concat(_this7.namespace, ": failed to connect ").concat(sessionId, "; attempting retry ").concat(number + 1, " in ").concat(delay, " ms"));
|
|
351
517
|
/* istanbul ignore if */
|
|
352
518
|
if (process.env.NODE_ENV === 'development') {
|
|
353
|
-
|
|
519
|
+
_this7.logger.debug("".concat(_this7.namespace, ": "), err, err.stack);
|
|
354
520
|
}
|
|
355
521
|
return;
|
|
356
522
|
}
|
|
357
|
-
|
|
523
|
+
_this7.logger.info("".concat(_this7.namespace, ": connected ").concat(sessionId));
|
|
358
524
|
});
|
|
359
525
|
call.start();
|
|
360
|
-
_this6.backoffCall = call;
|
|
361
526
|
});
|
|
362
527
|
},
|
|
363
528
|
_emit: function _emit() {
|
|
364
|
-
for (var
|
|
365
|
-
args[
|
|
529
|
+
for (var _len6 = arguments.length, args = new Array(_len6), _key6 = 0; _key6 < _len6; _key6++) {
|
|
530
|
+
args[_key6] = arguments[_key6];
|
|
366
531
|
}
|
|
367
532
|
try {
|
|
368
|
-
|
|
533
|
+
// Validate args before processing
|
|
534
|
+
if (args && args.length > 0) {
|
|
535
|
+
this.trigger.apply(this, args);
|
|
536
|
+
}
|
|
369
537
|
} catch (error) {
|
|
370
|
-
|
|
538
|
+
// Safely handle errors without causing additional issues during cleanup
|
|
539
|
+
try {
|
|
540
|
+
this.logger.error("".concat(this.namespace, ": error occurred in event handler:"), error, ' with args: ', args);
|
|
541
|
+
} catch (logError) {
|
|
542
|
+
// If even logging fails, just ignore to prevent cascading errors during cleanup
|
|
543
|
+
this.logger.error('Mercury _emit error handling failed:', logError);
|
|
544
|
+
}
|
|
371
545
|
}
|
|
372
546
|
},
|
|
373
547
|
_getEventHandlers: function _getEventHandlers(eventType) {
|
|
@@ -388,36 +562,48 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
388
562
|
}
|
|
389
563
|
return handlers;
|
|
390
564
|
},
|
|
391
|
-
_onclose: function _onclose(event) {
|
|
565
|
+
_onclose: function _onclose(sessionId, event) {
|
|
392
566
|
// I don't see any way to avoid the complexity or statement count in here.
|
|
393
567
|
/* eslint complexity: [0] */
|
|
394
568
|
|
|
395
569
|
try {
|
|
570
|
+
var _sessionSocket;
|
|
396
571
|
var reason = event.reason && event.reason.toLowerCase();
|
|
397
|
-
var
|
|
398
|
-
|
|
399
|
-
this.
|
|
400
|
-
|
|
401
|
-
this.
|
|
402
|
-
|
|
572
|
+
var sessionSocket = this.sockets.get(sessionId);
|
|
573
|
+
var socketUrl = (_sessionSocket = sessionSocket) === null || _sessionSocket === void 0 ? void 0 : _sessionSocket.url;
|
|
574
|
+
var suffix = sessionId === this.defaultSessionId ? '' : ":".concat(sessionId);
|
|
575
|
+
event.sessionId = sessionId;
|
|
576
|
+
this.sockets.delete(sessionId);
|
|
577
|
+
if (sessionSocket) {
|
|
578
|
+
sessionSocket.removeAllListeners();
|
|
579
|
+
sessionSocket = null;
|
|
580
|
+
this._emit("offline".concat(suffix), event);
|
|
581
|
+
}
|
|
582
|
+
|
|
583
|
+
// Update overall connected status
|
|
584
|
+
this.connecting = this.hasConnectingSockets();
|
|
585
|
+
this.connected = this.hasConnectedSockets();
|
|
586
|
+
if (!this.connected) {
|
|
587
|
+
this.webex.internal.newMetrics.callDiagnosticMetrics.setMercuryConnectedStatus(false);
|
|
588
|
+
}
|
|
403
589
|
switch (event.code) {
|
|
404
590
|
case 1003:
|
|
405
591
|
// metric: disconnect
|
|
406
|
-
this.logger.info("".concat(this.namespace, ": Mercury service rejected last message; will not reconnect: ").concat(event.reason));
|
|
407
|
-
this._emit(
|
|
592
|
+
this.logger.info("".concat(this.namespace, ": Mercury service rejected last message for ").concat(sessionId, "; will not reconnect: ").concat(event.reason));
|
|
593
|
+
this._emit("offline.permanent".concat(suffix), event);
|
|
408
594
|
break;
|
|
409
595
|
case 4000:
|
|
410
596
|
// metric: disconnect
|
|
411
|
-
this.logger.info("".concat(this.namespace, ": socket replaced; will not reconnect"));
|
|
412
|
-
this._emit(
|
|
597
|
+
this.logger.info("".concat(this.namespace, ": socket ").concat(sessionId, " replaced; will not reconnect"));
|
|
598
|
+
this._emit("offline.replaced".concat(suffix), event);
|
|
413
599
|
break;
|
|
414
600
|
case 1001:
|
|
415
601
|
case 1005:
|
|
416
602
|
case 1006:
|
|
417
603
|
case 1011:
|
|
418
|
-
this.logger.info("".concat(this.namespace, ": socket disconnected; reconnecting"));
|
|
419
|
-
this._emit(
|
|
420
|
-
this._reconnect(socketUrl);
|
|
604
|
+
this.logger.info("".concat(this.namespace, ": socket ").concat(sessionId, " disconnected; reconnecting"));
|
|
605
|
+
this._emit("offline.transient".concat(suffix), event);
|
|
606
|
+
this._reconnect(socketUrl, sessionId);
|
|
421
607
|
// metric: disconnect
|
|
422
608
|
// if (code == 1011 && reason !== ping error) metric: unexpected disconnect
|
|
423
609
|
break;
|
|
@@ -425,32 +611,33 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
425
611
|
case 3050:
|
|
426
612
|
// 3050 indicates logout form of closure, default to old behavior, use config reason defined by consumer to proceed with the permanent block
|
|
427
613
|
if (normalReconnectReasons.includes(reason)) {
|
|
428
|
-
this.logger.info("".concat(this.namespace, ": socket disconnected; reconnecting"));
|
|
429
|
-
this._emit(
|
|
430
|
-
this._reconnect(socketUrl);
|
|
614
|
+
this.logger.info("".concat(this.namespace, ": socket ").concat(sessionId, " disconnected; reconnecting"));
|
|
615
|
+
this._emit("offline.transient".concat(suffix), event);
|
|
616
|
+
this._reconnect(socketUrl, sessionId);
|
|
431
617
|
// metric: disconnect
|
|
432
618
|
// if (reason === done forced) metric: force closure
|
|
433
619
|
} else {
|
|
434
|
-
this.logger.info("".concat(this.namespace, ": socket disconnected; will not reconnect: ").concat(event.reason));
|
|
435
|
-
this._emit(
|
|
620
|
+
this.logger.info("".concat(this.namespace, ": socket ").concat(sessionId, " disconnected; will not reconnect: ").concat(event.reason));
|
|
621
|
+
this._emit("offline.permanent".concat(suffix), event);
|
|
436
622
|
}
|
|
437
623
|
break;
|
|
438
624
|
default:
|
|
439
|
-
this.logger.info("".concat(this.namespace, ": socket disconnected unexpectedly; will not reconnect"));
|
|
625
|
+
this.logger.info("".concat(this.namespace, ": socket ").concat(sessionId, " disconnected unexpectedly; will not reconnect"));
|
|
440
626
|
// unexpected disconnect
|
|
441
|
-
this._emit(
|
|
627
|
+
this._emit("offline.permanent".concat(suffix), event);
|
|
442
628
|
}
|
|
443
629
|
} catch (error) {
|
|
444
|
-
this.logger.error("".concat(this.namespace, ": error occurred in close handler"), error);
|
|
630
|
+
this.logger.error("".concat(this.namespace, ": error occurred in close handler for ").concat(sessionId), error);
|
|
445
631
|
}
|
|
446
632
|
},
|
|
447
|
-
_onmessage: function _onmessage(event) {
|
|
448
|
-
var
|
|
449
|
-
this._setTimeOffset(event);
|
|
633
|
+
_onmessage: function _onmessage(sessionId, event) {
|
|
634
|
+
var _this8 = this;
|
|
635
|
+
this._setTimeOffset(sessionId, event);
|
|
450
636
|
var envelope = event.data;
|
|
451
637
|
if (process.env.ENABLE_MERCURY_LOGGING) {
|
|
452
|
-
this.logger.debug("".concat(this.namespace, ": message envelope: "), envelope);
|
|
638
|
+
this.logger.debug("".concat(this.namespace, ": message envelope from ").concat(sessionId, ": "), envelope);
|
|
453
639
|
}
|
|
640
|
+
envelope.sessionId = sessionId;
|
|
454
641
|
var data = envelope.data;
|
|
455
642
|
this._applyOverrides(data);
|
|
456
643
|
return this._getEventHandlers(data.eventType).reduce(function (promise, handler) {
|
|
@@ -458,37 +645,39 @@ var Mercury = _webexCore.WebexPlugin.extend((_dec = (0, _common.deprecated)('Mer
|
|
|
458
645
|
var namespace = handler.namespace,
|
|
459
646
|
name = handler.name;
|
|
460
647
|
return new _promise.default(function (resolve) {
|
|
461
|
-
return resolve((
|
|
648
|
+
return resolve((_this8.webex[namespace] || _this8.webex.internal[namespace])[name](data));
|
|
462
649
|
}).catch(function (reason) {
|
|
463
|
-
return
|
|
650
|
+
return _this8.logger.error("".concat(_this8.namespace, ": error occurred in autowired event handler for ").concat(data.eventType, " from ").concat(sessionId), reason);
|
|
464
651
|
});
|
|
465
652
|
});
|
|
466
653
|
}, _promise.default.resolve()).then(function () {
|
|
467
|
-
|
|
654
|
+
var suffix = sessionId === _this8.defaultSessionId ? '' : ":".concat(sessionId);
|
|
655
|
+
_this8._emit("event".concat(suffix), envelope);
|
|
468
656
|
var _data$eventType$split = data.eventType.split('.'),
|
|
469
657
|
_data$eventType$split2 = (0, _slicedToArray2.default)(_data$eventType$split, 1),
|
|
470
658
|
namespace = _data$eventType$split2[0];
|
|
471
659
|
if (namespace === data.eventType) {
|
|
472
|
-
|
|
660
|
+
_this8._emit("event:".concat(namespace).concat(suffix), envelope);
|
|
473
661
|
} else {
|
|
474
|
-
|
|
475
|
-
|
|
662
|
+
_this8._emit("event:".concat(namespace).concat(suffix), envelope);
|
|
663
|
+
_this8._emit("event:".concat(data.eventType).concat(suffix), envelope);
|
|
476
664
|
}
|
|
477
665
|
}).catch(function (reason) {
|
|
478
|
-
|
|
666
|
+
_this8.logger.error("".concat(_this8.namespace, ": error occurred processing socket message from ").concat(sessionId), reason);
|
|
479
667
|
});
|
|
480
668
|
},
|
|
481
|
-
_setTimeOffset: function _setTimeOffset(event) {
|
|
669
|
+
_setTimeOffset: function _setTimeOffset(sessionId, event) {
|
|
482
670
|
var wsWriteTimestamp = event.data.wsWriteTimestamp;
|
|
483
671
|
if (typeof wsWriteTimestamp === 'number' && wsWriteTimestamp > 0) {
|
|
484
672
|
this.mercuryTimeOffset = (0, _now.default)() - wsWriteTimestamp;
|
|
485
673
|
}
|
|
486
674
|
},
|
|
487
675
|
_reconnect: function _reconnect(webSocketUrl) {
|
|
488
|
-
|
|
489
|
-
|
|
676
|
+
var sessionId = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : this.defaultSessionId;
|
|
677
|
+
this.logger.info("".concat(this.namespace, ": reconnecting ").concat(sessionId));
|
|
678
|
+
return this.connect(webSocketUrl, sessionId);
|
|
490
679
|
},
|
|
491
|
-
version: "3.
|
|
492
|
-
}, ((0, _applyDecoratedDescriptor2.default)(_obj, "
|
|
493
|
-
var
|
|
680
|
+
version: "3.9.0-multiple-llm.1"
|
|
681
|
+
}, ((0, _applyDecoratedDescriptor2.default)(_obj, "listen", [_dec], (0, _getOwnPropertyDescriptor.default)(_obj, "listen"), _obj), (0, _applyDecoratedDescriptor2.default)(_obj, "stopListening", [_dec2], (0, _getOwnPropertyDescriptor.default)(_obj, "stopListening"), _obj)), _obj)));
|
|
682
|
+
var _default2 = exports.default = Mercury;
|
|
494
683
|
//# sourceMappingURL=mercury.js.map
|