@amplitude/session-replay-browser 1.2.1 → 1.2.2

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.
Files changed (63) hide show
  1. package/lib/cjs/config.d.ts +0 -3
  2. package/lib/cjs/config.d.ts.map +1 -1
  3. package/lib/cjs/config.js +0 -9
  4. package/lib/cjs/config.js.map +1 -1
  5. package/lib/cjs/identifiers.d.ts +9 -0
  6. package/lib/cjs/identifiers.d.ts.map +1 -0
  7. package/lib/cjs/identifiers.js +18 -0
  8. package/lib/cjs/identifiers.js.map +1 -0
  9. package/lib/cjs/session-idb-store.d.ts +15 -0
  10. package/lib/cjs/session-idb-store.d.ts.map +1 -0
  11. package/lib/cjs/session-idb-store.js +107 -0
  12. package/lib/cjs/session-idb-store.js.map +1 -0
  13. package/lib/cjs/session-replay.d.ts +6 -23
  14. package/lib/cjs/session-replay.d.ts.map +1 -1
  15. package/lib/cjs/session-replay.js +62 -312
  16. package/lib/cjs/session-replay.js.map +1 -1
  17. package/lib/cjs/track-destination.d.ts +28 -0
  18. package/lib/cjs/track-destination.d.ts.map +1 -0
  19. package/lib/cjs/track-destination.js +204 -0
  20. package/lib/cjs/track-destination.js.map +1 -0
  21. package/lib/cjs/typings/session-replay.d.ts +27 -7
  22. package/lib/cjs/typings/session-replay.d.ts.map +1 -1
  23. package/lib/cjs/typings/session-replay.js.map +1 -1
  24. package/lib/esm/config.d.ts +0 -3
  25. package/lib/esm/config.d.ts.map +1 -1
  26. package/lib/esm/config.js +0 -9
  27. package/lib/esm/config.js.map +1 -1
  28. package/lib/esm/identifiers.d.ts +9 -0
  29. package/lib/esm/identifiers.d.ts.map +1 -0
  30. package/lib/esm/identifiers.js +16 -0
  31. package/lib/esm/identifiers.js.map +1 -0
  32. package/lib/esm/session-idb-store.d.ts +15 -0
  33. package/lib/esm/session-idb-store.d.ts.map +1 -0
  34. package/lib/esm/session-idb-store.js +105 -0
  35. package/lib/esm/session-idb-store.js.map +1 -0
  36. package/lib/esm/session-replay.d.ts +6 -23
  37. package/lib/esm/session-replay.d.ts.map +1 -1
  38. package/lib/esm/session-replay.js +66 -316
  39. package/lib/esm/session-replay.js.map +1 -1
  40. package/lib/esm/track-destination.d.ts +28 -0
  41. package/lib/esm/track-destination.d.ts.map +1 -0
  42. package/lib/esm/track-destination.js +202 -0
  43. package/lib/esm/track-destination.js.map +1 -0
  44. package/lib/esm/typings/session-replay.d.ts +27 -7
  45. package/lib/esm/typings/session-replay.d.ts.map +1 -1
  46. package/lib/esm/typings/session-replay.js.map +1 -1
  47. package/lib/scripts/amplitude-min.js +1 -1
  48. package/lib/scripts/amplitude-min.js.gz +0 -0
  49. package/lib/scripts/amplitude-min.umd.js +1 -1
  50. package/lib/scripts/amplitude-min.umd.js.gz +0 -0
  51. package/lib/scripts/config.d.ts +0 -3
  52. package/lib/scripts/config.d.ts.map +1 -1
  53. package/lib/scripts/identifiers.d.ts +9 -0
  54. package/lib/scripts/identifiers.d.ts.map +1 -0
  55. package/lib/scripts/session-idb-store.d.ts +15 -0
  56. package/lib/scripts/session-idb-store.d.ts.map +1 -0
  57. package/lib/scripts/session-replay.d.ts +6 -23
  58. package/lib/scripts/session-replay.d.ts.map +1 -1
  59. package/lib/scripts/track-destination.d.ts +28 -0
  60. package/lib/scripts/track-destination.d.ts.map +1 -0
  61. package/lib/scripts/typings/session-replay.d.ts +27 -7
  62. package/lib/scripts/typings/session-replay.d.ts.map +1 -1
  63. package/package.json +2 -2
