@logspace/sdk 1.1.8 → 1.1.10
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/logspace.esm.js +77 -4
- package/logspace.esm.js.map +1 -1
- package/logspace.iife.js +1 -1
- package/logspace.iife.js.map +1 -1
- package/logspace.umd.js +1 -1
- package/logspace.umd.js.map +1 -1
- package/package.json +1 -1
- package/sdk/storage/indexed-db.d.ts +10 -0
- package/sdk/types.d.ts +9 -7
package/logspace.esm.js
CHANGED
|
@@ -14490,7 +14490,7 @@ async function updatePendingSessionRetry(sessionId) {
|
|
|
14490
14490
|
async function cleanupOldPendingSessions() {
|
|
14491
14491
|
if (!isIndexedDBAvailable()) return;
|
|
14492
14492
|
const MAX_AGE_MS = 7 * 24 * 60 * 60 * 1e3;
|
|
14493
|
-
const MAX_RETRIES =
|
|
14493
|
+
const MAX_RETRIES = 10;
|
|
14494
14494
|
const now = Date.now();
|
|
14495
14495
|
try {
|
|
14496
14496
|
const sessions = await getPendingSessions();
|
|
@@ -14505,6 +14505,18 @@ async function cleanupOldPendingSessions() {
|
|
|
14505
14505
|
console.warn("[LogSpace] Failed to cleanup old sessions:", error);
|
|
14506
14506
|
}
|
|
14507
14507
|
}
|
|
14508
|
+
function getBackoffInterval(retryCount) {
|
|
14509
|
+
const baseMs = 60 * 1e3;
|
|
14510
|
+
const maxMs = 60 * 60 * 1e3;
|
|
14511
|
+
const backoff = Math.min(baseMs * Math.pow(2, retryCount), maxMs);
|
|
14512
|
+
return backoff;
|
|
14513
|
+
}
|
|
14514
|
+
function isReadyForRetry(session2) {
|
|
14515
|
+
if (!session2.lastRetryAt) return true;
|
|
14516
|
+
const backoffMs = getBackoffInterval(session2.retryCount);
|
|
14517
|
+
const timeSinceLastRetry = Date.now() - session2.lastRetryAt;
|
|
14518
|
+
return timeSinceLastRetry >= backoffMs;
|
|
14519
|
+
}
|
|
14508
14520
|
function closeDB() {
|
|
14509
14521
|
if (db) {
|
|
14510
14522
|
db.close();
|
|
@@ -14532,7 +14544,9 @@ let idleTimer = null;
|
|
|
14532
14544
|
let durationTimer = null;
|
|
14533
14545
|
let checkpointTimer = null;
|
|
14534
14546
|
let visibilityTimer = null;
|
|
14547
|
+
let pendingRetryTimer = null;
|
|
14535
14548
|
let lastMouseMoveTime = 0;
|
|
14549
|
+
const PENDING_RETRY_INTERVAL = 2 * 60 * 1e3;
|
|
14536
14550
|
let samplingTriggered = false;
|
|
14537
14551
|
let samplingTriggerType = null;
|
|
14538
14552
|
let samplingFirstTriggerTime = null;
|
|
@@ -14548,15 +14562,20 @@ const processedRecoverySessionIds = /* @__PURE__ */ new Set();
|
|
|
14548
14562
|
const RECORDING_QUALITY_PRESETS = {
|
|
14549
14563
|
low: {
|
|
14550
14564
|
maskAllInputs: false,
|
|
14551
|
-
checkoutEveryNth:
|
|
14565
|
+
checkoutEveryNth: 1e3,
|
|
14552
14566
|
recordCanvas: false
|
|
14553
14567
|
},
|
|
14554
14568
|
medium: {
|
|
14555
14569
|
maskAllInputs: false,
|
|
14556
|
-
checkoutEveryNth:
|
|
14570
|
+
checkoutEveryNth: 500,
|
|
14557
14571
|
recordCanvas: false
|
|
14558
14572
|
},
|
|
14559
14573
|
high: {
|
|
14574
|
+
maskAllInputs: false,
|
|
14575
|
+
checkoutEveryNth: 300,
|
|
14576
|
+
recordCanvas: false
|
|
14577
|
+
},
|
|
14578
|
+
extrahigh: {
|
|
14560
14579
|
maskAllInputs: false,
|
|
14561
14580
|
checkoutEveryNth: 150,
|
|
14562
14581
|
recordCanvas: false
|
|
@@ -14578,7 +14597,7 @@ const DEFAULT_CONFIG = {
|
|
|
14578
14597
|
},
|
|
14579
14598
|
rrweb: {
|
|
14580
14599
|
maskAllInputs: false,
|
|
14581
|
-
checkoutEveryNth:
|
|
14600
|
+
checkoutEveryNth: 500,
|
|
14582
14601
|
// Default to 'medium' quality
|
|
14583
14602
|
recordCanvas: false
|
|
14584
14603
|
},
|
|
@@ -15192,6 +15211,48 @@ function stopCheckpointTimer() {
|
|
|
15192
15211
|
checkpointTimer = null;
|
|
15193
15212
|
}
|
|
15194
15213
|
}
|
|
15214
|
+
function startPendingRetryTimer() {
|
|
15215
|
+
if (pendingRetryTimer || !isIndexedDBAvailable()) return;
|
|
15216
|
+
pendingRetryTimer = setInterval(async () => {
|
|
15217
|
+
if (!config?.serverUrl) return;
|
|
15218
|
+
try {
|
|
15219
|
+
const pendingSessions = await getPendingSessions();
|
|
15220
|
+
if (pendingSessions.length === 0) return;
|
|
15221
|
+
const readySessions = pendingSessions.filter(isReadyForRetry);
|
|
15222
|
+
if (readySessions.length === 0) return;
|
|
15223
|
+
if (config.debug) {
|
|
15224
|
+
console.log(
|
|
15225
|
+
`[LogSpace] Periodic retry: ${readySessions.length} of ${pendingSessions.length} pending sessions ready`
|
|
15226
|
+
);
|
|
15227
|
+
}
|
|
15228
|
+
for (const stored of readySessions) {
|
|
15229
|
+
try {
|
|
15230
|
+
await sendPayloadToServer(stored.data);
|
|
15231
|
+
await removePendingSession(stored.id);
|
|
15232
|
+
if (config.debug) {
|
|
15233
|
+
console.log("[LogSpace] Pending session sent:", stored.id);
|
|
15234
|
+
}
|
|
15235
|
+
} catch (error) {
|
|
15236
|
+
await updatePendingSessionRetry(stored.id);
|
|
15237
|
+
if (config.debug) {
|
|
15238
|
+
const nextBackoff = Math.ceil(getBackoffInterval(stored.retryCount + 1) / 1e3);
|
|
15239
|
+
console.warn(`[LogSpace] Retry failed for ${stored.id}, next retry in ${nextBackoff}s`);
|
|
15240
|
+
}
|
|
15241
|
+
}
|
|
15242
|
+
}
|
|
15243
|
+
} catch (error) {
|
|
15244
|
+
if (config?.debug) {
|
|
15245
|
+
console.warn("[LogSpace] Periodic retry check failed:", error);
|
|
15246
|
+
}
|
|
15247
|
+
}
|
|
15248
|
+
}, PENDING_RETRY_INTERVAL);
|
|
15249
|
+
}
|
|
15250
|
+
function stopPendingRetryTimer() {
|
|
15251
|
+
if (pendingRetryTimer) {
|
|
15252
|
+
clearInterval(pendingRetryTimer);
|
|
15253
|
+
pendingRetryTimer = null;
|
|
15254
|
+
}
|
|
15255
|
+
}
|
|
15195
15256
|
const EMERGENCY_BACKUP_KEY = "__logspace_emergency_backup";
|
|
15196
15257
|
const SAMPLING_STATE_KEY = "__logspace_sampling_state";
|
|
15197
15258
|
function saveSamplingState(sessionId) {
|
|
@@ -15842,6 +15903,16 @@ async function recoverPendingSessions() {
|
|
|
15842
15903
|
await removePendingSession(stored.id);
|
|
15843
15904
|
continue;
|
|
15844
15905
|
}
|
|
15906
|
+
if (!isReadyForRetry(stored)) {
|
|
15907
|
+
if (config.debug) {
|
|
15908
|
+
const backoffMs = getBackoffInterval(stored.retryCount);
|
|
15909
|
+
const waitTime = Math.ceil((backoffMs - (Date.now() - (stored.lastRetryAt || 0))) / 1e3);
|
|
15910
|
+
console.log(
|
|
15911
|
+
`[LogSpace] Pending session ${stored.id} waiting for backoff (${waitTime}s remaining, retry #${stored.retryCount})`
|
|
15912
|
+
);
|
|
15913
|
+
}
|
|
15914
|
+
continue;
|
|
15915
|
+
}
|
|
15845
15916
|
try {
|
|
15846
15917
|
await sendPayloadToServer(stored.data);
|
|
15847
15918
|
processedRecoverySessionIds.add(stored.id);
|
|
@@ -15934,6 +16005,7 @@ const LogSpace = {
|
|
|
15934
16005
|
}
|
|
15935
16006
|
unloadHandled = false;
|
|
15936
16007
|
isNavigatingAway = false;
|
|
16008
|
+
startPendingRetryTimer();
|
|
15937
16009
|
this.startSession();
|
|
15938
16010
|
recoverPendingSessions().catch(() => {
|
|
15939
16011
|
});
|
|
@@ -16305,6 +16377,7 @@ const LogSpace = {
|
|
|
16305
16377
|
visibilityTimer = null;
|
|
16306
16378
|
}
|
|
16307
16379
|
stopCheckpointTimer();
|
|
16380
|
+
stopPendingRetryTimer();
|
|
16308
16381
|
stopSamplingTrimTimer();
|
|
16309
16382
|
if (config?.capture.rrweb) {
|
|
16310
16383
|
stopRRWebRecording();
|