@nxtedition/deepstream.io-client-js 23.4.36 → 23.4.38

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 CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@nxtedition/deepstream.io-client-js",
3
- "version": "23.4.36",
3
+ "version": "23.4.38",
4
4
  "description": "the javascript client for deepstream.io",
5
5
  "homepage": "http://deepstream.io",
6
6
  "bugs": {
@@ -73,8 +73,6 @@ class RecordHandler {
73
73
  }
74
74
 
75
75
  _prune()
76
-
77
- this._syncAll = this._syncAll.bind(this)
78
76
  }
79
77
 
80
78
  _onRef(rec) {
@@ -163,121 +161,55 @@ class RecordHandler {
163
161
  }
164
162
  }
165
163
 
166
- sync(options) {
167
- return new Promise((resolve, reject) => {
168
- const timeoutValue = options?.timeout ?? 2 * 60e3
169
- const signal = options?.signal
170
-
171
- if (signal?.aborted) {
172
- reject(new utils.AbortError())
173
- return
174
- }
175
-
176
- let done = false
177
- let token
178
- let timeoutHandle
179
-
180
- const records = [...this._pending]
181
- for (const rec of records) {
182
- rec.ref()
183
- }
164
+ sync() {
165
+ return new Promise((resolve) => {
166
+ let counter = 0
184
167
 
185
- const onDone = (val) => {
186
- if (done) {
168
+ const onUpdate = (rec) => {
169
+ if (rec.pending) {
187
170
  return
188
171
  }
189
172
 
190
- done = true
191
-
192
- signal?.removeEventListener('abort', onAbort)
193
-
194
- if (timeoutHandle) {
195
- timers.clearTimeout(timeoutHandle)
196
- timeoutHandle = null
197
- }
198
-
199
- if (token) {
200
- this._syncEmitter.off(token, onToken)
201
- token = null
202
- }
173
+ rec.unsubscribe(onUpdate)
174
+ rec.unref()
175
+ counter -= 1
203
176
 
204
- for (const rec of records) {
205
- rec.unref()
177
+ if (counter > 0) {
178
+ return
206
179
  }
207
180
 
208
- resolve(val)
209
- }
210
-
211
- const onToken = () => {
212
- onDone(true)
213
- }
214
-
215
- const onAbort = () => {
216
- onDone(Promise.reject(new utils.AbortError()))
217
- }
218
-
219
- const onTimeout = () => {
220
- const elapsed = Date.now() - this._connected
221
- if (elapsed < timeoutValue) {
222
- timeoutHandle = timers.setTimeout(onTimeout, timeoutValue - elapsed)
223
- } else {
224
- for (const rec of records.filter((rec) => !rec.isReady)) {
225
- this._client._$onError(C.TOPIC.RECORD, C.EVENT.TIMEOUT, 'record timeout', [
226
- rec.name,
227
- rec.version,
228
- rec.state,
229
- ...(rec._entry ?? []),
230
- ])
231
- }
232
-
233
- this._client._$onError(C.TOPIC.RECORD, C.EVENT.TIMEOUT, 'sync timeout', [token])
181
+ if (!this._syncQueue) {
182
+ this._syncQueue = []
183
+ queueMicrotask(() => {
184
+ const syncQueue = this._syncQueue
185
+ if (!syncQueue) {
186
+ return
187
+ }
188
+
189
+ const token = xuid()
190
+
191
+ this._syncQueue = null
192
+ this._syncEmitter.once(token, () => {
193
+ for (const callback of syncQueue) {
194
+ callback()
195
+ }
196
+ })
234
197
 
235
- onDone(false)
198
+ if (this._connected) {
199
+ this._connection.sendMsg(C.TOPIC.RECORD, C.ACTIONS.SYNC, [token])
200
+ }
201
+ })
236
202
  }
237
- }
238
203
 
239
- if (timeoutValue) {
240
- timeoutHandle = timers.setTimeout(onTimeout, timeoutValue)
204
+ this._syncQueue.push(resolve)
241
205
  }
242
206
 
243
- signal?.addEventListener('abort', onAbort)
244
-
245
- Promise.all(records.map((rec) => rec.when())).then(
246
- () => {
247
- if (done) {
248
- return
249
- }
250
-
251
- if (!this._syncQueue) {
252
- this._syncQueue = []
253
- queueMicrotask(this._syncAll)
254
- }
255
-
256
- this._syncQueue.push(onToken)
257
- },
258
- (err) => onDone(Promise.reject(err))
259
- )
260
- })
261
- }
262
-
263
- _syncAll() {
264
- if (!this._syncQueue) {
265
- return
266
- }
267
-
268
- const syncQueue = this._syncQueue
269
- const token = xuid()
270
-
271
- this._syncQueue = null
272
- this._syncEmitter.once(token, () => {
273
- for (const callback of syncQueue) {
274
- callback()
207
+ for (const rec of this._pending) {
208
+ rec.ref()
209
+ rec.subscribe(onUpdate)
210
+ counter += 1
275
211
  }
276
212
  })
277
-
278
- if (this._connected) {
279
- this._connection.sendMsg(C.TOPIC.RECORD, C.ACTIONS.SYNC, [token])
280
- }
281
213
  }
282
214
 
283
215
  set(name, ...args) {
@@ -19,6 +19,7 @@ class Record {
19
19
  this._refs = 1
20
20
  this._subscribed = false
21
21
  this._subscriptions = []
22
+ this._subscriptionsEmitting = false
22
23
  this._updating = null
23
24
  this._patches = null
24
25
  this._pending = false
@@ -72,12 +73,22 @@ class Record {
72
73
  }
73
74
 
74
75
  subscribe(fn) {
76
+ if (this._subscriptionsEmitting) {
77
+ this._subscriptions = this._subscriptions.slice()
78
+ this._subscriptionsEmitting = false
79
+ }
80
+
75
81
  this._subscriptions.push(fn)
76
82
 
77
83
  return this
78
84
  }
79
85
 
80
86
  unsubscribe(fn) {
87
+ if (this._subscriptionsEmitting) {
88
+ this._subscriptions = this._subscriptions.slice()
89
+ this._subscriptionsEmitting = false
90
+ }
91
+
81
92
  const idx = this._subscriptions.indexOf(fn)
82
93
  if (idx !== -1) {
83
94
  this._subscriptions.splice(idx, 1)
@@ -200,8 +211,13 @@ class Record {
200
211
  }
201
212
 
202
213
  _emitUpdate() {
203
- for (const fn of this._subscriptions.slice()) {
204
- fn(this)
214
+ try {
215
+ this._subscriptionsEmitting = true
216
+ for (const fn of this._subscriptions) {
217
+ fn(this)
218
+ }
219
+ } finally {
220
+ this._subscriptionsEmitting = false
205
221
  }
206
222
  }
207
223
 
@@ -266,6 +282,7 @@ class Record {
266
282
  if (!this._pending) {
267
283
  this._pending = true
268
284
  this._handler._onPending(this)
285
+ this._emitUpdate()
269
286
  }
270
287
 
271
288
  const connection = this._handler._connection
@@ -305,6 +322,7 @@ class Record {
305
322
  const prevData = this._data
306
323
  const prevVersion = this._version
307
324
  const prevState = this._state
325
+ const prevPending = this._pending
308
326
 
309
327
  if (this._updating?.delete(version)) {
310
328
  this._handler._stats.updating -= 1
@@ -337,7 +355,12 @@ class Record {
337
355
  this._state = this._version.charAt(0) === 'I' ? Record.STATE.STALE : Record.STATE.SERVER
338
356
  }
339
357
 
340
- if (this._data !== prevData || this._version !== prevVersion || this._state !== prevState) {
358
+ if (
359
+ this._data !== prevData ||
360
+ this._version !== prevVersion ||
361
+ this._state !== prevState ||
362
+ this._pending !== prevPending
363
+ ) {
341
364
  this._emitUpdate()
342
365
  }
343
366
  }