@@ -3,25 +3,20 @@ exports.SessionReplay = void 0;
3
3
  var tslib_1 = require("tslib");
4
4
  var analytics_client_common_1 = require("@amplitude/analytics-client-common");
5
5
  var analytics_core_1 = require("@amplitude/analytics-core");
6
- var analytics_types_1 = require("@amplitude/analytics-types");
7
6
  var rrweb_1 = require("@amplitude/rrweb");
8
- var IDBKeyVal = tslib_1.__importStar(require("idb-keyval"));
9
7
  var config_1 = require("./config");
10
8
  var constants_1 = require("./constants");
11
9
  var helpers_1 = require("./helpers");
12
- var messages_1 = require("./messages");
10
+ var identifiers_1 = require("./identifiers");
11
+ var session_idb_store_1 = require("./session-idb-store");
12
+ var track_destination_1 = require("./track-destination");
13
13
  var session_replay_1 = require("./typings/session-replay");
14
- var version_1 = require("./version");
15
14
  var SessionReplay = /** @class */ (function () {
16
15
  function SessionReplay() {
17
16
  var _this = this;
18
17
  this.name = '@amplitude/session-replay-browser';
19
- this.storageKey = '';
20
- this.retryTimeout = 1000;
21
18
  this.events = [];
22
19
  this.currentSequenceId = 0;
23
- this.scheduled = null;
24
- this.queue = [];
25
20
  this.stopRecordingEvents = null;
26
21
  this.maxPersistedEventsSize = constants_1.MAX_EVENT_LIST_SIZE_IN_BYTES;
27
22
  this.interval = constants_1.MIN_INTERVAL;
@@ -52,6 +47,7 @@ var SessionReplay = /** @class */ (function () {
52
47
  return false;
53
48
  };
54
49
  this.loggerProvider = new analytics_core_1.Logger();
50
+ this.trackDestination = new track_destination_1.SessionReplayTrackDestination({ loggerProvider: this.loggerProvider });
55
51
  }
56
52
  SessionReplay.prototype.init = function (apiKey, options) {
57
53
  return (0, analytics_core_1.returnWrapper)(this._init(apiKey, options));
@@ -64,8 +60,14 @@ var SessionReplay = /** @class */ (function () {
64
60
  case 0:
65
61
  this.config = new config_1.SessionReplayConfig(apiKey, options);
66
62
  this.loggerProvider = this.config.loggerProvider;
63
+ this.identifiers = new identifiers_1.SessionIdentifiers(options, this.loggerProvider);
64
+ // Update logger provider in trackDestination
65
+ this.trackDestination.setLoggerProvider(this.loggerProvider);
66
+ this.sessionIDBStore = new session_idb_store_1.SessionReplaySessionIDBStore({
67
+ loggerProvider: this.loggerProvider,
68
+ apiKey: this.config.apiKey,
69
+ });
67
70
  this.loggerProvider.log('Installing @amplitude/session-replay-browser.');
68
- this.storageKey = "".concat(constants_1.STORAGE_PREFIX, "_").concat(this.config.apiKey.substring(0, 10));
69
71
  globalScope = (0, analytics_client_common_1.getGlobalScope)();
70
72
  if (globalScope) {
71
73
  globalScope.addEventListener('blur', this.blurListener);
@@ -82,24 +84,24 @@ var SessionReplay = /** @class */ (function () {
82
84
  });
83
85
  };
84
86
  SessionReplay.prototype.setSessionId = function (sessionId, deviceId) {
85
- if (!this.config) {
87
+ if (!this.identifiers) {
86
88
  this.loggerProvider.error('Session replay init has not been called, cannot set session id.');
87
89
  return;
88
90
  }
89
91
  if (deviceId) {
90
- this.config.deviceId = deviceId;
92
+ this.identifiers.deviceId = deviceId;
91
93
  }
92
94
  // use a consistent device id.
93
95
  var deviceIdForReplayId = this.getDeviceId();
94
96
  if (sessionId && deviceIdForReplayId) {
95
- this.config.sessionReplayId = (0, helpers_1.generateSessionReplayId)(sessionId, deviceIdForReplayId);
97
+ this.identifiers.sessionReplayId = (0, helpers_1.generateSessionReplayId)(sessionId, deviceIdForReplayId);
96
98
  }
97
99
  else {
98
100
  this.loggerProvider.error('Must provide either session replay id or session id when starting a new session.');
99
101
  return;
100
102
  }
101
- this.stopRecordingAndSendEvents(this.config.sessionId);
102
- this.config.sessionId = sessionId;
103
+ this.stopRecordingAndSendEvents(this.identifiers.sessionId);
104
+ this.identifiers.sessionId = sessionId;
103
105
  this.events = [];
104
106
  this.currentSequenceId = 0;
105
107
  this.recordEvents();
@@ -115,7 +117,7 @@ var SessionReplay = /** @class */ (function () {
115
117
  };
116
118
  SessionReplay.prototype.getSessionReplayProperties = function () {
117
119
  var _a;
118
- if (!this.config) {
120
+ if (!this.config || !this.identifiers) {
119
121
  this.loggerProvider.error('Session replay init has not been called, cannot get session recording properties.');
120
122
  return {};
121
123
  }
@@ -125,7 +127,7 @@ var SessionReplay = /** @class */ (function () {
125
127
  var shouldRecord = this.getShouldRecord(ignoreFocus);
126
128
  if (shouldRecord) {
127
129
  var eventProperties = (_a = {},
128
- _a[constants_1.DEFAULT_SESSION_REPLAY_PROPERTY] = this.config.sessionReplayId ? this.config.sessionReplayId : null,
130
+ _a[constants_1.DEFAULT_SESSION_REPLAY_PROPERTY] = this.identifiers.sessionReplayId ? this.identifiers.sessionReplayId : null,
129
131
  _a);
130
132
  if (this.config.debugMode) {
131
133
  eventProperties[constants_1.SESSION_REPLAY_DEBUG_PROPERTY] = this.getSessionReplayDebugPropertyValue();
@@ -144,7 +146,7 @@ var SessionReplay = /** @class */ (function () {
144
146
  var typedError = error;
145
147
  this.loggerProvider.warn("Error occurred while stopping recording: ".concat(typedError.toString()));
146
148
  }
147
- var sessionIdToSend = sessionId || ((_a = this.config) === null || _a === void 0 ? void 0 : _a.sessionId);
149
+ var sessionIdToSend = sessionId || ((_a = this.identifiers) === null || _a === void 0 ? void 0 : _a.sessionId);
148
150
  if (this.events.length && sessionIdToSend) {
149
151
  this.sendEventsList({
150
152
  events: this.events,
@@ -157,25 +159,30 @@ var SessionReplay = /** @class */ (function () {
157
159
  var _a;
158
160
  if (shouldSendStoredEvents === void 0) { shouldSendStoredEvents = false; }
159
161
  return tslib_1.__awaiter(this, void 0, void 0, function () {
160
- var storedReplaySessions, storedSequencesForSession, storedSeqId, lastSequence;
161
- return tslib_1.__generator(this, function (_b) {
162
- switch (_b.label) {
162
+ var storedReplaySessions, _b, storedSequencesForSession, storedSeqId, lastSequence;
163
+ return tslib_1.__generator(this, function (_c) {
164
+ switch (_c.label) {
163
165
  case 0:
164
166
  this.timeAtLastSend = Date.now(); // Initialize this so we have a point of comparison when events are recorded
165
- if (!((_a = this.config) === null || _a === void 0 ? void 0 : _a.sessionId)) {
167
+ if (!((_a = this.identifiers) === null || _a === void 0 ? void 0 : _a.sessionId)) {
166
168
  this.loggerProvider.warn("Session is not being recorded due to lack of session id.");
167
169
  return [2 /*return*/];
168
170
  }
169
- return [4 /*yield*/, this.getAllSessionEventsFromStore()];
171
+ _b = this.sessionIDBStore;
172
+ if (!_b) return [3 /*break*/, 2];
173
+ return [4 /*yield*/, this.sessionIDBStore.getAllSessionDataFromStore()];
170
174
  case 1:
171
- storedReplaySessions = _b.sent();
175
+ _b = (_c.sent());
176
+ _c.label = 2;
177
+ case 2:
178
+ storedReplaySessions = _b;
172
179
  // This resolves a timing issue when focus is fired multiple times in short succession,
173
180
  // we only want the rest of this function to run once. We can be sure that initialize has
174
181
  // already been called if this.stopRecordingEvents is defined
175
182
  if (this.stopRecordingEvents) {
176
183
  return [2 /*return*/];
177
184
  }
178
- storedSequencesForSession = storedReplaySessions && storedReplaySessions[this.config.sessionId];
185
+ storedSequencesForSession = storedReplaySessions && storedReplaySessions[this.identifiers.sessionId];
179
186
  if (storedReplaySessions && storedSequencesForSession && storedSequencesForSession.sessionSequences) {
180
187
  storedSeqId = storedSequencesForSession.currentSequenceId;
181
188
  lastSequence = storedSequencesForSession.sessionSequences[storedSeqId];
@@ -209,30 +216,30 @@ var SessionReplay = /** @class */ (function () {
209
216
  };
210
217
  SessionReplay.prototype.getShouldRecord = function (ignoreFocus) {
211
218
  if (ignoreFocus === void 0) { ignoreFocus = false; }
212
- if (!this.config) {
219
+ if (!this.identifiers || !this.config) {
213
220
  this.loggerProvider.error("Session is not being recorded due to lack of config, please call sessionReplay.init.");
214
221
  return false;
215
222
  }
216
223
  var globalScope = (0, analytics_client_common_1.getGlobalScope)();
217
224
  if (!ignoreFocus && globalScope && globalScope.document && !globalScope.document.hasFocus()) {
218
- if (this.config.sessionId) {
219
- this.loggerProvider.log("Session ".concat(this.config.sessionId, " temporarily not recording due to lack of browser focus."));
225
+ if (this.identifiers.sessionId) {
226
+ this.loggerProvider.log("Session ".concat(this.identifiers.sessionId, " temporarily not recording due to lack of browser focus."));
220
227
  }
221
228
  return false;
222
229
  }
223
230
  else if (this.shouldOptOut()) {
224
- if (this.config.sessionId) {
225
- this.loggerProvider.log("Opting session ".concat(this.config.sessionId, " out of recording due to optOut config."));
231
+ if (this.identifiers.sessionId) {
232
+ this.loggerProvider.log("Opting session ".concat(this.identifiers.sessionId, " out of recording due to optOut config."));
226
233
  }
227
234
  return false;
228
235
  }
229
- else if (!this.config.sessionId) {
236
+ else if (!this.identifiers.sessionId) {
230
237
  this.loggerProvider.warn("Session is not being recorded due to lack of session id.");
231
238
  return false;
232
239
  }
233
- var isInSample = (0, helpers_1.isSessionInSample)(this.config.sessionId, this.getSampleRate());
240
+ var isInSample = (0, helpers_1.isSessionInSample)(this.identifiers.sessionId, this.config.sampleRate);
234
241
  if (!isInSample) {
235
- this.loggerProvider.log("Opting session ".concat(this.config.sessionId, " out of recording due to sample rate."));
242
+ this.loggerProvider.log("Opting session ".concat(this.identifiers.sessionId, " out of recording due to sample rate."));
236
243
  }
237
244
  return isInSample;
238
245
  };
@@ -248,7 +255,7 @@ var SessionReplay = /** @class */ (function () {
248
255
  var seq = storedSequences[storedSeqId];
249
256
  var numericSeqId = parseInt(storedSeqId, 10);
250
257
  var numericSessionId = parseInt(sessionId, 10);
251
- if (numericSessionId === ((_a = this.config) === null || _a === void 0 ? void 0 : _a.sessionId) && numericSeqId === this.currentSequenceId) {
258
+ if (numericSessionId === ((_a = this.identifiers) === null || _a === void 0 ? void 0 : _a.sessionId) && numericSeqId === this.currentSequenceId) {
252
259
  continue;
253
260
  }
254
261
  if (seq.events && seq.events.length && seq.status === session_replay_1.RecordingStatus.RECORDING) {
@@ -265,7 +272,7 @@ var SessionReplay = /** @class */ (function () {
265
272
  var _this = this;
266
273
  var _a;
267
274
  var shouldRecord = this.getShouldRecord();
268
- var sessionId = (_a = this.config) === null || _a === void 0 ? void 0 : _a.sessionId;
275
+ var sessionId = (_a = this.identifiers) === null || _a === void 0 ? void 0 : _a.sessionId;
269
276
  if (!shouldRecord || !sessionId) {
270
277
  return;
271
278
  }
@@ -278,7 +285,7 @@ var SessionReplay = /** @class */ (function () {
278
285
  }
279
286
  var eventString = JSON.stringify(event);
280
287
  var shouldSplit = _this.shouldSplitEventsList(eventString);
281
- if (shouldSplit) {
288
+ if (shouldSplit && _this.config) {
282
289
  _this.sendEventsList({
283
290
  events: _this.events,
284
291
  sequenceId: _this.currentSequenceId,
@@ -288,7 +295,8 @@ var SessionReplay = /** @class */ (function () {
288
295
  _this.currentSequenceId++;
289
296
  }
290
297
  _this.events.push(eventString);
291
- void _this.storeEventsForSession(_this.events, _this.currentSequenceId, sessionId);
298
+ _this.sessionIDBStore &&
299
+ void _this.sessionIDBStore.storeEventsForSession(_this.events, _this.currentSequenceId, sessionId);
292
300
  },
293
301
  packFn: rrweb_1.pack,
294
302
  maskAllInputs: true,
@@ -307,94 +315,22 @@ var SessionReplay = /** @class */ (function () {
307
315
  };
308
316
  SessionReplay.prototype.sendEventsList = function (_a) {
309
317
  var events = _a.events, sequenceId = _a.sequenceId, sessionId = _a.sessionId;
310
- this.addToQueue({
318
+ if (!this.config || !this.sessionIDBStore) {
319
+ this.loggerProvider.error("Session is not being recorded due to lack of config, please call sessionReplay.init.");
320
+ return;
321
+ }
322
+ this.trackDestination.sendEventsList({
311
323
  events: events,
312
324
  sequenceId: sequenceId,
313
- attempts: 0,
314
- timeout: 0,
315
325
  sessionId: sessionId,
326
+ flushMaxRetries: this.config.flushMaxRetries,
327
+ apiKey: this.config.apiKey,
328
+ deviceId: this.getDeviceId(),
329
+ sampleRate: this.config.sampleRate,
330
+ serverZone: this.config.serverZone,
331
+ onComplete: this.sessionIDBStore.cleanUpSessionEventsStore.bind(this.sessionIDBStore),
316
332
  });
317
333
  };
318
- SessionReplay.prototype.addToQueue = function () {
319
- var _this = this;
320
- var list = [];
321
- for (var _i = 0; _i < arguments.length; _i++) {
322
- list[_i] = arguments[_i];
323
- }
324
- var tryable = list.filter(function (context) {
325
- var _a;
326
- if (context.attempts < (((_a = _this.config) === null || _a === void 0 ? void 0 : _a.flushMaxRetries) || 0)) {
327
- context.attempts += 1;
328
- return true;
329
- }
330
- _this.completeRequest({
331
- context: context,
332
- err: "".concat(messages_1.MAX_RETRIES_EXCEEDED_MESSAGE, ", batch sequence id, ").concat(context.sequenceId),
333
- });
334
- return false;
335
- });
336
- tryable.forEach(function (context) {
337
- _this.queue = _this.queue.concat(context);
338
- if (context.timeout === 0) {
339
- _this.schedule(0);
340
- return;
341
- }
342
- setTimeout(function () {
343
- context.timeout = 0;
344
- _this.schedule(0);
345
- }, context.timeout);
346
- });
347
- };
348
- SessionReplay.prototype.schedule = function (timeout) {
349
- var _this = this;
350
- if (this.scheduled)
351
- return;
352
- this.scheduled = setTimeout(function () {
353
- void _this.flush(true).then(function () {
354
- if (_this.queue.length > 0) {
355
- _this.schedule(timeout);
356
- }
357
- });
358
- }, timeout);
359
- };
360
- SessionReplay.prototype.flush = function (useRetry) {
361
- if (useRetry === void 0) { useRetry = false; }
362
- return tslib_1.__awaiter(this, void 0, void 0, function () {
363
- var list, later;
364
- var _this = this;
365
- return tslib_1.__generator(this, function (_a) {
366
- switch (_a.label) {
367
- case 0:
368
- list = [];
369
- later = [];
370
- this.queue.forEach(function (context) { return (context.timeout === 0 ? list.push(context) : later.push(context)); });
371
- this.queue = later;
372
- if (this.scheduled) {
373
- clearTimeout(this.scheduled);
374
- this.scheduled = null;
375
- }
376
- return [4 /*yield*/, Promise.all(list.map(function (context) { return _this.send(context, useRetry); }))];
377
- case 1:
378
- _a.sent();
379
- return [2 /*return*/];
380
- }
381
- });
382
- });
383
- };
384
- SessionReplay.prototype.getSampleRate = function () {
385
- var _a;
386
- return ((_a = this.config) === null || _a === void 0 ? void 0 : _a.sampleRate) || constants_1.DEFAULT_SAMPLE_RATE;
387
- };
388
- SessionReplay.prototype.getServerUrl = function () {
389
- var _a, _b;
390
- if (((_a = this.config) === null || _a === void 0 ? void 0 : _a.serverZone) === analytics_types_1.ServerZone.STAGING) {
391
- return constants_1.SESSION_REPLAY_STAGING_URL;
392
- }
393
- if (((_b = this.config) === null || _b === void 0 ? void 0 : _b.serverZone) === analytics_types_1.ServerZone.EU) {
394
- return constants_1.SESSION_REPLAY_EU_URL;
395
- }
396
- return constants_1.SESSION_REPLAY_SERVER_URL;
397
- };
398
334
  SessionReplay.prototype.getDeviceId = function () {
399
335
  var _a, _b;
400
336
  var identityStoreDeviceId;
@@ -402,209 +338,23 @@ var SessionReplay = /** @class */ (function () {
402
338
  var identityStore = (0, analytics_client_common_1.getAnalyticsConnector)(this.config.instanceName).identityStore;
403
339
  identityStoreDeviceId = identityStore.getIdentity().deviceId;
404
340
  }
405
- return identityStoreDeviceId || ((_b = this.config) === null || _b === void 0 ? void 0 : _b.deviceId);
341
+ return identityStoreDeviceId || ((_b = this.identifiers) === null || _b === void 0 ? void 0 : _b.deviceId);
406
342
  };
407
343
  SessionReplay.prototype.getSessionId = function () {
408
344
  var _a;
409
- return (_a = this.config) === null || _a === void 0 ? void 0 : _a.sessionId;
345
+ return (_a = this.identifiers) === null || _a === void 0 ? void 0 : _a.sessionId;
410
346
  };
411
- SessionReplay.prototype.send = function (context, useRetry) {
412
- var _a;
413
- if (useRetry === void 0) { useRetry = true; }
414
- return tslib_1.__awaiter(this, void 0, void 0, function () {
415
- var apiKey, deviceId, url, version, sampleRate, urlParams, payload, options, server_url, res, responseBody, e_1;
416
- return tslib_1.__generator(this, function (_b) {
417
- switch (_b.label) {
418
- case 0:
419
- apiKey = (_a = this.config) === null || _a === void 0 ? void 0 : _a.apiKey;
420
- if (!apiKey) {
421
- return [2 /*return*/, this.completeRequest({ context: context, err: messages_1.MISSING_API_KEY_MESSAGE })];
422
- }
423
- deviceId = this.getDeviceId();
424
- if (!deviceId) {
425
- return [2 /*return*/, this.completeRequest({ context: context, err: messages_1.MISSING_DEVICE_ID_MESSAGE })];
426
- }
427
- url = (0, helpers_1.getCurrentUrl)();
428
- version = version_1.VERSION;
429
- sampleRate = this.getSampleRate();
430
- urlParams = new URLSearchParams({
431
- device_id: deviceId,
432
- session_id: "".concat(context.sessionId),
433
- seq_number: "".concat(context.sequenceId),
434
- });
435
- payload = {
436
- version: 1,
437
- events: context.events,
438
- };
439
- _b.label = 1;
440
- case 1:
441
- _b.trys.push([1, 3, , 4]);
442
- options = {
443
- headers: {
444
- 'Content-Type': 'application/json',
445
- Accept: '*/*',
446
- Authorization: "Bearer ".concat(apiKey),
447
- 'X-Client-Version': version,
448
- 'X-Client-Url': url,
449
- 'X-Client-Sample-Rate': "".concat(sampleRate),
450
- },
451
- body: JSON.stringify(payload),
452
- method: 'POST',
453
- };
454
- server_url = "".concat(this.getServerUrl(), "?").concat(urlParams.toString());
455
- return [4 /*yield*/, fetch(server_url, options)];
456
- case 2:
457
- res = _b.sent();
458
- if (res === null) {
459
- this.completeRequest({ context: context, err: messages_1.UNEXPECTED_ERROR_MESSAGE });
460
- return [2 /*return*/];
461
- }
462
- if (!useRetry) {
463
- responseBody = '';
464
- try {
465
- responseBody = JSON.stringify(res.body, null, 2);
466
- }
467
- catch (_c) {
468
- // to avoid crash, but don't care about the error, add comment to avoid empty block lint error
469
- }
470
- this.completeRequest({ context: context, success: "".concat(res.status, ": ").concat(responseBody) });
471
- }
472
- else {
473
- this.handleReponse(res.status, context);
474
- }
475
- return [3 /*break*/, 4];
476
- case 3:
477
- e_1 = _b.sent();
478
- this.completeRequest({ context: context, err: e_1 });
479
- return [3 /*break*/, 4];
480
- case 4: return [2 /*return*/];
481
- }
482
- });
483
- });
484
- };
485
- SessionReplay.prototype.handleReponse = function (status, context) {
486
- var parsedStatus = new analytics_core_1.BaseTransport().buildStatus(status);
487
- switch (parsedStatus) {
488
- case analytics_types_1.Status.Success:
489
- this.handleSuccessResponse(context);
490
- break;
491
- case analytics_types_1.Status.Failed:
492
- this.handleOtherResponse(context);
493
- break;
494
- default:
495
- this.completeRequest({ context: context, err: messages_1.UNEXPECTED_NETWORK_ERROR_MESSAGE });
496
- }
497
- };
498
- SessionReplay.prototype.handleSuccessResponse = function (context) {
499
- this.completeRequest({ context: context, success: (0, messages_1.getSuccessMessage)(context.sessionId) });
500
- };
501
- SessionReplay.prototype.handleOtherResponse = function (context) {
502
- this.addToQueue(tslib_1.__assign(tslib_1.__assign({}, context), { timeout: context.attempts * this.retryTimeout }));
503
- };
504
- SessionReplay.prototype.getAllSessionEventsFromStore = function () {
505
- return tslib_1.__awaiter(this, void 0, void 0, function () {
506
- var storedReplaySessionContexts, e_2;
507
- return tslib_1.__generator(this, function (_a) {
508
- switch (_a.label) {
509
- case 0:
510
- _a.trys.push([0, 2, , 3]);
511
- return [4 /*yield*/, IDBKeyVal.get(this.storageKey)];
512
- case 1:
513
- storedReplaySessionContexts = _a.sent();
514
- return [2 /*return*/, storedReplaySessionContexts];
515
- case 2:
516
- e_2 = _a.sent();
517
- this.loggerProvider.warn("".concat(messages_1.STORAGE_FAILURE, ": ").concat(e_2));
518
- return [3 /*break*/, 3];
519
- case 3: return [2 /*return*/, undefined];
520
- }
521
- });
522
- });
523
- };
524
- SessionReplay.prototype.storeEventsForSession = function (events, sequenceId, sessionId) {
525
- return tslib_1.__awaiter(this, void 0, void 0, function () {
526
- var e_3;
527
- return tslib_1.__generator(this, function (_a) {
528
- switch (_a.label) {
529
- case 0:
530
- _a.trys.push([0, 2, , 3]);
531
- return [4 /*yield*/, IDBKeyVal.update(this.storageKey, function (sessionMap) {
532
- var _a, _b;
533
- if (sessionMap === void 0) { sessionMap = {}; }
534
- var session = sessionMap[sessionId] || tslib_1.__assign({}, constants_1.defaultSessionStore);
535
- session.currentSequenceId = sequenceId;
536
- var currentSequence = (session.sessionSequences && session.sessionSequences[sequenceId]) || {};
537
- currentSequence.events = events;
538
- currentSequence.status = session_replay_1.RecordingStatus.RECORDING;
539
- return tslib_1.__assign(tslib_1.__assign({}, sessionMap), (_a = {}, _a[sessionId] = tslib_1.__assign(tslib_1.__assign({}, session), { sessionSequences: tslib_1.__assign(tslib_1.__assign({}, session.sessionSequences), (_b = {}, _b[sequenceId] = currentSequence, _b)) }), _a));
540
- })];
541
- case 1:
542
- _a.sent();
543
- return [3 /*break*/, 3];
544
- case 2:
545
- e_3 = _a.sent();
546
- this.loggerProvider.warn("".concat(messages_1.STORAGE_FAILURE, ": ").concat(e_3));
547
- return [3 /*break*/, 3];
548
- case 3: return [2 /*return*/];
549
- }
550
- });
551
- });
552
- };
553
- SessionReplay.prototype.cleanUpSessionEventsStore = function (sessionId, sequenceId) {
347
+ SessionReplay.prototype.flush = function (useRetry) {
348
+ if (useRetry === void 0) { useRetry = false; }
554
349
  return tslib_1.__awaiter(this, void 0, void 0, function () {
555
- var e_4;
556
350
  return tslib_1.__generator(this, function (_a) {
557
- switch (_a.label) {
558
- case 0:
559
- _a.trys.push([0, 2, , 3]);
560
- return [4 /*yield*/, IDBKeyVal.update(this.storageKey, function (sessionMap) {
561
- if (sessionMap === void 0) { sessionMap = {}; }
562
- var session = sessionMap[sessionId];
563
- var sequenceToUpdate = (session === null || session === void 0 ? void 0 : session.sessionSequences) && session.sessionSequences[sequenceId];
564
- if (!sequenceToUpdate) {
565
- return sessionMap;
566
- }
567
- sequenceToUpdate.events = [];
568
- sequenceToUpdate.status = session_replay_1.RecordingStatus.SENT;
569
- // Delete sent sequences for current session
570
- Object.entries(session.sessionSequences).forEach(function (_a) {
571
- var _b = tslib_1.__read(_a, 2), storedSeqId = _b[0], sequence = _b[1];
572
- var numericStoredSeqId = parseInt(storedSeqId, 10);
573
- if (sequence.status === session_replay_1.RecordingStatus.SENT && sequenceId !== numericStoredSeqId) {
574
- delete session.sessionSequences[numericStoredSeqId];
575
- }
576
- });
577
- // Delete any sessions that are older than 3 days
578
- Object.keys(sessionMap).forEach(function (sessionId) {
579
- var numericSessionId = parseInt(sessionId, 10);
580
- if (Date.now() - numericSessionId >= constants_1.MAX_IDB_STORAGE_LENGTH) {
581
- delete sessionMap[numericSessionId];
582
- }
583
- });
584
- return sessionMap;
585
- })];
586
- case 1:
587
- _a.sent();
588
- return [3 /*break*/, 3];
589
- case 2:
590
- e_4 = _a.sent();
591
- this.loggerProvider.warn("".concat(messages_1.STORAGE_FAILURE, ": ").concat(e_4));
592
- return [3 /*break*/, 3];
593
- case 3: return [2 /*return*/];
351
+ if (this.trackDestination) {
352
+ return [2 /*return*/, this.trackDestination.flush(useRetry)];
594
353
  }
354
+ return [2 /*return*/];
595
355
  });
596
356
  });
597
357
  };
598
- SessionReplay.prototype.completeRequest = function (_a) {
599
- var context = _a.context, err = _a.err, success = _a.success;
600
- context.sessionId && this.cleanUpSessionEventsStore(context.sessionId, context.sequenceId);
601
- if (err) {
602
- this.loggerProvider.warn(err);
603
- }
604
- else if (success) {
605
- this.loggerProvider.log(success);
606
- }
607
- };
608
358
  SessionReplay.prototype.shutdown = function () {
609
359
  var globalScope = (0, analytics_client_common_1.getGlobalScope)();
610
360
  if (globalScope) {