@amplitude/analytics-core 2.38.0 → 2.40.0
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/lib/cjs/core-client.d.ts +9 -1
- package/lib/cjs/core-client.d.ts.map +1 -1
- package/lib/cjs/core-client.js +15 -5
- package/lib/cjs/core-client.js.map +1 -1
- package/lib/cjs/diagnostics/uncaught-sdk-errors.d.ts.map +1 -1
- package/lib/cjs/diagnostics/uncaught-sdk-errors.js +42 -12
- package/lib/cjs/diagnostics/uncaught-sdk-errors.js.map +1 -1
- package/lib/cjs/index.d.ts +5 -0
- package/lib/cjs/index.d.ts.map +1 -1
- package/lib/cjs/index.js +13 -1
- package/lib/cjs/index.js.map +1 -1
- package/lib/cjs/messenger/background-capture.d.ts +13 -0
- package/lib/cjs/messenger/background-capture.d.ts.map +1 -0
- package/lib/cjs/messenger/background-capture.js +64 -0
- package/lib/cjs/messenger/background-capture.js.map +1 -0
- package/lib/cjs/messenger/base-window-messenger.d.ts +100 -0
- package/lib/cjs/messenger/base-window-messenger.d.ts.map +1 -0
- package/lib/cjs/messenger/base-window-messenger.js +261 -0
- package/lib/cjs/messenger/base-window-messenger.js.map +1 -0
- package/lib/cjs/messenger/constants.d.ts +6 -0
- package/lib/cjs/messenger/constants.d.ts.map +1 -0
- package/lib/cjs/messenger/constants.js +15 -0
- package/lib/cjs/messenger/constants.js.map +1 -0
- package/lib/cjs/messenger/utils.d.ts +12 -0
- package/lib/cjs/messenger/utils.d.ts.map +1 -0
- package/lib/cjs/messenger/utils.js +48 -0
- package/lib/cjs/messenger/utils.js.map +1 -0
- package/lib/cjs/observers/network.d.ts.map +1 -1
- package/lib/cjs/observers/network.js +58 -39
- package/lib/cjs/observers/network.js.map +1 -1
- package/lib/cjs/storage/cookie.d.ts +0 -1
- package/lib/cjs/storage/cookie.d.ts.map +1 -1
- package/lib/cjs/storage/cookie.js +4 -4
- package/lib/cjs/storage/cookie.js.map +1 -1
- package/lib/cjs/types/client/browser-client.d.ts +33 -0
- package/lib/cjs/types/client/browser-client.d.ts.map +1 -1
- package/lib/cjs/types/client/browser-client.js.map +1 -1
- package/lib/cjs/types/element-interactions.d.ts +0 -1
- package/lib/cjs/types/element-interactions.d.ts.map +1 -1
- package/lib/cjs/types/element-interactions.js.map +1 -1
- package/lib/cjs/utils/safe-stringify.d.ts +4 -0
- package/lib/cjs/utils/safe-stringify.d.ts.map +1 -0
- package/lib/cjs/utils/safe-stringify.js +9 -0
- package/lib/cjs/utils/safe-stringify.js.map +1 -0
- package/lib/esm/core-client.d.ts +9 -1
- package/lib/esm/core-client.d.ts.map +1 -1
- package/lib/esm/core-client.js +16 -6
- package/lib/esm/core-client.js.map +1 -1
- package/lib/esm/diagnostics/uncaught-sdk-errors.d.ts.map +1 -1
- package/lib/esm/diagnostics/uncaught-sdk-errors.js +43 -13
- package/lib/esm/diagnostics/uncaught-sdk-errors.js.map +1 -1
- package/lib/esm/index.d.ts +5 -0
- package/lib/esm/index.d.ts.map +1 -1
- package/lib/esm/index.js +4 -0
- package/lib/esm/index.js.map +1 -1
- package/lib/esm/messenger/background-capture.d.ts +13 -0
- package/lib/esm/messenger/background-capture.d.ts.map +1 -0
- package/lib/esm/messenger/background-capture.js +60 -0
- package/lib/esm/messenger/background-capture.js.map +1 -0
- package/lib/esm/messenger/base-window-messenger.d.ts +100 -0
- package/lib/esm/messenger/base-window-messenger.d.ts.map +1 -0
- package/lib/esm/messenger/base-window-messenger.js +257 -0
- package/lib/esm/messenger/base-window-messenger.js.map +1 -0
- package/lib/esm/messenger/constants.d.ts +6 -0
- package/lib/esm/messenger/constants.d.ts.map +1 -0
- package/lib/esm/messenger/constants.js +12 -0
- package/lib/esm/messenger/constants.js.map +1 -0
- package/lib/esm/messenger/utils.d.ts +12 -0
- package/lib/esm/messenger/utils.d.ts.map +1 -0
- package/lib/esm/messenger/utils.js +43 -0
- package/lib/esm/messenger/utils.js.map +1 -0
- package/lib/esm/observers/network.d.ts.map +1 -1
- package/lib/esm/observers/network.js +58 -39
- package/lib/esm/observers/network.js.map +1 -1
- package/lib/esm/storage/cookie.d.ts +0 -1
- package/lib/esm/storage/cookie.d.ts.map +1 -1
- package/lib/esm/storage/cookie.js +4 -4
- package/lib/esm/storage/cookie.js.map +1 -1
- package/lib/esm/types/client/browser-client.d.ts +33 -0
- package/lib/esm/types/client/browser-client.d.ts.map +1 -1
- package/lib/esm/types/client/browser-client.js.map +1 -1
- package/lib/esm/types/element-interactions.d.ts +0 -1
- package/lib/esm/types/element-interactions.d.ts.map +1 -1
- package/lib/esm/types/element-interactions.js.map +1 -1
- package/lib/esm/utils/safe-stringify.d.ts +4 -0
- package/lib/esm/utils/safe-stringify.d.ts.map +1 -0
- package/lib/esm/utils/safe-stringify.js +6 -0
- package/lib/esm/utils/safe-stringify.js.map +1 -0
- package/package.json +5 -1
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
import { ILogger } from '../logger';
|
|
2
|
+
import { Messenger } from '../types/element-interactions';
|
|
3
|
+
type MessageRequest = {
|
|
4
|
+
id: string;
|
|
5
|
+
action: string;
|
|
6
|
+
args: Record<string, any>;
|
|
7
|
+
};
|
|
8
|
+
export type ActionHandler = (data: any) => void;
|
|
9
|
+
/**
|
|
10
|
+
* Brand key used to identify BaseWindowMessenger instances across bundle boundaries.
|
|
11
|
+
*/
|
|
12
|
+
declare const MESSENGER_BRAND: "__AMPLITUDE_MESSENGER_INSTANCE__";
|
|
13
|
+
/**
|
|
14
|
+
* BaseWindowMessenger provides generic cross-window communication via postMessage.
|
|
15
|
+
* Singleton access via getOrCreateWindowMessenger() to prevent duplicate instances
|
|
16
|
+
*/
|
|
17
|
+
declare class BaseWindowMessenger implements Messenger {
|
|
18
|
+
/** Brand property for cross-bundle instanceof checks. */
|
|
19
|
+
readonly [MESSENGER_BRAND] = true;
|
|
20
|
+
endpoint: string;
|
|
21
|
+
logger?: ILogger;
|
|
22
|
+
private isSetup;
|
|
23
|
+
private messageHandler;
|
|
24
|
+
requestCallbacks: {
|
|
25
|
+
[id: string]: {
|
|
26
|
+
resolve: (data: any) => void;
|
|
27
|
+
reject: (data: any) => void;
|
|
28
|
+
};
|
|
29
|
+
};
|
|
30
|
+
private actionHandlers;
|
|
31
|
+
/**
|
|
32
|
+
* Messages received for actions that had no registered handler yet.
|
|
33
|
+
* Drained automatically when the corresponding handler is registered via
|
|
34
|
+
* registerActionHandler(), solving startup race conditions between
|
|
35
|
+
* independently-initialized plugins.
|
|
36
|
+
*/
|
|
37
|
+
private pendingMessages;
|
|
38
|
+
/**
|
|
39
|
+
* Tracks in-flight and completed script loads by URL.
|
|
40
|
+
* Using a map, this prevents duplicate loads before the first resolves.
|
|
41
|
+
*/
|
|
42
|
+
private scriptLoadPromises;
|
|
43
|
+
constructor({ origin }?: {
|
|
44
|
+
origin?: string;
|
|
45
|
+
});
|
|
46
|
+
/**
|
|
47
|
+
* Send a message to the parent window (window.opener).
|
|
48
|
+
*/
|
|
49
|
+
notify(message: {
|
|
50
|
+
action: string;
|
|
51
|
+
data?: any;
|
|
52
|
+
} | MessageRequest): void;
|
|
53
|
+
/**
|
|
54
|
+
* Send an async request to the parent window with a unique ID.
|
|
55
|
+
* Returns a Promise that resolves when the parent responds.
|
|
56
|
+
*/
|
|
57
|
+
sendRequest(action: string, args: Record<string, any>, options?: {
|
|
58
|
+
timeout: number;
|
|
59
|
+
}): Promise<any>;
|
|
60
|
+
/**
|
|
61
|
+
* Handle a response to a previous request by resolving its Promise.
|
|
62
|
+
*/
|
|
63
|
+
private handleResponse;
|
|
64
|
+
/**
|
|
65
|
+
* Register a handler for a specific action type.
|
|
66
|
+
* Logs a warning if overwriting an existing handler.
|
|
67
|
+
*/
|
|
68
|
+
registerActionHandler(action: string, handler: ActionHandler): void;
|
|
69
|
+
/**
|
|
70
|
+
* Load a script once, deduplicating by URL.
|
|
71
|
+
* Safe against concurrent calls — the second call awaits the first's in-flight Promise
|
|
72
|
+
* rather than triggering a duplicate load.
|
|
73
|
+
*/
|
|
74
|
+
loadScriptOnce(url: string): Promise<void>;
|
|
75
|
+
/**
|
|
76
|
+
* Set up the message listener. Idempotent — safe to call multiple times.
|
|
77
|
+
* Subclasses should call super.setup() and then register their own action handlers.
|
|
78
|
+
*/
|
|
79
|
+
setup({ logger, endpoint }?: {
|
|
80
|
+
logger?: ILogger;
|
|
81
|
+
endpoint?: string;
|
|
82
|
+
}): void;
|
|
83
|
+
/**
|
|
84
|
+
* Tear down the messenger: remove the message listener, clear all state.
|
|
85
|
+
*/
|
|
86
|
+
destroy(): void;
|
|
87
|
+
}
|
|
88
|
+
/**
|
|
89
|
+
* Get or create a singleton BaseWindowMessenger instance.
|
|
90
|
+
* Ensures only one messenger (and one message listener) exists per page,
|
|
91
|
+
* preventing duplicate script loads and double notifications.
|
|
92
|
+
*
|
|
93
|
+
* The singleton is stored on globalScope under the same MESSENGER_KEY.
|
|
94
|
+
* The branded property check verifies the stored value is actually a messenger.
|
|
95
|
+
*/
|
|
96
|
+
export declare function getOrCreateWindowMessenger(options?: {
|
|
97
|
+
origin?: string;
|
|
98
|
+
}): BaseWindowMessenger;
|
|
99
|
+
export type { BaseWindowMessenger };
|
|
100
|
+
//# sourceMappingURL=base-window-messenger.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"base-window-messenger.d.ts","sourceRoot":"","sources":["../../../src/messenger/base-window-messenger.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,EAAE,SAAS,EAAE,MAAM,+BAA+B,CAAC;AAK1D,KAAK,cAAc,GAAG;IACpB,EAAE,EAAE,MAAM,CAAC;IACX,MAAM,EAAE,MAAM,CAAC;IACf,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;CAC3B,CAAC;AAQF,MAAM,MAAM,aAAa,GAAG,CAAC,IAAI,EAAE,GAAG,KAAK,IAAI,CAAC;AAEhD;;GAEG;AACH,QAAA,MAAM,eAAe,oCAA8C,CAAC;AAKpE;;;GAGG;AACH,cAAM,mBAAoB,YAAW,SAAS;IAC5C,yDAAyD;IACzD,QAAQ,CAAC,CAAC,eAAe,CAAC,QAAQ;IAElC,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,OAAO,CAAC,OAAO,CAAS;IACxB,OAAO,CAAC,cAAc,CAAgD;IACtE,gBAAgB,EAAE;QAChB,CAAC,EAAE,EAAE,MAAM,GAAG;YACZ,OAAO,EAAE,CAAC,IAAI,EAAE,GAAG,KAAK,IAAI,CAAC;YAC7B,MAAM,EAAE,CAAC,IAAI,EAAE,GAAG,KAAK,IAAI,CAAC;SAC7B,CAAC;KACH,CAAM;IACP,OAAO,CAAC,cAAc,CAAoC;IAE1D;;;;;OAKG;IACH,OAAO,CAAC,eAAe,CAA4B;IAEnD;;;OAGG;IACH,OAAO,CAAC,kBAAkB,CAAoC;gBAElD,EAAE,MAAyB,EAAE,GAAE;QAAE,MAAM,CAAC,EAAE,MAAM,CAAA;KAAO;IAInE;;OAEG;IACH,MAAM,CAAC,OAAO,EAAE;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,IAAI,CAAC,EAAE,GAAG,CAAA;KAAE,GAAG,cAAc;IAK/D;;;OAGG;IACI,WAAW,CAAC,MAAM,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,EAAE,OAAO;;KAAsB,GAAG,OAAO,CAAC,GAAG,CAAC;IAoB1G;;OAEG;IACH,OAAO,CAAC,cAAc;IAUtB;;;OAGG;IACH,qBAAqB,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,aAAa;IAgB5D;;;;OAIG;IACG,cAAc,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAoBhD;;;OAGG;IACH,KAAK,CAAC,EAAE,MAAM,EAAE,QAAQ,EAAE,GAAE;QAAE,MAAM,CAAC,EAAE,OAAO,CAAC;QAAC,QAAQ,CAAC,EAAE,MAAM,CAAA;KAAO;IA6DxE;;OAEG;IACH,OAAO;CAiBR;AAcD;;;;;;;GAOG;AACH,wBAAgB,0BAA0B,CAAC,OAAO,CAAC,EAAE;IAAE,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE,GAAG,mBAAmB,CAa7F;AAED,YAAY,EAAE,mBAAmB,EAAE,CAAC"}
|
|
@@ -0,0 +1,261 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var _a;
|
|
3
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
|
+
exports.getOrCreateWindowMessenger = void 0;
|
|
5
|
+
var tslib_1 = require("tslib");
|
|
6
|
+
var global_scope_1 = require("../global-scope");
|
|
7
|
+
var constants_1 = require("./constants");
|
|
8
|
+
var utils_1 = require("./utils");
|
|
9
|
+
/**
|
|
10
|
+
* Brand key used to identify BaseWindowMessenger instances across bundle boundaries.
|
|
11
|
+
*/
|
|
12
|
+
var MESSENGER_BRAND = '__AMPLITUDE_MESSENGER_INSTANCE__';
|
|
13
|
+
/** Global scope key where the singleton messenger is stored. */
|
|
14
|
+
var MESSENGER_GLOBAL_KEY = '__AMPLITUDE_MESSENGER__';
|
|
15
|
+
/**
|
|
16
|
+
* BaseWindowMessenger provides generic cross-window communication via postMessage.
|
|
17
|
+
* Singleton access via getOrCreateWindowMessenger() to prevent duplicate instances
|
|
18
|
+
*/
|
|
19
|
+
var BaseWindowMessenger = /** @class */ (function () {
|
|
20
|
+
function BaseWindowMessenger(_b) {
|
|
21
|
+
var _c = _b === void 0 ? {} : _b, _d = _c.origin, origin = _d === void 0 ? constants_1.AMPLITUDE_ORIGIN : _d;
|
|
22
|
+
/** Brand property for cross-bundle instanceof checks. */
|
|
23
|
+
this[_a] = true;
|
|
24
|
+
this.isSetup = false;
|
|
25
|
+
this.messageHandler = null;
|
|
26
|
+
this.requestCallbacks = {};
|
|
27
|
+
this.actionHandlers = new Map();
|
|
28
|
+
/**
|
|
29
|
+
* Messages received for actions that had no registered handler yet.
|
|
30
|
+
* Drained automatically when the corresponding handler is registered via
|
|
31
|
+
* registerActionHandler(), solving startup race conditions between
|
|
32
|
+
* independently-initialized plugins.
|
|
33
|
+
*/
|
|
34
|
+
this.pendingMessages = new Map();
|
|
35
|
+
/**
|
|
36
|
+
* Tracks in-flight and completed script loads by URL.
|
|
37
|
+
* Using a map, this prevents duplicate loads before the first resolves.
|
|
38
|
+
*/
|
|
39
|
+
this.scriptLoadPromises = new Map();
|
|
40
|
+
this.endpoint = origin;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Send a message to the parent window (window.opener).
|
|
44
|
+
*/
|
|
45
|
+
BaseWindowMessenger.prototype.notify = function (message) {
|
|
46
|
+
var _b, _c, _d, _e;
|
|
47
|
+
(_c = (_b = this.logger) === null || _b === void 0 ? void 0 : _b.debug) === null || _c === void 0 ? void 0 : _c.call(_b, 'Message sent: ', JSON.stringify(message));
|
|
48
|
+
(_e = (_d = window.opener) === null || _d === void 0 ? void 0 : _d.postMessage) === null || _e === void 0 ? void 0 : _e.call(_d, message, this.endpoint);
|
|
49
|
+
};
|
|
50
|
+
/**
|
|
51
|
+
* Send an async request to the parent window with a unique ID.
|
|
52
|
+
* Returns a Promise that resolves when the parent responds.
|
|
53
|
+
*/
|
|
54
|
+
BaseWindowMessenger.prototype.sendRequest = function (action, args, options) {
|
|
55
|
+
var _this = this;
|
|
56
|
+
if (options === void 0) { options = { timeout: 15000 }; }
|
|
57
|
+
var id = (0, utils_1.generateUniqueId)();
|
|
58
|
+
var request = { id: id, action: action, args: args };
|
|
59
|
+
var promise = new Promise(function (resolve, reject) {
|
|
60
|
+
_this.requestCallbacks[id] = { resolve: resolve, reject: reject };
|
|
61
|
+
_this.notify(request);
|
|
62
|
+
if (options.timeout > 0) {
|
|
63
|
+
setTimeout(function () {
|
|
64
|
+
reject(new Error("".concat(action, " timed out (id: ").concat(id, ")")));
|
|
65
|
+
delete _this.requestCallbacks[id];
|
|
66
|
+
}, options.timeout);
|
|
67
|
+
}
|
|
68
|
+
});
|
|
69
|
+
return promise;
|
|
70
|
+
};
|
|
71
|
+
/**
|
|
72
|
+
* Handle a response to a previous request by resolving its Promise.
|
|
73
|
+
*/
|
|
74
|
+
BaseWindowMessenger.prototype.handleResponse = function (response) {
|
|
75
|
+
var _b;
|
|
76
|
+
if (!this.requestCallbacks[response.id]) {
|
|
77
|
+
(_b = this.logger) === null || _b === void 0 ? void 0 : _b.warn("No callback found for request id: ".concat(response.id));
|
|
78
|
+
return;
|
|
79
|
+
}
|
|
80
|
+
this.requestCallbacks[response.id].resolve(response.responseData);
|
|
81
|
+
delete this.requestCallbacks[response.id];
|
|
82
|
+
};
|
|
83
|
+
/**
|
|
84
|
+
* Register a handler for a specific action type.
|
|
85
|
+
* Logs a warning if overwriting an existing handler.
|
|
86
|
+
*/
|
|
87
|
+
BaseWindowMessenger.prototype.registerActionHandler = function (action, handler) {
|
|
88
|
+
var e_1, _b;
|
|
89
|
+
var _c, _d;
|
|
90
|
+
if (this.actionHandlers.has(action)) {
|
|
91
|
+
(_d = (_c = this.logger) === null || _c === void 0 ? void 0 : _c.warn) === null || _d === void 0 ? void 0 : _d.call(_c, "Overwriting existing action handler for: ".concat(action));
|
|
92
|
+
}
|
|
93
|
+
this.actionHandlers.set(action, handler);
|
|
94
|
+
// Replay any messages that arrived before this handler was registered
|
|
95
|
+
var queued = this.pendingMessages.get(action);
|
|
96
|
+
if (queued) {
|
|
97
|
+
this.pendingMessages.delete(action);
|
|
98
|
+
try {
|
|
99
|
+
for (var queued_1 = tslib_1.__values(queued), queued_1_1 = queued_1.next(); !queued_1_1.done; queued_1_1 = queued_1.next()) {
|
|
100
|
+
var data = queued_1_1.value;
|
|
101
|
+
handler(data);
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
catch (e_1_1) { e_1 = { error: e_1_1 }; }
|
|
105
|
+
finally {
|
|
106
|
+
try {
|
|
107
|
+
if (queued_1_1 && !queued_1_1.done && (_b = queued_1.return)) _b.call(queued_1);
|
|
108
|
+
}
|
|
109
|
+
finally { if (e_1) throw e_1.error; }
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
};
|
|
113
|
+
/**
|
|
114
|
+
* Load a script once, deduplicating by URL.
|
|
115
|
+
* Safe against concurrent calls — the second call awaits the first's in-flight Promise
|
|
116
|
+
* rather than triggering a duplicate load.
|
|
117
|
+
*/
|
|
118
|
+
BaseWindowMessenger.prototype.loadScriptOnce = function (url) {
|
|
119
|
+
return tslib_1.__awaiter(this, void 0, void 0, function () {
|
|
120
|
+
var existing, loadPromise, error_1;
|
|
121
|
+
return tslib_1.__generator(this, function (_b) {
|
|
122
|
+
switch (_b.label) {
|
|
123
|
+
case 0:
|
|
124
|
+
existing = this.scriptLoadPromises.get(url);
|
|
125
|
+
if (existing) {
|
|
126
|
+
return [2 /*return*/, existing];
|
|
127
|
+
}
|
|
128
|
+
loadPromise = (0, utils_1.asyncLoadScript)(url).then(function () {
|
|
129
|
+
// Resolve to void
|
|
130
|
+
});
|
|
131
|
+
this.scriptLoadPromises.set(url, loadPromise);
|
|
132
|
+
_b.label = 1;
|
|
133
|
+
case 1:
|
|
134
|
+
_b.trys.push([1, 3, , 4]);
|
|
135
|
+
return [4 /*yield*/, loadPromise];
|
|
136
|
+
case 2:
|
|
137
|
+
_b.sent();
|
|
138
|
+
return [3 /*break*/, 4];
|
|
139
|
+
case 3:
|
|
140
|
+
error_1 = _b.sent();
|
|
141
|
+
// Remove failed loads so they can be retried
|
|
142
|
+
this.scriptLoadPromises.delete(url);
|
|
143
|
+
throw error_1;
|
|
144
|
+
case 4: return [2 /*return*/];
|
|
145
|
+
}
|
|
146
|
+
});
|
|
147
|
+
});
|
|
148
|
+
};
|
|
149
|
+
/**
|
|
150
|
+
* Set up the message listener. Idempotent — safe to call multiple times.
|
|
151
|
+
* Subclasses should call super.setup() and then register their own action handlers.
|
|
152
|
+
*/
|
|
153
|
+
BaseWindowMessenger.prototype.setup = function (_b) {
|
|
154
|
+
var _this = this;
|
|
155
|
+
var _c, _d;
|
|
156
|
+
var _e = _b === void 0 ? {} : _b, logger = _e.logger, endpoint = _e.endpoint;
|
|
157
|
+
if (logger) {
|
|
158
|
+
this.logger = logger;
|
|
159
|
+
}
|
|
160
|
+
// If endpoint is customized, don't override a previously customized endpoint.
|
|
161
|
+
if (endpoint && this.endpoint === constants_1.AMPLITUDE_ORIGIN) {
|
|
162
|
+
this.endpoint = endpoint;
|
|
163
|
+
}
|
|
164
|
+
// Only attach the message listener once
|
|
165
|
+
if (this.isSetup) {
|
|
166
|
+
return;
|
|
167
|
+
}
|
|
168
|
+
this.isSetup = true;
|
|
169
|
+
(_d = (_c = this.logger) === null || _c === void 0 ? void 0 : _c.debug) === null || _d === void 0 ? void 0 : _d.call(_c, 'Setting up messenger');
|
|
170
|
+
// Attach Event Listener to listen for messages from the parent window
|
|
171
|
+
this.messageHandler = function (event) {
|
|
172
|
+
var _b, _c, _d, _e, _f;
|
|
173
|
+
(_c = (_b = _this.logger) === null || _b === void 0 ? void 0 : _b.debug) === null || _c === void 0 ? void 0 : _c.call(_b, 'Message received: ', JSON.stringify(event));
|
|
174
|
+
// Only accept messages from the specified origin
|
|
175
|
+
if (_this.endpoint !== event.origin) {
|
|
176
|
+
return;
|
|
177
|
+
}
|
|
178
|
+
var eventData = event.data;
|
|
179
|
+
var action = eventData === null || eventData === void 0 ? void 0 : eventData.action;
|
|
180
|
+
// Ignore messages without action
|
|
181
|
+
if (!action) {
|
|
182
|
+
return;
|
|
183
|
+
}
|
|
184
|
+
// If id exists, handle responses to previous requests
|
|
185
|
+
if ('id' in eventData && eventData.id) {
|
|
186
|
+
(_e = (_d = _this.logger) === null || _d === void 0 ? void 0 : _d.debug) === null || _e === void 0 ? void 0 : _e.call(_d, 'Received Response to previous request: ', JSON.stringify(event));
|
|
187
|
+
_this.handleResponse(eventData);
|
|
188
|
+
}
|
|
189
|
+
else {
|
|
190
|
+
if (action === 'ping') {
|
|
191
|
+
_this.notify({ action: 'pong' });
|
|
192
|
+
return;
|
|
193
|
+
}
|
|
194
|
+
// Dispatch to registered action handlers, or buffer for late registration
|
|
195
|
+
var handler = _this.actionHandlers.get(action);
|
|
196
|
+
if (handler) {
|
|
197
|
+
handler(eventData.data);
|
|
198
|
+
}
|
|
199
|
+
else {
|
|
200
|
+
var queue = (_f = _this.pendingMessages.get(action)) !== null && _f !== void 0 ? _f : [];
|
|
201
|
+
queue.push(eventData.data);
|
|
202
|
+
_this.pendingMessages.set(action, queue);
|
|
203
|
+
}
|
|
204
|
+
}
|
|
205
|
+
};
|
|
206
|
+
window.addEventListener('message', this.messageHandler);
|
|
207
|
+
this.notify({ action: 'page-loaded' });
|
|
208
|
+
};
|
|
209
|
+
/**
|
|
210
|
+
* Tear down the messenger: remove the message listener, clear all state.
|
|
211
|
+
*/
|
|
212
|
+
BaseWindowMessenger.prototype.destroy = function () {
|
|
213
|
+
if (this.messageHandler) {
|
|
214
|
+
window.removeEventListener('message', this.messageHandler);
|
|
215
|
+
this.messageHandler = null;
|
|
216
|
+
}
|
|
217
|
+
this.isSetup = false;
|
|
218
|
+
this.actionHandlers.clear();
|
|
219
|
+
this.pendingMessages.clear();
|
|
220
|
+
this.requestCallbacks = {};
|
|
221
|
+
this.scriptLoadPromises.clear();
|
|
222
|
+
// Remove from global scope if this is the singleton
|
|
223
|
+
var globalScope = (0, global_scope_1.getGlobalScope)();
|
|
224
|
+
if ((globalScope === null || globalScope === void 0 ? void 0 : globalScope[MESSENGER_GLOBAL_KEY]) === this) {
|
|
225
|
+
delete globalScope[MESSENGER_GLOBAL_KEY];
|
|
226
|
+
}
|
|
227
|
+
};
|
|
228
|
+
return BaseWindowMessenger;
|
|
229
|
+
}());
|
|
230
|
+
_a = MESSENGER_BRAND;
|
|
231
|
+
/**
|
|
232
|
+
* Type guard: checks whether a value is a BaseWindowMessenger instance.
|
|
233
|
+
*/
|
|
234
|
+
function isWindowMessenger(value) {
|
|
235
|
+
return (typeof value === 'object' &&
|
|
236
|
+
value !== null &&
|
|
237
|
+
MESSENGER_BRAND in value &&
|
|
238
|
+
value[MESSENGER_BRAND] === true);
|
|
239
|
+
}
|
|
240
|
+
/**
|
|
241
|
+
* Get or create a singleton BaseWindowMessenger instance.
|
|
242
|
+
* Ensures only one messenger (and one message listener) exists per page,
|
|
243
|
+
* preventing duplicate script loads and double notifications.
|
|
244
|
+
*
|
|
245
|
+
* The singleton is stored on globalScope under the same MESSENGER_KEY.
|
|
246
|
+
* The branded property check verifies the stored value is actually a messenger.
|
|
247
|
+
*/
|
|
248
|
+
function getOrCreateWindowMessenger(options) {
|
|
249
|
+
var globalScope = (0, global_scope_1.getGlobalScope)();
|
|
250
|
+
var existing = globalScope === null || globalScope === void 0 ? void 0 : globalScope[MESSENGER_GLOBAL_KEY];
|
|
251
|
+
if (isWindowMessenger(existing)) {
|
|
252
|
+
return existing;
|
|
253
|
+
}
|
|
254
|
+
var messenger = new BaseWindowMessenger(options);
|
|
255
|
+
if (globalScope) {
|
|
256
|
+
globalScope[MESSENGER_GLOBAL_KEY] = messenger;
|
|
257
|
+
}
|
|
258
|
+
return messenger;
|
|
259
|
+
}
|
|
260
|
+
exports.getOrCreateWindowMessenger = getOrCreateWindowMessenger;
|
|
261
|
+
//# sourceMappingURL=base-window-messenger.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"base-window-messenger.js","sourceRoot":"","sources":["../../../src/messenger/base-window-messenger.ts"],"names":[],"mappings":"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","sourcesContent":["/* eslint-disable no-restricted-globals */\nimport { ILogger } from '../logger';\nimport { Messenger } from '../types/element-interactions';\nimport { getGlobalScope } from '../global-scope';\nimport { AMPLITUDE_ORIGIN } from './constants';\nimport { asyncLoadScript, generateUniqueId } from './utils';\n\ntype MessageRequest = {\n id: string;\n action: string;\n args: Record<string, any>;\n};\n\ntype MessageResponse = {\n id: string;\n action: string;\n responseData: any;\n};\n\nexport type ActionHandler = (data: any) => void;\n\n/**\n * Brand key used to identify BaseWindowMessenger instances across bundle boundaries.\n */\nconst MESSENGER_BRAND = '__AMPLITUDE_MESSENGER_INSTANCE__' as const;\n\n/** Global scope key where the singleton messenger is stored. */\nconst MESSENGER_GLOBAL_KEY = '__AMPLITUDE_MESSENGER__';\n\n/**\n * BaseWindowMessenger provides generic cross-window communication via postMessage.\n * Singleton access via getOrCreateWindowMessenger() to prevent duplicate instances\n */\nclass BaseWindowMessenger implements Messenger {\n /** Brand property for cross-bundle instanceof checks. */\n readonly [MESSENGER_BRAND] = true;\n\n endpoint: string;\n logger?: ILogger;\n private isSetup = false;\n private messageHandler: ((event: MessageEvent) => void) | null = null;\n requestCallbacks: {\n [id: string]: {\n resolve: (data: any) => void;\n reject: (data: any) => void;\n };\n } = {};\n private actionHandlers = new Map<string, ActionHandler>();\n\n /**\n * Messages received for actions that had no registered handler yet.\n * Drained automatically when the corresponding handler is registered via\n * registerActionHandler(), solving startup race conditions between\n * independently-initialized plugins.\n */\n private pendingMessages = new Map<string, any[]>();\n\n /**\n * Tracks in-flight and completed script loads by URL.\n * Using a map, this prevents duplicate loads before the first resolves.\n */\n private scriptLoadPromises = new Map<string, Promise<void>>();\n\n constructor({ origin = AMPLITUDE_ORIGIN }: { origin?: string } = {}) {\n this.endpoint = origin;\n }\n\n /**\n * Send a message to the parent window (window.opener).\n */\n notify(message: { action: string; data?: any } | MessageRequest) {\n this.logger?.debug?.('Message sent: ', JSON.stringify(message));\n (window.opener as WindowProxy)?.postMessage?.(message, this.endpoint);\n }\n\n /**\n * Send an async request to the parent window with a unique ID.\n * Returns a Promise that resolves when the parent responds.\n */\n public sendRequest(action: string, args: Record<string, any>, options = { timeout: 15_000 }): Promise<any> {\n const id = generateUniqueId();\n const request: MessageRequest = { id, action, args };\n\n const promise = new Promise((resolve, reject) => {\n this.requestCallbacks[id] = { resolve, reject };\n\n this.notify(request);\n\n if (options.timeout > 0) {\n setTimeout(() => {\n reject(new Error(`${action} timed out (id: ${id})`));\n delete this.requestCallbacks[id];\n }, options.timeout);\n }\n });\n\n return promise;\n }\n\n /**\n * Handle a response to a previous request by resolving its Promise.\n */\n private handleResponse(response: MessageResponse) {\n if (!this.requestCallbacks[response.id]) {\n this.logger?.warn(`No callback found for request id: ${response.id}`);\n return;\n }\n\n this.requestCallbacks[response.id].resolve(response.responseData);\n delete this.requestCallbacks[response.id];\n }\n\n /**\n * Register a handler for a specific action type.\n * Logs a warning if overwriting an existing handler.\n */\n registerActionHandler(action: string, handler: ActionHandler) {\n if (this.actionHandlers.has(action)) {\n this.logger?.warn?.(`Overwriting existing action handler for: ${action}`);\n }\n this.actionHandlers.set(action, handler);\n\n // Replay any messages that arrived before this handler was registered\n const queued = this.pendingMessages.get(action);\n if (queued) {\n this.pendingMessages.delete(action);\n for (const data of queued) {\n handler(data);\n }\n }\n }\n\n /**\n * Load a script once, deduplicating by URL.\n * Safe against concurrent calls — the second call awaits the first's in-flight Promise\n * rather than triggering a duplicate load.\n */\n async loadScriptOnce(url: string): Promise<void> {\n const existing = this.scriptLoadPromises.get(url);\n if (existing) {\n return existing;\n }\n\n const loadPromise = asyncLoadScript(url).then(() => {\n // Resolve to void\n });\n this.scriptLoadPromises.set(url, loadPromise);\n\n try {\n await loadPromise;\n } catch (error) {\n // Remove failed loads so they can be retried\n this.scriptLoadPromises.delete(url);\n throw error;\n }\n }\n\n /**\n * Set up the message listener. Idempotent — safe to call multiple times.\n * Subclasses should call super.setup() and then register their own action handlers.\n */\n setup({ logger, endpoint }: { logger?: ILogger; endpoint?: string } = {}) {\n if (logger) {\n this.logger = logger;\n }\n\n // If endpoint is customized, don't override a previously customized endpoint.\n if (endpoint && this.endpoint === AMPLITUDE_ORIGIN) {\n this.endpoint = endpoint;\n }\n\n // Only attach the message listener once\n if (this.isSetup) {\n return;\n }\n this.isSetup = true;\n\n this.logger?.debug?.('Setting up messenger');\n\n // Attach Event Listener to listen for messages from the parent window\n this.messageHandler = (event: MessageEvent) => {\n this.logger?.debug?.('Message received: ', JSON.stringify(event));\n\n // Only accept messages from the specified origin\n if (this.endpoint !== event.origin) {\n return;\n }\n\n const eventData = event.data as { action?: string; id?: string; data?: any; responseData?: any };\n const action = eventData?.action;\n\n // Ignore messages without action\n if (!action) {\n return;\n }\n\n // If id exists, handle responses to previous requests\n if ('id' in eventData && eventData.id) {\n this.logger?.debug?.('Received Response to previous request: ', JSON.stringify(event));\n this.handleResponse(eventData as MessageResponse);\n } else {\n if (action === 'ping') {\n this.notify({ action: 'pong' });\n return;\n }\n\n // Dispatch to registered action handlers, or buffer for late registration\n const handler = this.actionHandlers.get(action);\n if (handler) {\n handler(eventData.data);\n } else {\n const queue = this.pendingMessages.get(action) ?? [];\n queue.push(eventData.data);\n this.pendingMessages.set(action, queue);\n }\n }\n };\n window.addEventListener('message', this.messageHandler);\n\n this.notify({ action: 'page-loaded' });\n }\n\n /**\n * Tear down the messenger: remove the message listener, clear all state.\n */\n destroy() {\n if (this.messageHandler) {\n window.removeEventListener('message', this.messageHandler);\n this.messageHandler = null;\n }\n this.isSetup = false;\n this.actionHandlers.clear();\n this.pendingMessages.clear();\n this.requestCallbacks = {};\n this.scriptLoadPromises.clear();\n\n // Remove from global scope if this is the singleton\n const globalScope = getGlobalScope() as Record<string, unknown> | undefined;\n if (globalScope?.[MESSENGER_GLOBAL_KEY] === this) {\n delete globalScope[MESSENGER_GLOBAL_KEY];\n }\n }\n}\n\n/**\n * Type guard: checks whether a value is a BaseWindowMessenger instance.\n */\nfunction isWindowMessenger(value: unknown): value is BaseWindowMessenger {\n return (\n typeof value === 'object' &&\n value !== null &&\n MESSENGER_BRAND in value &&\n (value as Record<string, unknown>)[MESSENGER_BRAND] === true\n );\n}\n\n/**\n * Get or create a singleton BaseWindowMessenger instance.\n * Ensures only one messenger (and one message listener) exists per page,\n * preventing duplicate script loads and double notifications.\n *\n * The singleton is stored on globalScope under the same MESSENGER_KEY.\n * The branded property check verifies the stored value is actually a messenger.\n */\nexport function getOrCreateWindowMessenger(options?: { origin?: string }): BaseWindowMessenger {\n const globalScope = getGlobalScope() as Record<string, unknown> | undefined;\n\n const existing = globalScope?.[MESSENGER_GLOBAL_KEY];\n if (isWindowMessenger(existing)) {\n return existing;\n }\n\n const messenger = new BaseWindowMessenger(options);\n if (globalScope) {\n globalScope[MESSENGER_GLOBAL_KEY] = messenger;\n }\n return messenger;\n}\n\nexport type { BaseWindowMessenger };\n"]}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
export declare const AMPLITUDE_ORIGIN = "https://app.amplitude.com";
|
|
2
|
+
export declare const AMPLITUDE_ORIGIN_EU = "https://app.eu.amplitude.com";
|
|
3
|
+
export declare const AMPLITUDE_ORIGIN_STAGING = "https://apps.stag2.amplitude.com";
|
|
4
|
+
export declare const AMPLITUDE_ORIGINS_MAP: Record<string, string>;
|
|
5
|
+
export declare const AMPLITUDE_BACKGROUND_CAPTURE_SCRIPT_URL = "https://cdn.amplitude.com/libs/background-capture-1.0.0-alpha.1.js.gz";
|
|
6
|
+
//# sourceMappingURL=constants.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../../src/messenger/constants.ts"],"names":[],"mappings":"AACA,eAAO,MAAM,gBAAgB,8BAA8B,CAAC;AAC5D,eAAO,MAAM,mBAAmB,iCAAiC,CAAC;AAClE,eAAO,MAAM,wBAAwB,qCAAqC,CAAC;AAC3E,eAAO,MAAM,qBAAqB,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAIxD,CAAC;AAGF,eAAO,MAAM,uCAAuC,0EACqB,CAAC"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.AMPLITUDE_BACKGROUND_CAPTURE_SCRIPT_URL = exports.AMPLITUDE_ORIGINS_MAP = exports.AMPLITUDE_ORIGIN_STAGING = exports.AMPLITUDE_ORIGIN_EU = exports.AMPLITUDE_ORIGIN = void 0;
|
|
4
|
+
// Shared origin constants for Amplitude cross-window communication
|
|
5
|
+
exports.AMPLITUDE_ORIGIN = 'https://app.amplitude.com';
|
|
6
|
+
exports.AMPLITUDE_ORIGIN_EU = 'https://app.eu.amplitude.com';
|
|
7
|
+
exports.AMPLITUDE_ORIGIN_STAGING = 'https://apps.stag2.amplitude.com';
|
|
8
|
+
exports.AMPLITUDE_ORIGINS_MAP = {
|
|
9
|
+
US: exports.AMPLITUDE_ORIGIN,
|
|
10
|
+
EU: exports.AMPLITUDE_ORIGIN_EU,
|
|
11
|
+
STAGING: exports.AMPLITUDE_ORIGIN_STAGING,
|
|
12
|
+
};
|
|
13
|
+
// Background capture script URL (shared between autocapture and session-replay)
|
|
14
|
+
exports.AMPLITUDE_BACKGROUND_CAPTURE_SCRIPT_URL = 'https://cdn.amplitude.com/libs/background-capture-1.0.0-alpha.1.js.gz';
|
|
15
|
+
//# sourceMappingURL=constants.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"constants.js","sourceRoot":"","sources":["../../../src/messenger/constants.ts"],"names":[],"mappings":";;;AAAA,mEAAmE;AACtD,QAAA,gBAAgB,GAAG,2BAA2B,CAAC;AAC/C,QAAA,mBAAmB,GAAG,8BAA8B,CAAC;AACrD,QAAA,wBAAwB,GAAG,kCAAkC,CAAC;AAC9D,QAAA,qBAAqB,GAA2B;IAC3D,EAAE,EAAE,wBAAgB;IACpB,EAAE,EAAE,2BAAmB;IACvB,OAAO,EAAE,gCAAwB;CAClC,CAAC;AAEF,gFAAgF;AACnE,QAAA,uCAAuC,GAClD,uEAAuE,CAAC","sourcesContent":["// Shared origin constants for Amplitude cross-window communication\nexport const AMPLITUDE_ORIGIN = 'https://app.amplitude.com';\nexport const AMPLITUDE_ORIGIN_EU = 'https://app.eu.amplitude.com';\nexport const AMPLITUDE_ORIGIN_STAGING = 'https://apps.stag2.amplitude.com';\nexport const AMPLITUDE_ORIGINS_MAP: Record<string, string> = {\n US: AMPLITUDE_ORIGIN,\n EU: AMPLITUDE_ORIGIN_EU,\n STAGING: AMPLITUDE_ORIGIN_STAGING,\n};\n\n// Background capture script URL (shared between autocapture and session-replay)\nexport const AMPLITUDE_BACKGROUND_CAPTURE_SCRIPT_URL =\n 'https://cdn.amplitude.com/libs/background-capture-1.0.0-alpha.1.js.gz';\n"]}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Dynamically loads an external script by appending a <script> tag to the document head.
|
|
3
|
+
* Deduplicates by checking if a script with the same src already exists.
|
|
4
|
+
*/
|
|
5
|
+
export declare const asyncLoadScript: (url: string) => Promise<{
|
|
6
|
+
status: boolean;
|
|
7
|
+
}>;
|
|
8
|
+
/**
|
|
9
|
+
* Generates a simple unique ID for message request/response correlation.
|
|
10
|
+
*/
|
|
11
|
+
export declare function generateUniqueId(): string;
|
|
12
|
+
//# sourceMappingURL=utils.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../../../src/messenger/utils.ts"],"names":[],"mappings":"AAEA;;;GAGG;AACH,eAAO,MAAM,eAAe,QAAS,MAAM,KAAG,QAAQ;IAAE,QAAQ,OAAO,CAAA;CAAE,CAiCxE,CAAC;AAEF;;GAEG;AACH,wBAAgB,gBAAgB,IAAI,MAAM,CAEzC"}
|
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/* eslint-disable no-restricted-globals */
|
|
3
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
|
+
exports.generateUniqueId = exports.asyncLoadScript = void 0;
|
|
5
|
+
/**
|
|
6
|
+
* Dynamically loads an external script by appending a <script> tag to the document head.
|
|
7
|
+
* Deduplicates by checking if a script with the same src already exists.
|
|
8
|
+
*/
|
|
9
|
+
var asyncLoadScript = function (url) {
|
|
10
|
+
// Dedup: if a script with this src already exists, resolve immediately
|
|
11
|
+
var existing = document.querySelector("script[src=\"".concat(CSS.escape(url), "\"]"));
|
|
12
|
+
if (existing) {
|
|
13
|
+
return Promise.resolve({ status: true });
|
|
14
|
+
}
|
|
15
|
+
return new Promise(function (resolve, reject) {
|
|
16
|
+
var _a;
|
|
17
|
+
try {
|
|
18
|
+
var scriptElement = document.createElement('script');
|
|
19
|
+
scriptElement.type = 'text/javascript';
|
|
20
|
+
scriptElement.async = true;
|
|
21
|
+
scriptElement.src = url;
|
|
22
|
+
scriptElement.addEventListener('load', function () {
|
|
23
|
+
resolve({ status: true });
|
|
24
|
+
}, { once: true });
|
|
25
|
+
scriptElement.addEventListener('error', function () {
|
|
26
|
+
reject({
|
|
27
|
+
status: false,
|
|
28
|
+
message: "Failed to load the script ".concat(url),
|
|
29
|
+
});
|
|
30
|
+
});
|
|
31
|
+
/* istanbul ignore next */
|
|
32
|
+
(_a = document.head) === null || _a === void 0 ? void 0 : _a.appendChild(scriptElement);
|
|
33
|
+
}
|
|
34
|
+
catch (error) {
|
|
35
|
+
/* istanbul ignore next */
|
|
36
|
+
reject(error);
|
|
37
|
+
}
|
|
38
|
+
});
|
|
39
|
+
};
|
|
40
|
+
exports.asyncLoadScript = asyncLoadScript;
|
|
41
|
+
/**
|
|
42
|
+
* Generates a simple unique ID for message request/response correlation.
|
|
43
|
+
*/
|
|
44
|
+
function generateUniqueId() {
|
|
45
|
+
return "".concat(Date.now(), "-").concat(Math.random().toString(36).substr(2, 9));
|
|
46
|
+
}
|
|
47
|
+
exports.generateUniqueId = generateUniqueId;
|
|
48
|
+
//# sourceMappingURL=utils.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"utils.js","sourceRoot":"","sources":["../../../src/messenger/utils.ts"],"names":[],"mappings":";AAAA,0CAA0C;;;AAE1C;;;GAGG;AACI,IAAM,eAAe,GAAG,UAAC,GAAW;IACzC,uEAAuE;IACvE,IAAM,QAAQ,GAAG,QAAQ,CAAC,aAAa,CAAC,uBAAe,GAAG,CAAC,MAAM,CAAC,GAAG,CAAC,QAAI,CAAC,CAAC;IAC5E,IAAI,QAAQ,EAAE;QACZ,OAAO,OAAO,CAAC,OAAO,CAAC,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;KAC1C;IAED,OAAO,IAAI,OAAO,CAAC,UAAC,OAAO,EAAE,MAAM;;QACjC,IAAI;YACF,IAAM,aAAa,GAAG,QAAQ,CAAC,aAAa,CAAC,QAAQ,CAAC,CAAC;YACvD,aAAa,CAAC,IAAI,GAAG,iBAAiB,CAAC;YACvC,aAAa,CAAC,KAAK,GAAG,IAAI,CAAC;YAC3B,aAAa,CAAC,GAAG,GAAG,GAAG,CAAC;YACxB,aAAa,CAAC,gBAAgB,CAC5B,MAAM,EACN;gBACE,OAAO,CAAC,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;YAC5B,CAAC,EACD,EAAE,IAAI,EAAE,IAAI,EAAE,CACf,CAAC;YACF,aAAa,CAAC,gBAAgB,CAAC,OAAO,EAAE;gBACtC,MAAM,CAAC;oBACL,MAAM,EAAE,KAAK;oBACb,OAAO,EAAE,oCAA6B,GAAG,CAAE;iBAC5C,CAAC,CAAC;YACL,CAAC,CAAC,CAAC;YACH,0BAA0B;YAC1B,MAAA,QAAQ,CAAC,IAAI,0CAAE,WAAW,CAAC,aAAa,CAAC,CAAC;SAC3C;QAAC,OAAO,KAAK,EAAE;YACd,0BAA0B;YAC1B,MAAM,CAAC,KAAK,CAAC,CAAC;SACf;IACH,CAAC,CAAC,CAAC;AACL,CAAC,CAAC;AAjCW,QAAA,eAAe,mBAiC1B;AAEF;;GAEG;AACH,SAAgB,gBAAgB;IAC9B,OAAO,UAAG,IAAI,CAAC,GAAG,EAAE,cAAI,IAAI,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC,EAAE,CAAC,CAAC,CAAE,CAAC;AACpE,CAAC;AAFD,4CAEC","sourcesContent":["/* eslint-disable no-restricted-globals */\n\n/**\n * Dynamically loads an external script by appending a <script> tag to the document head.\n * Deduplicates by checking if a script with the same src already exists.\n */\nexport const asyncLoadScript = (url: string): Promise<{ status: boolean }> => {\n // Dedup: if a script with this src already exists, resolve immediately\n const existing = document.querySelector(`script[src=\"${CSS.escape(url)}\"]`);\n if (existing) {\n return Promise.resolve({ status: true });\n }\n\n return new Promise((resolve, reject) => {\n try {\n const scriptElement = document.createElement('script');\n scriptElement.type = 'text/javascript';\n scriptElement.async = true;\n scriptElement.src = url;\n scriptElement.addEventListener(\n 'load',\n () => {\n resolve({ status: true });\n },\n { once: true },\n );\n scriptElement.addEventListener('error', () => {\n reject({\n status: false,\n message: `Failed to load the script ${url}`,\n });\n });\n /* istanbul ignore next */\n document.head?.appendChild(scriptElement);\n } catch (error) {\n /* istanbul ignore next */\n reject(error);\n }\n });\n};\n\n/**\n * Generates a simple unique ID for message request/response correlation.\n */\nexport function generateUniqueId(): string {\n return `${Date.now()}-${Math.random().toString(36).substr(2, 9)}`;\n}\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"network.d.ts","sourceRoot":"","sources":["../../../src/observers/network.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,EACL,eAAe,EACf,mBAAmB,EAKnB,gBAAgB,EAGjB,MAAM,0BAA0B,CAAC;AAoBlC,MAAM,MAAM,sBAAsB,GAAG,CAAC,KAAK,EAAE,mBAAmB,KAAK,IAAI,CAAC;AAE1E,qBAAa,oBAAoB;aACH,QAAQ,EAAE,CAAC,KAAK,EAAE,mBAAmB,KAAK,IAAI;aAAkB,EAAE,EAAE,MAAM;gBAA1E,QAAQ,EAAE,CAAC,KAAK,EAAE,mBAAmB,KAAK,IAAI,EAAkB,EAAE,GAAE,MAAe;CAChH;AAED,KAAK,mBAAmB,GAAG;IACzB,GAAG,EAAE,MAAM,GAAG,GAAG,GAAG,SAAS,CAAC;IAC9B,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC;CAC5B,CAAC;
|
|
1
|
+
{"version":3,"file":"network.d.ts","sourceRoot":"","sources":["../../../src/observers/network.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AACpC,OAAO,EACL,eAAe,EACf,mBAAmB,EAKnB,gBAAgB,EAGjB,MAAM,0BAA0B,CAAC;AAoBlC,MAAM,MAAM,sBAAsB,GAAG,CAAC,KAAK,EAAE,mBAAmB,KAAK,IAAI,CAAC;AAE1E,qBAAa,oBAAoB;aACH,QAAQ,EAAE,CAAC,KAAK,EAAE,mBAAmB,KAAK,IAAI;aAAkB,EAAE,EAAE,MAAM;gBAA1E,QAAQ,EAAE,CAAC,KAAK,EAAE,mBAAmB,KAAK,IAAI,EAAkB,EAAE,GAAE,MAAe;CAChH;AAED,KAAK,mBAAmB,GAAG;IACzB,GAAG,EAAE,MAAM,GAAG,GAAG,GAAG,SAAS,CAAC;IAC9B,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC;CAC5B,CAAC;AAwBF,qBAAa,eAAe;IAC1B,OAAO,CAAC,cAAc,CAAgD;IAEtE,OAAO,CAAC,WAAW,CAAC,CAAoB;IACxC,OAAO,CAAC,MAAM,CAAC,CAAU;IACzB,OAAO,CAAC,WAAW,CAAS;gBAChB,MAAM,CAAC,EAAE,OAAO;IAU5B,MAAM,CAAC,WAAW,IAAI,OAAO;IAK7B,SAAS,CAAC,aAAa,EAAE,oBAAoB,EAAE,MAAM,CAAC,EAAE,OAAO;IA+B/D,WAAW,CAAC,aAAa,EAAE,oBAAoB;IAI/C,SAAS,CAAC,qBAAqB,CAAC,KAAK,EAAE,mBAAmB;IAe1D,yBAAyB,CACvB,WAAW,EAAE,OAAO,GAAG,KAAK,EAC5B,WAAW,EAAE,WAAW,GAAG,GAAG,GAAG,mBAAmB,GAAG,SAAS,EAChE,cAAc,EAAE,eAAe,GAAG,SAAS,EAC3C,eAAe,EAAE,gBAAgB,GAAG,SAAS,EAC7C,UAAU,EAAE,KAAK,GAAG,SAAS,EAC7B,SAAS,CAAC,EAAE,MAAM,EAClB,aAAa,CAAC,EAAE,MAAM;IA+DxB,OAAO,CAAC,aAAa;IAQrB,OAAO,CAAC,YAAY;IA8DpB;;;;;;;;;OASG;IACH,MAAM,CAAC,mBAAmB,CAAC,SAAS,EAAE,cAAc,EAAE,OAAO,EAAE,eAAe;IAgC9E,OAAO,CAAC,UAAU;CAmInB;AAGD,eAAO,MAAM,eAAe,iBAAwB,CAAC"}
|