@abraca/dabra 1.0.17 → 1.0.18

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.
@@ -3100,8 +3100,11 @@ var AbracadabraProvider = class AbracadabraProvider extends AbracadabraBaseProvi
3100
3100
  }
3101
3101
  destroy() {
3102
3102
  this.document.off("subdocs", this.boundHandleYSubdocsChange);
3103
+ const childIds = [...this.childProviders.keys()];
3103
3104
  for (const provider of this.childProviders.values()) provider.destroy();
3104
3105
  this.childProviders.clear();
3106
+ const wsProviderMap = this.configuration.websocketProvider?.configuration?.providerMap;
3107
+ if (wsProviderMap) for (const childId of childIds) wsProviderMap.delete(childId);
3105
3108
  this.offlineStore?.destroy();
3106
3109
  this.offlineStore = null;
3107
3110
  super.destroy();
@@ -8419,7 +8422,9 @@ var BackgroundSyncManager = class extends EventEmitter {
8419
8422
  this.opts = {
8420
8423
  concurrency: opts?.concurrency ?? 2,
8421
8424
  syncTimeout: opts?.syncTimeout ?? 15e3,
8422
- prefetchFiles: opts?.prefetchFiles ?? true
8425
+ prefetchFiles: opts?.prefetchFiles ?? true,
8426
+ throttleMs: opts?.throttleMs ?? 50,
8427
+ maxRetries: opts?.maxRetries ?? 2
8423
8428
  };
8424
8429
  let serverOrigin = "default";
8425
8430
  try {
@@ -8453,7 +8458,38 @@ var BackgroundSyncManager = class extends EventEmitter {
8453
8458
  for (const [docId, v] of entries) updatedAtMap.set(docId, v?.updatedAt ?? v?.createdAt ?? 0);
8454
8459
  this._prefetchCovers(entries).catch(() => null);
8455
8460
  const queue = this._buildQueue(entries);
8456
- await Promise.all(queue.map((docId) => this._syncWithSemaphore(docId, updatedAtMap.get(docId) ?? 0)));
8461
+ const failed = [];
8462
+ let idx = 0;
8463
+ const next = async () => {
8464
+ while (idx < queue.length) {
8465
+ if (this._destroyed) return;
8466
+ const docId = queue[idx++];
8467
+ const updatedAt = updatedAtMap.get(docId) ?? 0;
8468
+ if (!await this._syncWithSemaphore(docId, updatedAt)) failed.push(docId);
8469
+ if (this.opts.throttleMs > 0 && idx < queue.length) await new Promise((r) => setTimeout(r, this.opts.throttleMs));
8470
+ }
8471
+ };
8472
+ const workers = Array.from({ length: this.opts.concurrency }, () => next());
8473
+ await Promise.all(workers);
8474
+ for (let retry = 0; retry < this.opts.maxRetries && failed.length > 0; retry++) {
8475
+ if (this._destroyed) return;
8476
+ const batch = failed.splice(0, failed.length);
8477
+ const backoff = 2e3 * 2 ** retry;
8478
+ await new Promise((r) => setTimeout(r, backoff));
8479
+ idx = 0;
8480
+ const retryQueue = batch;
8481
+ const retryNext = async () => {
8482
+ while (idx < retryQueue.length) {
8483
+ if (this._destroyed) return;
8484
+ const docId = retryQueue[idx++];
8485
+ const updatedAt = updatedAtMap.get(docId) ?? 0;
8486
+ if (!await this._syncWithSemaphore(docId, updatedAt)) failed.push(docId);
8487
+ if (this.opts.throttleMs > 0 && idx < retryQueue.length) await new Promise((r) => setTimeout(r, this.opts.throttleMs));
8488
+ }
8489
+ };
8490
+ const retryWorkers = Array.from({ length: this.opts.concurrency }, () => retryNext());
8491
+ await Promise.all(retryWorkers);
8492
+ }
8457
8493
  }
8458
8494
  /** Sync a single document by ID. */
8459
8495
  async syncDoc(docId) {
@@ -8534,15 +8570,16 @@ var BackgroundSyncManager = class extends EventEmitter {
8534
8570
  items.sort((a, b) => b.priority - a.priority);
8535
8571
  return items.map((i) => i.docId);
8536
8572
  }
8573
+ /** Returns true on success (or skip), false on error. */
8537
8574
  async _syncWithSemaphore(docId, updatedAt) {
8538
- if (this._destroyed) return;
8575
+ if (this._destroyed) return true;
8539
8576
  const existing = this.syncStates.get(docId);
8540
8577
  if (existing && existing.status === "synced" && existing.lastSynced !== null && existing.lastSynced >= updatedAt) {
8541
8578
  this.emit("stateChanged", {
8542
8579
  docId,
8543
8580
  state: existing
8544
8581
  });
8545
- return;
8582
+ return true;
8546
8583
  }
8547
8584
  await this.semaphore.acquire();
8548
8585
  try {
@@ -8553,6 +8590,7 @@ var BackgroundSyncManager = class extends EventEmitter {
8553
8590
  docId,
8554
8591
  state
8555
8592
  });
8593
+ return state.status !== "error";
8556
8594
  } finally {
8557
8595
  this.semaphore.release();
8558
8596
  }