@nxtedition/deepstream.io-client-js 26.0.13 → 26.0.14
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/package.json +1 -1
- package/src/event/event-handler.js +2 -2
- package/src/message/connection.js +30 -30
- package/src/message/message-builder.js +9 -84
- package/src/message/message-parser.js +2 -2
- package/src/record/record-handler.js +1 -1
- package/src/record/record.js +7 -7
- package/src/utils/multicast-listener.js +5 -5
- package/src/utils/unicast-listener.js +4 -3
- package/src/utils/utils.js +1 -1
package/package.json
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
|
+
import * as C from '../constants/constants.js'
|
|
1
2
|
import * as messageBuilder from '../message/message-builder.js'
|
|
2
3
|
import messageParser from '../message/message-parser.js'
|
|
3
|
-
import * as C from '../constants/constants.js'
|
|
4
4
|
import MulticastListener from '../utils/multicast-listener.js'
|
|
5
5
|
import UnicastListener from '../utils/unicast-listener.js'
|
|
6
6
|
import EventEmitter from 'component-emitter2'
|
|
7
|
-
import
|
|
7
|
+
import rxjs from 'rxjs'
|
|
8
8
|
|
|
9
9
|
const EventHandler = function (options, connection, client) {
|
|
10
10
|
this._options = options
|
|
@@ -1,14 +1,13 @@
|
|
|
1
|
-
import * as utils from '../utils/utils.js'
|
|
2
|
-
import messageParser from './message-parser.js'
|
|
3
|
-
import * as messageBuilder from './message-builder.js'
|
|
4
|
-
import * as C from '../constants/constants.js'
|
|
5
|
-
import xxhash from 'xxhash-wasm'
|
|
6
|
-
import FixedQueue from '../utils/fixed-queue.js'
|
|
7
|
-
import Emitter from 'component-emitter2'
|
|
8
|
-
|
|
9
|
-
const HASHER = await xxhash()
|
|
10
|
-
const NodeWebSocket = utils.isNode ? await import('ws').then((x) => x.default) : null
|
|
11
1
|
const BrowserWebSocket = globalThis.WebSocket || globalThis.MozWebSocket
|
|
2
|
+
const utils = require('../utils/utils')
|
|
3
|
+
const NodeWebSocket = utils.isNode ? require('ws') : null
|
|
4
|
+
const messageParser = require('./message-parser')
|
|
5
|
+
const messageBuilder = require('./message-builder')
|
|
6
|
+
const C = require('../constants/constants')
|
|
7
|
+
const pkg = require('../../package.json')
|
|
8
|
+
const xxhash = require('xxhash-wasm')
|
|
9
|
+
const FixedQueue = require('../utils/fixed-queue')
|
|
10
|
+
const Emitter = require('component-emitter2')
|
|
12
11
|
|
|
13
12
|
const Connection = function (client, url, options) {
|
|
14
13
|
this._client = client
|
|
@@ -40,9 +39,11 @@ const Connection = function (client, url, options) {
|
|
|
40
39
|
|
|
41
40
|
this._state = C.CONNECTION_STATE.CLOSED
|
|
42
41
|
|
|
43
|
-
this.hasher =
|
|
44
|
-
|
|
45
|
-
|
|
42
|
+
this.hasher = null
|
|
43
|
+
xxhash().then((hasher) => {
|
|
44
|
+
this.hasher = hasher
|
|
45
|
+
this._createEndpoint()
|
|
46
|
+
})
|
|
46
47
|
}
|
|
47
48
|
|
|
48
49
|
Emitter(Connection.prototype)
|
|
@@ -86,30 +87,25 @@ Connection.prototype.close = function () {
|
|
|
86
87
|
this._endpoint?.close()
|
|
87
88
|
|
|
88
89
|
if (this._reconnectTimeout) {
|
|
89
|
-
|
|
90
|
+
clearTimeout(this._reconnectTimeout)
|
|
90
91
|
this._reconnectTimeout = null
|
|
91
92
|
}
|
|
92
93
|
}
|
|
93
94
|
|
|
94
95
|
Connection.prototype._createEndpoint = function () {
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
this._endpoint = new BrowserWebSocket(this._url)
|
|
101
|
-
this._endpoint.binaryType = 'arraybuffer'
|
|
102
|
-
}
|
|
96
|
+
this._endpoint = NodeWebSocket
|
|
97
|
+
? new NodeWebSocket(this._url, {
|
|
98
|
+
generateMask() {},
|
|
99
|
+
})
|
|
100
|
+
: new BrowserWebSocket(this._url)
|
|
103
101
|
this._corked = false
|
|
104
102
|
|
|
105
103
|
this._endpoint.onopen = this._onOpen.bind(this)
|
|
106
104
|
this._endpoint.onerror = this._onError.bind(this)
|
|
107
105
|
this._endpoint.onclose = this._onClose.bind(this)
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
this._onMessage(typeof data === 'string' ? data : decoder.decode(data))
|
|
112
|
-
}
|
|
106
|
+
this._endpoint.onmessage = BrowserWebSocket
|
|
107
|
+
? ({ data }) => this._onMessage(typeof data === 'string' ? data : Buffer.from(data).toString())
|
|
108
|
+
: ({ data }) => this._onMessage(typeof data === 'string' ? data : data.toString())
|
|
113
109
|
}
|
|
114
110
|
|
|
115
111
|
Connection.prototype.send = function (message) {
|
|
@@ -136,7 +132,7 @@ Connection.prototype.send = function (message) {
|
|
|
136
132
|
if (this._endpoint._socket && !this._corked) {
|
|
137
133
|
this._endpoint._socket.cork()
|
|
138
134
|
this._corked = true
|
|
139
|
-
|
|
135
|
+
setTimeout(() => {
|
|
140
136
|
this._endpoint._socket.uncork()
|
|
141
137
|
this._corked = false
|
|
142
138
|
}, 1)
|
|
@@ -170,7 +166,7 @@ Connection.prototype._sendAuthParams = function () {
|
|
|
170
166
|
this._setState(C.CONNECTION_STATE.AUTHENTICATING)
|
|
171
167
|
const authMessage = messageBuilder.getMsg(C.TOPIC.AUTH, C.ACTIONS.REQUEST, [
|
|
172
168
|
this._authParams,
|
|
173
|
-
|
|
169
|
+
pkg.version,
|
|
174
170
|
utils.isNode
|
|
175
171
|
? `Node/${process.version}`
|
|
176
172
|
: globalThis.navigator && globalThis.navigator.userAgent,
|
|
@@ -245,6 +241,10 @@ Connection.prototype._recvMessages = function (deadline) {
|
|
|
245
241
|
continue
|
|
246
242
|
}
|
|
247
243
|
|
|
244
|
+
if (this._logger) {
|
|
245
|
+
this._logger.trace(message, 'receive')
|
|
246
|
+
}
|
|
247
|
+
|
|
248
248
|
messageParser.parseMessage(message, this._client, this._message)
|
|
249
249
|
|
|
250
250
|
this.emit('recv', this._message)
|
|
@@ -366,4 +366,4 @@ Connection.prototype._clearReconnect = function () {
|
|
|
366
366
|
this._reconnectionAttempt = 0
|
|
367
367
|
}
|
|
368
368
|
|
|
369
|
-
|
|
369
|
+
module.exports = Connection
|
|
@@ -1,103 +1,28 @@
|
|
|
1
|
-
|
|
2
|
-
import varint from 'varint'
|
|
3
|
-
import * as utils from '../utils/utils.js'
|
|
1
|
+
const C = require('../constants/constants')
|
|
4
2
|
|
|
5
|
-
const
|
|
3
|
+
const SEP = C.MESSAGE_PART_SEPERATOR
|
|
6
4
|
|
|
7
|
-
|
|
8
|
-
let poolBuffer
|
|
9
|
-
let poolView
|
|
10
|
-
let poolOffset
|
|
11
|
-
|
|
12
|
-
function allocPool(size) {
|
|
13
|
-
poolSize = size || poolSize || 1024 * 1024
|
|
14
|
-
poolBuffer = utils.isNode
|
|
15
|
-
? globalThis.Buffer.allocUnsafe(poolSize)
|
|
16
|
-
: new Uint8Array(new ArrayBuffer(poolSize))
|
|
17
|
-
poolView = new DataView(poolBuffer.buffer)
|
|
18
|
-
poolOffset = 0
|
|
19
|
-
}
|
|
20
|
-
|
|
21
|
-
function alignPool() {
|
|
22
|
-
// Ensure aligned slices
|
|
23
|
-
if (poolOffset & 0x7) {
|
|
24
|
-
poolOffset |= 0x7
|
|
25
|
-
poolOffset++
|
|
26
|
-
}
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
function writeString(dst, str, offset) {
|
|
30
|
-
if (utils.isNode) {
|
|
31
|
-
return dst.write(str, offset)
|
|
32
|
-
} else {
|
|
33
|
-
const res = poolEncoder.encodeInto(str, new Uint8Array(dst.buffer, offset))
|
|
34
|
-
return res.written
|
|
35
|
-
}
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
export function getMsg(topic, action, data) {
|
|
5
|
+
module.exports.getMsg = function (topic, action, data) {
|
|
39
6
|
if (data && !(data instanceof Array)) {
|
|
40
7
|
throw new Error('data must be an array')
|
|
41
8
|
}
|
|
42
9
|
|
|
43
|
-
|
|
44
|
-
allocPool()
|
|
45
|
-
} else {
|
|
46
|
-
alignPool()
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
const start = poolOffset
|
|
50
|
-
|
|
51
|
-
const headerSize = 8
|
|
52
|
-
poolBuffer[poolOffset++] = 128 + headerSize
|
|
53
|
-
let headerPos = poolOffset
|
|
54
|
-
poolOffset += headerSize - 1
|
|
55
|
-
|
|
56
|
-
poolBuffer[poolOffset++] = topic.charCodeAt(0)
|
|
57
|
-
poolBuffer[poolOffset++] = 31
|
|
58
|
-
for (let n = 0; n < action.length; n++) {
|
|
59
|
-
poolBuffer[poolOffset++] = action.charCodeAt(n)
|
|
60
|
-
}
|
|
10
|
+
const sendData = [topic, action]
|
|
61
11
|
|
|
62
12
|
if (data) {
|
|
63
13
|
for (let i = 0; i < data.length; i++) {
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
if (data[i] == null) {
|
|
67
|
-
poolBuffer[poolOffset++] = 31
|
|
68
|
-
len = 0
|
|
69
|
-
} else if (type === 'object') {
|
|
70
|
-
poolBuffer[poolOffset++] = 31
|
|
71
|
-
len = writeString(poolBuffer, JSON.stringify(data[i]), poolOffset)
|
|
72
|
-
} else if (type === 'bigint') {
|
|
73
|
-
poolBuffer[poolOffset++] = 31
|
|
74
|
-
poolView.setBigUint64(poolOffset, data[i], false)
|
|
75
|
-
len = 8
|
|
76
|
-
} else if (type === 'string') {
|
|
77
|
-
poolBuffer[poolOffset++] = 31
|
|
78
|
-
len = writeString(poolBuffer, data[i], poolOffset)
|
|
14
|
+
if (typeof data[i] === 'object') {
|
|
15
|
+
sendData.push(JSON.stringify(data[i]))
|
|
79
16
|
} else {
|
|
80
|
-
|
|
81
|
-
}
|
|
82
|
-
poolOffset += len
|
|
83
|
-
|
|
84
|
-
varint.encode(len + 1, poolBuffer, headerPos)
|
|
85
|
-
headerPos += varint.encode.bytes
|
|
86
|
-
if (headerPos - start >= headerSize) {
|
|
87
|
-
throw new Error(`header too large: ${headerPos - start} ${headerSize}`)
|
|
88
|
-
}
|
|
89
|
-
|
|
90
|
-
if (poolOffset >= poolBuffer.length) {
|
|
91
|
-
allocPool(start === 0 ? poolSize * 2 : poolSize)
|
|
92
|
-
return getMsg(topic, action, data)
|
|
17
|
+
sendData.push(data[i])
|
|
93
18
|
}
|
|
94
19
|
}
|
|
95
20
|
}
|
|
96
21
|
|
|
97
|
-
return
|
|
22
|
+
return sendData.join(SEP)
|
|
98
23
|
}
|
|
99
24
|
|
|
100
|
-
|
|
25
|
+
module.exports.typed = function (value) {
|
|
101
26
|
const type = typeof value
|
|
102
27
|
|
|
103
28
|
if (type === 'string') {
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
|
|
1
|
+
const C = require('../constants/constants')
|
|
2
2
|
|
|
3
3
|
const MessageParser = function () {
|
|
4
4
|
this._actions = this._getActions()
|
|
@@ -88,4 +88,4 @@ MessageParser.prototype.parseMessage = function (message, client, result) {
|
|
|
88
88
|
result.data = parts.splice(2)
|
|
89
89
|
}
|
|
90
90
|
|
|
91
|
-
|
|
91
|
+
module.exports = new MessageParser()
|
|
@@ -2,7 +2,7 @@ import Record from './record.js'
|
|
|
2
2
|
import MulticastListener from '../utils/multicast-listener.js'
|
|
3
3
|
import UnicastListener from '../utils/unicast-listener.js'
|
|
4
4
|
import * as C from '../constants/constants.js'
|
|
5
|
-
import
|
|
5
|
+
import rxjs from 'rxjs'
|
|
6
6
|
import invariant from 'invariant'
|
|
7
7
|
import EventEmitter from 'component-emitter2'
|
|
8
8
|
import jsonPath from '@nxtedition/json-path'
|
package/src/record/record.js
CHANGED
|
@@ -1,20 +1,19 @@
|
|
|
1
1
|
import jsonPath from '@nxtedition/json-path'
|
|
2
2
|
import * as utils from '../utils/utils.js'
|
|
3
3
|
import * as C from '../constants/constants.js'
|
|
4
|
-
import messageParser from '../message/message-parser.js'
|
|
4
|
+
import * as messageParser from '../message/message-parser.js'
|
|
5
5
|
import xuid from 'xuid'
|
|
6
6
|
import invariant from 'invariant'
|
|
7
7
|
import cloneDeep from 'lodash.clonedeep'
|
|
8
8
|
import * as timers from '../utils/timers.js'
|
|
9
9
|
|
|
10
|
-
|
|
10
|
+
class Record {
|
|
11
11
|
static STATE = C.RECORD_STATE
|
|
12
12
|
|
|
13
13
|
constructor(name, handler) {
|
|
14
14
|
const connection = handler._connection
|
|
15
15
|
|
|
16
16
|
this._handler = handler
|
|
17
|
-
|
|
18
17
|
this._name = name
|
|
19
18
|
this._version = ''
|
|
20
19
|
this._data = jsonPath.EMPTY
|
|
@@ -22,6 +21,7 @@ export default class Record {
|
|
|
22
21
|
this._refs = 0
|
|
23
22
|
this._subscriptions = []
|
|
24
23
|
this._emitting = false
|
|
24
|
+
|
|
25
25
|
/** @type Map? */ this._updating = null
|
|
26
26
|
/** @type Array? */ this._patching = null
|
|
27
27
|
this._subscribed = connection.sendMsg(C.TOPIC.RECORD, C.ACTIONS.SUBSCRIBE, [this._name])
|
|
@@ -389,7 +389,7 @@ export default class Record {
|
|
|
389
389
|
this._version = nextVersion
|
|
390
390
|
}
|
|
391
391
|
|
|
392
|
-
_onUpdate([, version, data
|
|
392
|
+
_onUpdate([, version, data]) {
|
|
393
393
|
const prevData = this._data
|
|
394
394
|
const prevVersion = this._version
|
|
395
395
|
const prevState = this._state
|
|
@@ -422,9 +422,7 @@ export default class Record {
|
|
|
422
422
|
this._onPatching(false)
|
|
423
423
|
}
|
|
424
424
|
|
|
425
|
-
if (this._state < C.RECORD_STATE.
|
|
426
|
-
this._state = C.RECORD_STATE.PROVIDER
|
|
427
|
-
} else if (this._state < C.RECORD_STATE.SERVER) {
|
|
425
|
+
if (this._state < C.RECORD_STATE.SERVER) {
|
|
428
426
|
this._state = this._version.charAt(0) === 'I' ? C.RECORD_STATE.STALE : C.RECORD_STATE.SERVER
|
|
429
427
|
}
|
|
430
428
|
|
|
@@ -573,3 +571,5 @@ Object.defineProperty(Record.prototype, 'hasProvider', {
|
|
|
573
571
|
return this.state >= C.RECORD_STATE.PROVIDER
|
|
574
572
|
},
|
|
575
573
|
})
|
|
574
|
+
|
|
575
|
+
export default Record
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import * as C from '../constants/constants.js'
|
|
2
|
-
import
|
|
2
|
+
import rxjs from 'rxjs'
|
|
3
3
|
|
|
4
4
|
class Listener {
|
|
5
5
|
constructor(topic, pattern, callback, handler, { recursive = false, stringify = null } = {}) {
|
|
@@ -68,7 +68,7 @@ class Listener {
|
|
|
68
68
|
if (this.connected && provider.accepted) {
|
|
69
69
|
this._connection.sendMsg(this._topic, C.ACTIONS.LISTEN_REJECT, [
|
|
70
70
|
this._pattern,
|
|
71
|
-
provider.
|
|
71
|
+
provider.key,
|
|
72
72
|
])
|
|
73
73
|
}
|
|
74
74
|
|
|
@@ -77,7 +77,7 @@ class Listener {
|
|
|
77
77
|
provider.accepted = false
|
|
78
78
|
provider.sending = false
|
|
79
79
|
|
|
80
|
-
|
|
80
|
+
clearTimeout(provider.timeout)
|
|
81
81
|
provider.timeout = null
|
|
82
82
|
|
|
83
83
|
provider.patternSubscription?.unsubscribe()
|
|
@@ -101,7 +101,7 @@ class Listener {
|
|
|
101
101
|
this._connection.sendMsg(
|
|
102
102
|
this._topic,
|
|
103
103
|
accepted ? C.ACTIONS.LISTEN_ACCEPT : C.ACTIONS.LISTEN_REJECT,
|
|
104
|
-
[this._pattern, provider.
|
|
104
|
+
[this._pattern, provider.key],
|
|
105
105
|
)
|
|
106
106
|
|
|
107
107
|
provider.version = null
|
|
@@ -157,7 +157,7 @@ class Listener {
|
|
|
157
157
|
if (provider.version !== version) {
|
|
158
158
|
provider.version = version
|
|
159
159
|
this._connection.sendMsg(C.TOPIC.RECORD, C.ACTIONS.UPDATE, [
|
|
160
|
-
provider.
|
|
160
|
+
provider.key,
|
|
161
161
|
version,
|
|
162
162
|
body,
|
|
163
163
|
])
|
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
import * as C from '../constants/constants.js'
|
|
2
|
-
import
|
|
2
|
+
import rx from 'rxjs/operators'
|
|
3
|
+
import rxjs from 'rxjs'
|
|
3
4
|
|
|
4
5
|
const PIPE = rxjs.pipe(
|
|
5
|
-
|
|
6
|
+
rx.map((value) => {
|
|
6
7
|
let data
|
|
7
8
|
if (value && typeof value === 'string') {
|
|
8
9
|
if (value.charAt(0) !== '{' && value.charAt(0) !== '[') {
|
|
@@ -17,7 +18,7 @@ const PIPE = rxjs.pipe(
|
|
|
17
18
|
|
|
18
19
|
return data
|
|
19
20
|
}),
|
|
20
|
-
|
|
21
|
+
rx.distinctUntilChanged(),
|
|
21
22
|
)
|
|
22
23
|
|
|
23
24
|
class Listener {
|
package/src/utils/utils.js
CHANGED
|
@@ -79,7 +79,7 @@ export function setTimeout(callback, timeoutDuration) {
|
|
|
79
79
|
|
|
80
80
|
export function setInterval(callback, intervalDuration) {
|
|
81
81
|
if (intervalDuration !== null) {
|
|
82
|
-
return
|
|
82
|
+
return setInterval(callback, intervalDuration)
|
|
83
83
|
} else {
|
|
84
84
|
return -1
|
|
85
85
|
}
|