oorja 1.11.3 → 2.0.0
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/README.md +14 -52
- package/dist/commands/signout.d.ts +1 -1
- package/dist/commands/signout.js +4 -4
- package/dist/commands/teletype/index.d.ts +7 -6
- package/dist/commands/teletype/index.js +49 -47
- package/dist/lib/config.d.ts +7 -10
- package/dist/lib/config.js +29 -49
- package/dist/lib/{surya → connect}/index.d.ts +8 -8
- package/dist/lib/{surya → connect}/index.js +39 -36
- package/dist/lib/{surya → connect}/resources.js +2 -2
- package/dist/lib/{surya → connect}/types.d.ts +1 -3
- package/dist/lib/encryption.d.ts +2 -3
- package/dist/lib/encryption.js +6 -10
- package/dist/lib/oorja/client.d.ts +3 -0
- package/dist/lib/oorja/client.js +52 -0
- package/dist/lib/oorja/index.d.ts +7 -7
- package/dist/lib/oorja/index.js +40 -29
- package/dist/lib/oorja/preflight.d.ts +8 -8
- package/dist/lib/oorja/preflight.js +45 -41
- package/dist/lib/teletype/auxiliary.d.ts +2 -2
- package/dist/lib/teletype/auxiliary.js +5 -5
- package/dist/lib/teletype/index.d.ts +3 -4
- package/dist/lib/teletype/index.js +16 -16
- package/dist/lib/utils.js +5 -5
- package/oclif.manifest.json +11 -10
- package/package.json +22 -18
- package/dist/lib/surya/vendor/phoenix/ajax.d.ts +0 -8
- package/dist/lib/surya/vendor/phoenix/ajax.js +0 -82
- package/dist/lib/surya/vendor/phoenix/channel.d.ts +0 -154
- package/dist/lib/surya/vendor/phoenix/channel.js +0 -308
- package/dist/lib/surya/vendor/phoenix/constants.d.ts +0 -33
- package/dist/lib/surya/vendor/phoenix/constants.js +0 -29
- package/dist/lib/surya/vendor/phoenix/index.d.ts +0 -199
- package/dist/lib/surya/vendor/phoenix/index.js +0 -200
- package/dist/lib/surya/vendor/phoenix/longpoll.d.ts +0 -12
- package/dist/lib/surya/vendor/phoenix/longpoll.js +0 -126
- package/dist/lib/surya/vendor/phoenix/presence.d.ts +0 -44
- package/dist/lib/surya/vendor/phoenix/presence.js +0 -152
- package/dist/lib/surya/vendor/phoenix/push.d.ts +0 -57
- package/dist/lib/surya/vendor/phoenix/push.js +0 -122
- package/dist/lib/surya/vendor/phoenix/serializer.d.ts +0 -53
- package/dist/lib/surya/vendor/phoenix/serializer.js +0 -100
- package/dist/lib/surya/vendor/phoenix/socket.d.ts +0 -222
- package/dist/lib/surya/vendor/phoenix/socket.js +0 -541
- package/dist/lib/surya/vendor/phoenix/timer.d.ts +0 -25
- package/dist/lib/surya/vendor/phoenix/timer.js +0 -40
- package/dist/lib/surya/vendor/phoenix/utils.d.ts +0 -1
- package/dist/lib/surya/vendor/phoenix/utils.js +0 -11
- /package/dist/lib/{surya → connect}/errors.d.ts +0 -0
- /package/dist/lib/{surya → connect}/errors.js +0 -0
- /package/dist/lib/{surya → connect}/resources.d.ts +0 -0
- /package/dist/lib/{surya → connect}/types.js +0 -0
|
@@ -1,541 +0,0 @@
|
|
|
1
|
-
// @ts-nocheck
|
|
2
|
-
import { phxWindow, CHANNEL_EVENTS, DEFAULT_TIMEOUT, DEFAULT_VSN, SOCKET_STATES, TRANSPORTS, WS_CLOSE_NORMAL } from "./constants.js";
|
|
3
|
-
import { closure } from "./utils.js";
|
|
4
|
-
import Ajax from "./ajax.js";
|
|
5
|
-
import Channel from "./channel.js";
|
|
6
|
-
import LongPoll from "./longpoll.js";
|
|
7
|
-
import Serializer from "./serializer.js";
|
|
8
|
-
import Timer from "./timer.js";
|
|
9
|
-
import { WebSocket } from 'ws';
|
|
10
|
-
/** Initializes the Socket *
|
|
11
|
-
*
|
|
12
|
-
* For IE8 support use an ES5-shim (https://github.com/es-shims/es5-shim)
|
|
13
|
-
*
|
|
14
|
-
* @param {string} endPoint - The string WebSocket endpoint, ie, `"ws://example.com/socket"`,
|
|
15
|
-
* `"wss://example.com"`
|
|
16
|
-
* `"/socket"` (inherited host & protocol)
|
|
17
|
-
* @param {Object} [opts] - Optional configuration
|
|
18
|
-
* @param {Function} [opts.transport] - The Websocket Transport, for example WebSocket or Phoenix.LongPoll.
|
|
19
|
-
*
|
|
20
|
-
* Defaults to WebSocket with automatic LongPoll fallback.
|
|
21
|
-
* @param {Function} [opts.encode] - The function to encode outgoing messages.
|
|
22
|
-
*
|
|
23
|
-
* Defaults to JSON encoder.
|
|
24
|
-
*
|
|
25
|
-
* @param {Function} [opts.decode] - The function to decode incoming messages.
|
|
26
|
-
*
|
|
27
|
-
* Defaults to JSON:
|
|
28
|
-
*
|
|
29
|
-
* ```javascript
|
|
30
|
-
* (payload, callback) => callback(JSON.parse(payload))
|
|
31
|
-
* ```
|
|
32
|
-
*
|
|
33
|
-
* @param {number} [opts.timeout] - The default timeout in milliseconds to trigger push timeouts.
|
|
34
|
-
*
|
|
35
|
-
* Defaults `DEFAULT_TIMEOUT`
|
|
36
|
-
* @param {number} [opts.heartbeatIntervalMs] - The millisec interval to send a heartbeat message
|
|
37
|
-
* @param {number} [opts.reconnectAfterMs] - The optional function that returns the millisec
|
|
38
|
-
* socket reconnect interval.
|
|
39
|
-
*
|
|
40
|
-
* Defaults to stepped backoff of:
|
|
41
|
-
*
|
|
42
|
-
* ```javascript
|
|
43
|
-
* function(tries){
|
|
44
|
-
* return [10, 50, 100, 150, 200, 250, 500, 1000, 2000][tries - 1] || 5000
|
|
45
|
-
* }
|
|
46
|
-
* ````
|
|
47
|
-
*
|
|
48
|
-
* @param {number} [opts.rejoinAfterMs] - The optional function that returns the millisec
|
|
49
|
-
* rejoin interval for individual channels.
|
|
50
|
-
*
|
|
51
|
-
* ```javascript
|
|
52
|
-
* function(tries){
|
|
53
|
-
* return [1000, 2000, 5000][tries - 1] || 10000
|
|
54
|
-
* }
|
|
55
|
-
* ````
|
|
56
|
-
*
|
|
57
|
-
* @param {Function} [opts.logger] - The optional function for specialized logging, ie:
|
|
58
|
-
*
|
|
59
|
-
* ```javascript
|
|
60
|
-
* function(kind, msg, data) {
|
|
61
|
-
* console.log(`${kind}: ${msg}`, data)
|
|
62
|
-
* }
|
|
63
|
-
* ```
|
|
64
|
-
*
|
|
65
|
-
* @param {number} [opts.longpollerTimeout] - The maximum timeout of a long poll AJAX request.
|
|
66
|
-
*
|
|
67
|
-
* Defaults to 20s (double the server long poll timer).
|
|
68
|
-
*
|
|
69
|
-
* @param {(Object|function)} [opts.params] - The optional params to pass when connecting
|
|
70
|
-
* @param {string} [opts.binaryType] - The binary type to use for binary WebSocket frames.
|
|
71
|
-
*
|
|
72
|
-
* Defaults to "arraybuffer"
|
|
73
|
-
*
|
|
74
|
-
* @param {vsn} [opts.vsn] - The serializer's protocol version to send on connect.
|
|
75
|
-
*
|
|
76
|
-
* Defaults to DEFAULT_VSN.
|
|
77
|
-
*/
|
|
78
|
-
export default class Socket {
|
|
79
|
-
constructor(endPoint, opts = {}) {
|
|
80
|
-
this.stateChangeCallbacks = { open: [], close: [], error: [], message: [] };
|
|
81
|
-
this.channels = [];
|
|
82
|
-
this.sendBuffer = [];
|
|
83
|
-
this.ref = 0;
|
|
84
|
-
this.timeout = opts.timeout || DEFAULT_TIMEOUT;
|
|
85
|
-
this.transport = WebSocket;
|
|
86
|
-
this.establishedConnections = 0;
|
|
87
|
-
this.defaultEncoder = Serializer.encode.bind(Serializer);
|
|
88
|
-
this.defaultDecoder = Serializer.decode.bind(Serializer);
|
|
89
|
-
this.closeWasClean = false;
|
|
90
|
-
this.binaryType = opts.binaryType || "arraybuffer";
|
|
91
|
-
this.connectClock = 1;
|
|
92
|
-
if (this.transport !== LongPoll) {
|
|
93
|
-
this.encode = opts.encode || this.defaultEncoder;
|
|
94
|
-
this.decode = opts.decode || this.defaultDecoder;
|
|
95
|
-
}
|
|
96
|
-
else {
|
|
97
|
-
this.encode = this.defaultEncoder;
|
|
98
|
-
this.decode = this.defaultDecoder;
|
|
99
|
-
}
|
|
100
|
-
let awaitingConnectionOnPageShow = null;
|
|
101
|
-
if (phxWindow && phxWindow.addEventListener) {
|
|
102
|
-
phxWindow.addEventListener("pagehide", _e => {
|
|
103
|
-
if (this.conn) {
|
|
104
|
-
this.disconnect();
|
|
105
|
-
awaitingConnectionOnPageShow = this.connectClock;
|
|
106
|
-
}
|
|
107
|
-
});
|
|
108
|
-
phxWindow.addEventListener("pageshow", _e => {
|
|
109
|
-
if (awaitingConnectionOnPageShow === this.connectClock) {
|
|
110
|
-
awaitingConnectionOnPageShow = null;
|
|
111
|
-
this.connect();
|
|
112
|
-
}
|
|
113
|
-
});
|
|
114
|
-
}
|
|
115
|
-
this.heartbeatIntervalMs = opts.heartbeatIntervalMs || 30000;
|
|
116
|
-
this.rejoinAfterMs = (tries) => {
|
|
117
|
-
if (opts.rejoinAfterMs) {
|
|
118
|
-
return opts.rejoinAfterMs(tries);
|
|
119
|
-
}
|
|
120
|
-
else {
|
|
121
|
-
return [1000, 2000, 5000][tries - 1] || 10000;
|
|
122
|
-
}
|
|
123
|
-
};
|
|
124
|
-
this.reconnectAfterMs = (tries) => {
|
|
125
|
-
if (opts.reconnectAfterMs) {
|
|
126
|
-
return opts.reconnectAfterMs(tries);
|
|
127
|
-
}
|
|
128
|
-
else {
|
|
129
|
-
return [10, 50, 100, 150, 200, 250, 500, 1000, 2000][tries - 1] || 5000;
|
|
130
|
-
}
|
|
131
|
-
};
|
|
132
|
-
this.logger = opts.logger || null;
|
|
133
|
-
this.longpollerTimeout = opts.longpollerTimeout || 20000;
|
|
134
|
-
this.params = closure(opts.params || {});
|
|
135
|
-
this.endPoint = `${endPoint}/${TRANSPORTS.websocket}`;
|
|
136
|
-
this.vsn = opts.vsn || DEFAULT_VSN;
|
|
137
|
-
this.heartbeatTimeoutTimer = null;
|
|
138
|
-
this.heartbeatTimer = null;
|
|
139
|
-
this.pendingHeartbeatRef = null;
|
|
140
|
-
this.reconnectTimer = new Timer(() => {
|
|
141
|
-
this.teardown(() => this.connect());
|
|
142
|
-
}, this.reconnectAfterMs);
|
|
143
|
-
}
|
|
144
|
-
/**
|
|
145
|
-
* Returns the LongPoll transport reference
|
|
146
|
-
*/
|
|
147
|
-
getLongPollTransport() { return LongPoll; }
|
|
148
|
-
/**
|
|
149
|
-
* Disconnects and replaces the active transport
|
|
150
|
-
*
|
|
151
|
-
* @param {Function} newTransport - The new transport class to instantiate
|
|
152
|
-
*
|
|
153
|
-
*/
|
|
154
|
-
replaceTransport(newTransport) {
|
|
155
|
-
this.connectClock++;
|
|
156
|
-
this.closeWasClean = true;
|
|
157
|
-
this.reconnectTimer.reset();
|
|
158
|
-
this.sendBuffer = [];
|
|
159
|
-
if (this.conn) {
|
|
160
|
-
this.conn.close();
|
|
161
|
-
this.conn = null;
|
|
162
|
-
}
|
|
163
|
-
this.transport = newTransport;
|
|
164
|
-
}
|
|
165
|
-
/**
|
|
166
|
-
* Returns the socket protocol
|
|
167
|
-
*
|
|
168
|
-
* @returns {string}
|
|
169
|
-
*/
|
|
170
|
-
protocol() { return location.protocol.match(/^https/) ? "wss" : "ws"; }
|
|
171
|
-
/**
|
|
172
|
-
* The fully qualified socket url
|
|
173
|
-
*
|
|
174
|
-
* @returns {string}
|
|
175
|
-
*/
|
|
176
|
-
endPointURL() {
|
|
177
|
-
let uri = Ajax.appendParams(Ajax.appendParams(this.endPoint, this.params()), { vsn: this.vsn });
|
|
178
|
-
if (uri.charAt(0) !== "/") {
|
|
179
|
-
return uri;
|
|
180
|
-
}
|
|
181
|
-
if (uri.charAt(1) === "/") {
|
|
182
|
-
return `${this.protocol()}:${uri}`;
|
|
183
|
-
}
|
|
184
|
-
return `${this.protocol()}://${location.host}${uri}`;
|
|
185
|
-
}
|
|
186
|
-
/**
|
|
187
|
-
* Disconnects the socket
|
|
188
|
-
*
|
|
189
|
-
* See https://developer.mozilla.org/en-US/docs/Web/API/CloseEvent#Status_codes for valid status codes.
|
|
190
|
-
*
|
|
191
|
-
* @param {Function} callback - Optional callback which is called after socket is disconnected.
|
|
192
|
-
* @param {integer} code - A status code for disconnection (Optional).
|
|
193
|
-
* @param {string} reason - A textual description of the reason to disconnect. (Optional)
|
|
194
|
-
*/
|
|
195
|
-
disconnect(callback, code, reason) {
|
|
196
|
-
this.connectClock++;
|
|
197
|
-
this.closeWasClean = true;
|
|
198
|
-
this.reconnectTimer.reset();
|
|
199
|
-
this.teardown(callback, code, reason);
|
|
200
|
-
}
|
|
201
|
-
/**
|
|
202
|
-
*
|
|
203
|
-
* @param {Object} params - The params to send when connecting, for example `{user_id: userToken}`
|
|
204
|
-
*
|
|
205
|
-
* Passing params to connect is deprecated; pass them in the Socket constructor instead:
|
|
206
|
-
* `new Socket("/socket", {params: {user_id: userToken}})`.
|
|
207
|
-
*/
|
|
208
|
-
connect(params) {
|
|
209
|
-
if (params) {
|
|
210
|
-
console && console.log("passing params to connect is deprecated. Instead pass :params to the Socket constructor");
|
|
211
|
-
this.params = closure(params);
|
|
212
|
-
}
|
|
213
|
-
if (this.conn) {
|
|
214
|
-
return;
|
|
215
|
-
}
|
|
216
|
-
this.connectClock++;
|
|
217
|
-
this.closeWasClean = false;
|
|
218
|
-
this.conn = new WebSocket(this.endPointURL());
|
|
219
|
-
this.conn.binaryType = this.binaryType;
|
|
220
|
-
this.conn.timeout = this.longpollerTimeout;
|
|
221
|
-
this.conn.onopen = () => this.onConnOpen();
|
|
222
|
-
this.conn.onerror = error => this.onConnError(error);
|
|
223
|
-
this.conn.onmessage = event => this.onConnMessage(event);
|
|
224
|
-
this.conn.onclose = event => this.onConnClose(event);
|
|
225
|
-
}
|
|
226
|
-
/**
|
|
227
|
-
* Logs the message. Override `this.logger` for specialized logging. noops by default
|
|
228
|
-
* @param {string} kind
|
|
229
|
-
* @param {string} msg
|
|
230
|
-
* @param {Object} data
|
|
231
|
-
*/
|
|
232
|
-
log(kind, msg, data) { this.logger(kind, msg, data); }
|
|
233
|
-
/**
|
|
234
|
-
* Returns true if a logger has been set on this socket.
|
|
235
|
-
*/
|
|
236
|
-
hasLogger() { return this.logger !== null; }
|
|
237
|
-
/**
|
|
238
|
-
* Registers callbacks for connection open events
|
|
239
|
-
*
|
|
240
|
-
* @example socket.onOpen(function(){ console.info("the socket was opened") })
|
|
241
|
-
*
|
|
242
|
-
* @param {Function} callback
|
|
243
|
-
*/
|
|
244
|
-
onOpen(callback) {
|
|
245
|
-
let ref = this.makeRef();
|
|
246
|
-
this.stateChangeCallbacks.open.push([ref, callback]);
|
|
247
|
-
return ref;
|
|
248
|
-
}
|
|
249
|
-
/**
|
|
250
|
-
* Registers callbacks for connection close events
|
|
251
|
-
* @param {Function} callback
|
|
252
|
-
*/
|
|
253
|
-
onClose(callback) {
|
|
254
|
-
let ref = this.makeRef();
|
|
255
|
-
this.stateChangeCallbacks.close.push([ref, callback]);
|
|
256
|
-
return ref;
|
|
257
|
-
}
|
|
258
|
-
/**
|
|
259
|
-
* Registers callbacks for connection error events
|
|
260
|
-
*
|
|
261
|
-
* @example socket.onError(function(error){ alert("An error occurred") })
|
|
262
|
-
*
|
|
263
|
-
* @param {Function} callback
|
|
264
|
-
*/
|
|
265
|
-
onError(callback) {
|
|
266
|
-
let ref = this.makeRef();
|
|
267
|
-
this.stateChangeCallbacks.error.push([ref, callback]);
|
|
268
|
-
return ref;
|
|
269
|
-
}
|
|
270
|
-
/**
|
|
271
|
-
* Registers callbacks for connection message events
|
|
272
|
-
* @param {Function} callback
|
|
273
|
-
*/
|
|
274
|
-
onMessage(callback) {
|
|
275
|
-
let ref = this.makeRef();
|
|
276
|
-
this.stateChangeCallbacks.message.push([ref, callback]);
|
|
277
|
-
return ref;
|
|
278
|
-
}
|
|
279
|
-
/**
|
|
280
|
-
* Pings the server and invokes the callback with the RTT in milliseconds
|
|
281
|
-
* @param {Function} callback
|
|
282
|
-
*
|
|
283
|
-
* Returns true if the ping was pushed or false if unable to be pushed.
|
|
284
|
-
*/
|
|
285
|
-
ping(callback) {
|
|
286
|
-
if (!this.isConnected()) {
|
|
287
|
-
return false;
|
|
288
|
-
}
|
|
289
|
-
let ref = this.makeRef();
|
|
290
|
-
let startTime = Date.now();
|
|
291
|
-
this.push({ topic: "phoenix", event: "heartbeat", payload: {}, ref: ref });
|
|
292
|
-
let onMsgRef = this.onMessage(msg => {
|
|
293
|
-
if (msg.ref === ref) {
|
|
294
|
-
this.off([onMsgRef]);
|
|
295
|
-
callback(Date.now() - startTime);
|
|
296
|
-
}
|
|
297
|
-
});
|
|
298
|
-
return true;
|
|
299
|
-
}
|
|
300
|
-
/**
|
|
301
|
-
* @private
|
|
302
|
-
*/
|
|
303
|
-
clearHeartbeats() {
|
|
304
|
-
clearTimeout(this.heartbeatTimer);
|
|
305
|
-
clearTimeout(this.heartbeatTimeoutTimer);
|
|
306
|
-
}
|
|
307
|
-
onConnOpen() {
|
|
308
|
-
if (this.hasLogger())
|
|
309
|
-
this.log("transport", `connected to ${this.endPointURL()}`);
|
|
310
|
-
this.closeWasClean = false;
|
|
311
|
-
this.establishedConnections++;
|
|
312
|
-
this.flushSendBuffer();
|
|
313
|
-
this.reconnectTimer.reset();
|
|
314
|
-
this.resetHeartbeat();
|
|
315
|
-
this.stateChangeCallbacks.open.forEach(([, callback]) => callback());
|
|
316
|
-
}
|
|
317
|
-
/**
|
|
318
|
-
* @private
|
|
319
|
-
*/
|
|
320
|
-
heartbeatTimeout() {
|
|
321
|
-
if (this.pendingHeartbeatRef) {
|
|
322
|
-
this.pendingHeartbeatRef = null;
|
|
323
|
-
if (this.hasLogger()) {
|
|
324
|
-
this.log("transport", "heartbeat timeout. Attempting to re-establish connection");
|
|
325
|
-
}
|
|
326
|
-
this.triggerChanError();
|
|
327
|
-
this.closeWasClean = false;
|
|
328
|
-
this.teardown(() => this.reconnectTimer.scheduleTimeout(), WS_CLOSE_NORMAL, "heartbeat timeout");
|
|
329
|
-
}
|
|
330
|
-
}
|
|
331
|
-
resetHeartbeat() {
|
|
332
|
-
if (this.conn && this.conn.skipHeartbeat) {
|
|
333
|
-
return;
|
|
334
|
-
}
|
|
335
|
-
this.pendingHeartbeatRef = null;
|
|
336
|
-
this.clearHeartbeats();
|
|
337
|
-
this.heartbeatTimer = setTimeout(() => this.sendHeartbeat(), this.heartbeatIntervalMs);
|
|
338
|
-
}
|
|
339
|
-
teardown(callback, code, reason) {
|
|
340
|
-
if (!this.conn) {
|
|
341
|
-
return callback && callback();
|
|
342
|
-
}
|
|
343
|
-
this.waitForBufferDone(() => {
|
|
344
|
-
if (this.conn) {
|
|
345
|
-
if (code) {
|
|
346
|
-
this.conn.close(code, reason || "");
|
|
347
|
-
}
|
|
348
|
-
else {
|
|
349
|
-
this.conn.close();
|
|
350
|
-
}
|
|
351
|
-
}
|
|
352
|
-
this.waitForSocketClosed(() => {
|
|
353
|
-
if (this.conn) {
|
|
354
|
-
this.conn.onopen = function () { }; // noop
|
|
355
|
-
this.conn.onerror = function () { }; // noop
|
|
356
|
-
this.conn.onmessage = function () { }; // noop
|
|
357
|
-
this.conn.onclose = function () { }; // noop
|
|
358
|
-
this.conn = null;
|
|
359
|
-
}
|
|
360
|
-
callback && callback();
|
|
361
|
-
});
|
|
362
|
-
});
|
|
363
|
-
}
|
|
364
|
-
waitForBufferDone(callback, tries = 1) {
|
|
365
|
-
if (tries === 5 || !this.conn || !this.conn.bufferedAmount) {
|
|
366
|
-
callback();
|
|
367
|
-
return;
|
|
368
|
-
}
|
|
369
|
-
setTimeout(() => {
|
|
370
|
-
this.waitForBufferDone(callback, tries + 1);
|
|
371
|
-
}, 150 * tries);
|
|
372
|
-
}
|
|
373
|
-
waitForSocketClosed(callback, tries = 1) {
|
|
374
|
-
if (tries === 5 || !this.conn || this.conn.readyState === SOCKET_STATES.closed) {
|
|
375
|
-
callback();
|
|
376
|
-
return;
|
|
377
|
-
}
|
|
378
|
-
setTimeout(() => {
|
|
379
|
-
this.waitForSocketClosed(callback, tries + 1);
|
|
380
|
-
}, 150 * tries);
|
|
381
|
-
}
|
|
382
|
-
onConnClose(event) {
|
|
383
|
-
let closeCode = event && event.code;
|
|
384
|
-
if (this.hasLogger())
|
|
385
|
-
this.log("transport", "close", event);
|
|
386
|
-
this.triggerChanError();
|
|
387
|
-
this.clearHeartbeats();
|
|
388
|
-
if (!this.closeWasClean && closeCode !== 1000) {
|
|
389
|
-
this.reconnectTimer.scheduleTimeout();
|
|
390
|
-
}
|
|
391
|
-
this.stateChangeCallbacks.close.forEach(([, callback]) => callback(event));
|
|
392
|
-
}
|
|
393
|
-
/**
|
|
394
|
-
* @private
|
|
395
|
-
*/
|
|
396
|
-
onConnError(error) {
|
|
397
|
-
if (this.hasLogger())
|
|
398
|
-
this.log("transport", error);
|
|
399
|
-
let transportBefore = this.transport;
|
|
400
|
-
let establishedBefore = this.establishedConnections;
|
|
401
|
-
this.stateChangeCallbacks.error.forEach(([, callback]) => {
|
|
402
|
-
callback(error, transportBefore, establishedBefore);
|
|
403
|
-
});
|
|
404
|
-
if (transportBefore === this.transport || establishedBefore > 0) {
|
|
405
|
-
this.triggerChanError();
|
|
406
|
-
}
|
|
407
|
-
}
|
|
408
|
-
/**
|
|
409
|
-
* @private
|
|
410
|
-
*/
|
|
411
|
-
triggerChanError() {
|
|
412
|
-
this.channels.forEach(channel => {
|
|
413
|
-
if (!(channel.isErrored() || channel.isLeaving() || channel.isClosed())) {
|
|
414
|
-
channel.trigger(CHANNEL_EVENTS.error);
|
|
415
|
-
}
|
|
416
|
-
});
|
|
417
|
-
}
|
|
418
|
-
/**
|
|
419
|
-
* @returns {string}
|
|
420
|
-
*/
|
|
421
|
-
connectionState() {
|
|
422
|
-
switch (this.conn && this.conn.readyState) {
|
|
423
|
-
case SOCKET_STATES.connecting: return "connecting";
|
|
424
|
-
case SOCKET_STATES.open: return "open";
|
|
425
|
-
case SOCKET_STATES.closing: return "closing";
|
|
426
|
-
default: return "closed";
|
|
427
|
-
}
|
|
428
|
-
}
|
|
429
|
-
/**
|
|
430
|
-
* @returns {boolean}
|
|
431
|
-
*/
|
|
432
|
-
isConnected() { return this.connectionState() === "open"; }
|
|
433
|
-
/**
|
|
434
|
-
* @private
|
|
435
|
-
*
|
|
436
|
-
* @param {Channel}
|
|
437
|
-
*/
|
|
438
|
-
remove(channel) {
|
|
439
|
-
this.off(channel.stateChangeRefs);
|
|
440
|
-
this.channels = this.channels.filter(c => c.joinRef() !== channel.joinRef());
|
|
441
|
-
}
|
|
442
|
-
/**
|
|
443
|
-
* Removes `onOpen`, `onClose`, `onError,` and `onMessage` registrations.
|
|
444
|
-
*
|
|
445
|
-
* @param {refs} - list of refs returned by calls to
|
|
446
|
-
* `onOpen`, `onClose`, `onError,` and `onMessage`
|
|
447
|
-
*/
|
|
448
|
-
off(refs) {
|
|
449
|
-
for (let key in this.stateChangeCallbacks) {
|
|
450
|
-
this.stateChangeCallbacks[key] = this.stateChangeCallbacks[key].filter(([ref]) => {
|
|
451
|
-
return refs.indexOf(ref) === -1;
|
|
452
|
-
});
|
|
453
|
-
}
|
|
454
|
-
}
|
|
455
|
-
/**
|
|
456
|
-
* Initiates a new channel for the given topic
|
|
457
|
-
*
|
|
458
|
-
* @param {string} topic
|
|
459
|
-
* @param {Object} chanParams - Parameters for the channel
|
|
460
|
-
* @returns {Channel}
|
|
461
|
-
*/
|
|
462
|
-
channel(topic, chanParams = {}) {
|
|
463
|
-
let chan = new Channel(topic, chanParams, this);
|
|
464
|
-
this.channels.push(chan);
|
|
465
|
-
return chan;
|
|
466
|
-
}
|
|
467
|
-
/**
|
|
468
|
-
* @param {Object} data
|
|
469
|
-
*/
|
|
470
|
-
push(data) {
|
|
471
|
-
if (this.hasLogger()) {
|
|
472
|
-
let { topic, event, payload, ref, join_ref } = data;
|
|
473
|
-
this.log("push", `${topic} ${event} (${join_ref}, ${ref})`, payload);
|
|
474
|
-
}
|
|
475
|
-
if (this.isConnected()) {
|
|
476
|
-
this.encode(data, result => this.conn.send(result));
|
|
477
|
-
}
|
|
478
|
-
else {
|
|
479
|
-
this.sendBuffer.push(() => this.encode(data, result => this.conn.send(result)));
|
|
480
|
-
}
|
|
481
|
-
}
|
|
482
|
-
/**
|
|
483
|
-
* Return the next message ref, accounting for overflows
|
|
484
|
-
* @returns {string}
|
|
485
|
-
*/
|
|
486
|
-
makeRef() {
|
|
487
|
-
let newRef = this.ref + 1;
|
|
488
|
-
if (newRef === this.ref) {
|
|
489
|
-
this.ref = 0;
|
|
490
|
-
}
|
|
491
|
-
else {
|
|
492
|
-
this.ref = newRef;
|
|
493
|
-
}
|
|
494
|
-
return this.ref.toString();
|
|
495
|
-
}
|
|
496
|
-
sendHeartbeat() {
|
|
497
|
-
if (this.pendingHeartbeatRef && !this.isConnected()) {
|
|
498
|
-
return;
|
|
499
|
-
}
|
|
500
|
-
this.pendingHeartbeatRef = this.makeRef();
|
|
501
|
-
this.push({ topic: "phoenix", event: "heartbeat", payload: {}, ref: this.pendingHeartbeatRef });
|
|
502
|
-
this.heartbeatTimeoutTimer = setTimeout(() => this.heartbeatTimeout(), this.heartbeatIntervalMs);
|
|
503
|
-
}
|
|
504
|
-
flushSendBuffer() {
|
|
505
|
-
if (this.isConnected() && this.sendBuffer.length > 0) {
|
|
506
|
-
this.sendBuffer.forEach(callback => callback());
|
|
507
|
-
this.sendBuffer = [];
|
|
508
|
-
}
|
|
509
|
-
}
|
|
510
|
-
onConnMessage(rawMessage) {
|
|
511
|
-
this.decode(rawMessage.data, msg => {
|
|
512
|
-
let { topic, event, payload, ref, join_ref } = msg;
|
|
513
|
-
if (ref && ref === this.pendingHeartbeatRef) {
|
|
514
|
-
this.clearHeartbeats();
|
|
515
|
-
this.pendingHeartbeatRef = null;
|
|
516
|
-
this.heartbeatTimer = setTimeout(() => this.sendHeartbeat(), this.heartbeatIntervalMs);
|
|
517
|
-
}
|
|
518
|
-
if (this.hasLogger())
|
|
519
|
-
this.log("receive", `${payload.status || ""} ${topic} ${event} ${ref && "(" + ref + ")" || ""}`, payload);
|
|
520
|
-
for (let i = 0; i < this.channels.length; i++) {
|
|
521
|
-
const channel = this.channels[i];
|
|
522
|
-
if (!channel.isMember(topic, event, payload, join_ref)) {
|
|
523
|
-
continue;
|
|
524
|
-
}
|
|
525
|
-
channel.trigger(event, payload, ref, join_ref);
|
|
526
|
-
}
|
|
527
|
-
for (let i = 0; i < this.stateChangeCallbacks.message.length; i++) {
|
|
528
|
-
let [, callback] = this.stateChangeCallbacks.message[i];
|
|
529
|
-
callback(msg);
|
|
530
|
-
}
|
|
531
|
-
});
|
|
532
|
-
}
|
|
533
|
-
leaveOpenTopic(topic) {
|
|
534
|
-
let dupChannel = this.channels.find(c => c.topic === topic && (c.isJoined() || c.isJoining()));
|
|
535
|
-
if (dupChannel) {
|
|
536
|
-
if (this.hasLogger())
|
|
537
|
-
this.log("transport", `leaving duplicate topic "${topic}"`);
|
|
538
|
-
dupChannel.leave();
|
|
539
|
-
}
|
|
540
|
-
}
|
|
541
|
-
}
|
|
@@ -1,25 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
*
|
|
3
|
-
* Creates a timer that accepts a `timerCalc` function to perform
|
|
4
|
-
* calculated timeout retries, such as exponential backoff.
|
|
5
|
-
*
|
|
6
|
-
* @example
|
|
7
|
-
* let reconnectTimer = new Timer(() => this.connect(), function(tries){
|
|
8
|
-
* return [1000, 5000, 10000][tries - 1] || 10000
|
|
9
|
-
* })
|
|
10
|
-
* reconnectTimer.scheduleTimeout() // fires after 1000
|
|
11
|
-
* reconnectTimer.scheduleTimeout() // fires after 5000
|
|
12
|
-
* reconnectTimer.reset()
|
|
13
|
-
* reconnectTimer.scheduleTimeout() // fires after 1000
|
|
14
|
-
*
|
|
15
|
-
* @param {Function} callback
|
|
16
|
-
* @param {Function} timerCalc
|
|
17
|
-
*/
|
|
18
|
-
export default class Timer {
|
|
19
|
-
constructor(callback: any, timerCalc: any);
|
|
20
|
-
reset(): void;
|
|
21
|
-
/**
|
|
22
|
-
* Cancels any previous scheduleTimeout and schedules callback
|
|
23
|
-
*/
|
|
24
|
-
scheduleTimeout(): void;
|
|
25
|
-
}
|
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
// @ts-nocheck
|
|
2
|
-
/**
|
|
3
|
-
*
|
|
4
|
-
* Creates a timer that accepts a `timerCalc` function to perform
|
|
5
|
-
* calculated timeout retries, such as exponential backoff.
|
|
6
|
-
*
|
|
7
|
-
* @example
|
|
8
|
-
* let reconnectTimer = new Timer(() => this.connect(), function(tries){
|
|
9
|
-
* return [1000, 5000, 10000][tries - 1] || 10000
|
|
10
|
-
* })
|
|
11
|
-
* reconnectTimer.scheduleTimeout() // fires after 1000
|
|
12
|
-
* reconnectTimer.scheduleTimeout() // fires after 5000
|
|
13
|
-
* reconnectTimer.reset()
|
|
14
|
-
* reconnectTimer.scheduleTimeout() // fires after 1000
|
|
15
|
-
*
|
|
16
|
-
* @param {Function} callback
|
|
17
|
-
* @param {Function} timerCalc
|
|
18
|
-
*/
|
|
19
|
-
export default class Timer {
|
|
20
|
-
constructor(callback, timerCalc) {
|
|
21
|
-
this.callback = callback;
|
|
22
|
-
this.timerCalc = timerCalc;
|
|
23
|
-
this.timer = null;
|
|
24
|
-
this.tries = 0;
|
|
25
|
-
}
|
|
26
|
-
reset() {
|
|
27
|
-
this.tries = 0;
|
|
28
|
-
clearTimeout(this.timer);
|
|
29
|
-
}
|
|
30
|
-
/**
|
|
31
|
-
* Cancels any previous scheduleTimeout and schedules callback
|
|
32
|
-
*/
|
|
33
|
-
scheduleTimeout() {
|
|
34
|
-
clearTimeout(this.timer);
|
|
35
|
-
this.timer = setTimeout(() => {
|
|
36
|
-
this.tries = this.tries + 1;
|
|
37
|
-
this.callback();
|
|
38
|
-
}, this.timerCalc(this.tries + 1));
|
|
39
|
-
}
|
|
40
|
-
}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export declare let closure: (value: any) => any;
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|