@tracelog/lib 0.6.0 → 0.6.3
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/README.md +9 -9
- package/dist/browser/tracelog.esm.js +406 -304
- package/dist/browser/tracelog.esm.js.map +1 -0
- package/dist/browser/tracelog.js +2 -2
- package/dist/browser/tracelog.js.map +1 -0
- package/dist/cjs/api.d.ts +1 -1
- package/dist/cjs/api.js +13 -4
- package/dist/cjs/app.d.ts +1 -1
- package/dist/cjs/app.js +4 -4
- package/dist/cjs/constants/config.constants.d.ts +3 -0
- package/dist/cjs/constants/config.constants.js +5 -2
- package/dist/cjs/handlers/click.handler.js +2 -2
- package/dist/cjs/handlers/scroll.handler.js +1 -1
- package/dist/cjs/handlers/session.handler.js +1 -1
- package/dist/cjs/managers/event.manager.d.ts +3 -0
- package/dist/cjs/managers/event.manager.js +47 -6
- package/dist/cjs/managers/sender.manager.js +4 -5
- package/dist/cjs/managers/storage.manager.d.ts +5 -0
- package/dist/cjs/managers/storage.manager.js +95 -6
- package/dist/cjs/public-api.d.ts +1 -1
- package/dist/cjs/test-bridge.d.ts +1 -1
- package/dist/cjs/test-bridge.js +1 -1
- package/dist/cjs/types/config.types.d.ts +4 -4
- package/dist/cjs/types/state.types.d.ts +1 -1
- package/dist/cjs/types/test-bridge.types.d.ts +1 -1
- package/dist/cjs/utils/logging.utils.d.ts +16 -1
- package/dist/cjs/utils/logging.utils.js +65 -4
- package/dist/cjs/utils/network/url.utils.d.ts +1 -1
- package/dist/cjs/utils/network/url.utils.js +11 -12
- package/dist/cjs/utils/validations/config-validations.utils.d.ts +2 -2
- package/dist/cjs/utils/validations/config-validations.utils.js +30 -18
- package/dist/esm/api.d.ts +1 -1
- package/dist/esm/api.js +13 -4
- package/dist/esm/app.d.ts +1 -1
- package/dist/esm/app.js +5 -5
- package/dist/esm/constants/config.constants.d.ts +3 -0
- package/dist/esm/constants/config.constants.js +3 -0
- package/dist/esm/handlers/click.handler.js +2 -2
- package/dist/esm/handlers/scroll.handler.js +1 -1
- package/dist/esm/handlers/session.handler.js +1 -1
- package/dist/esm/managers/event.manager.d.ts +3 -0
- package/dist/esm/managers/event.manager.js +48 -7
- package/dist/esm/managers/sender.manager.js +4 -5
- package/dist/esm/managers/storage.manager.d.ts +5 -0
- package/dist/esm/managers/storage.manager.js +95 -6
- package/dist/esm/public-api.d.ts +1 -1
- package/dist/esm/test-bridge.d.ts +1 -1
- package/dist/esm/test-bridge.js +1 -1
- package/dist/esm/types/config.types.d.ts +4 -4
- package/dist/esm/types/state.types.d.ts +1 -1
- package/dist/esm/types/test-bridge.types.d.ts +1 -1
- package/dist/esm/utils/logging.utils.d.ts +16 -1
- package/dist/esm/utils/logging.utils.js +65 -4
- package/dist/esm/utils/network/url.utils.d.ts +1 -1
- package/dist/esm/utils/network/url.utils.js +9 -10
- package/dist/esm/utils/validations/config-validations.utils.d.ts +2 -2
- package/dist/esm/utils/validations/config-validations.utils.js +30 -18
- package/package.json +7 -6
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
const O = "data-tlog",
|
|
1
|
+
const O = "data-tlog", Ce = [
|
|
2
2
|
"button",
|
|
3
3
|
"a",
|
|
4
4
|
'input[type="button"]',
|
|
@@ -30,7 +30,7 @@ const O = "data-tlog", be = [
|
|
|
30
30
|
".menu-item",
|
|
31
31
|
"[data-testid]",
|
|
32
32
|
'[tabindex="0"]'
|
|
33
|
-
],
|
|
33
|
+
], be = ["utm_source", "utm_medium", "utm_campaign", "utm_term", "utm_content"];
|
|
34
34
|
const m = {
|
|
35
35
|
INVALID_SESSION_TIMEOUT: "Session timeout must be between 30000ms (30 seconds) and 86400000ms (24 hours)",
|
|
36
36
|
INVALID_SAMPLING_RATE: "Sampling rate must be between 0 and 1",
|
|
@@ -41,7 +41,7 @@ const m = {
|
|
|
41
41
|
INVALID_SCROLL_CONTAINER_SELECTORS: "Scroll container selectors must be valid CSS selectors",
|
|
42
42
|
INVALID_GLOBAL_METADATA: "Global metadata must be an object",
|
|
43
43
|
INVALID_SENSITIVE_QUERY_PARAMS: "Sensitive query params must be an array of strings"
|
|
44
|
-
},
|
|
44
|
+
}, Oe = [
|
|
45
45
|
/<script\b[^<]*(?:(?!<\/script>)<[^<]*)*<\/script>/gi,
|
|
46
46
|
/javascript:/gi,
|
|
47
47
|
/on\w+\s*=/gi,
|
|
@@ -49,54 +49,74 @@ const m = {
|
|
|
49
49
|
/<embed\b[^>]*>/gi,
|
|
50
50
|
/<object\b[^<]*(?:(?!<\/object>)<[^<]*)*<\/object>/gi
|
|
51
51
|
];
|
|
52
|
-
var
|
|
53
|
-
class
|
|
52
|
+
var j = /* @__PURE__ */ ((r) => (r.Localhost = "localhost:8080", r.Fail = "localhost:9999", r))(j || {}), _ = /* @__PURE__ */ ((r) => (r.Mobile = "mobile", r.Tablet = "tablet", r.Desktop = "desktop", r.Unknown = "unknown", r))(_ || {}), X = /* @__PURE__ */ ((r) => (r.EVENT = "event", r.QUEUE = "queue", r))(X || {}), d = /* @__PURE__ */ ((r) => (r.PAGE_VIEW = "page_view", r.CLICK = "click", r.SCROLL = "scroll", r.SESSION_START = "session_start", r.SESSION_END = "session_end", r.CUSTOM = "custom", r.WEB_VITALS = "web_vitals", r.ERROR = "error", r))(d || {}), D = /* @__PURE__ */ ((r) => (r.UP = "up", r.DOWN = "down", r))(D || {}), L = /* @__PURE__ */ ((r) => (r.JS_ERROR = "js_error", r.PROMISE_REJECTION = "promise_rejection", r))(L || {}), R = /* @__PURE__ */ ((r) => (r.QA = "qa", r))(R || {});
|
|
53
|
+
class C extends Error {
|
|
54
54
|
constructor(e, t, s) {
|
|
55
55
|
super(e), this.errorCode = t, this.layer = s, this.name = this.constructor.name, Error.captureStackTrace && Error.captureStackTrace(this, this.constructor);
|
|
56
56
|
}
|
|
57
57
|
}
|
|
58
|
-
class
|
|
58
|
+
class y extends C {
|
|
59
59
|
constructor(e, t = "config") {
|
|
60
60
|
super(e, "APP_CONFIG_INVALID", t);
|
|
61
61
|
}
|
|
62
62
|
}
|
|
63
|
-
class
|
|
63
|
+
class Pe extends C {
|
|
64
64
|
constructor(e, t = "config") {
|
|
65
65
|
super(e, "SESSION_TIMEOUT_INVALID", t);
|
|
66
66
|
}
|
|
67
67
|
}
|
|
68
|
-
class oe extends
|
|
68
|
+
class oe extends C {
|
|
69
69
|
constructor(e, t = "config") {
|
|
70
70
|
super(e, "SAMPLING_RATE_INVALID", t);
|
|
71
71
|
}
|
|
72
72
|
}
|
|
73
|
-
class
|
|
73
|
+
class v extends C {
|
|
74
74
|
constructor(e, t = "config") {
|
|
75
75
|
super(e, "INTEGRATION_INVALID", t);
|
|
76
76
|
}
|
|
77
77
|
}
|
|
78
|
-
class xt extends
|
|
78
|
+
class xt extends C {
|
|
79
79
|
constructor(e, t, s = "runtime") {
|
|
80
80
|
super(e, "INITIALIZATION_TIMEOUT", s), this.timeoutMs = t;
|
|
81
81
|
}
|
|
82
82
|
}
|
|
83
|
-
const
|
|
84
|
-
|
|
85
|
-
|
|
83
|
+
const De = (r, e) => {
|
|
84
|
+
if (e) {
|
|
85
|
+
if (e instanceof Error) {
|
|
86
|
+
const t = e.message.replace(/\s+at\s+.*$/gm, "").replace(/\(.*?:\d+:\d+\)/g, "");
|
|
87
|
+
return `[TraceLog] ${r}: ${t}`;
|
|
88
|
+
}
|
|
89
|
+
return `[TraceLog] ${r}: ${e instanceof Error ? e.message : "Unknown error"}`;
|
|
90
|
+
}
|
|
91
|
+
return `[TraceLog] ${r}`;
|
|
92
|
+
}, o = (r, e, t) => {
|
|
93
|
+
const { error: s, data: n, showToClient: i = !1 } = t ?? {}, a = s ? De(e, s) : `[TraceLog] ${e}`, l = r === "error" ? "error" : r === "warn" ? "warn" : "log";
|
|
94
|
+
if (!(r === "debug" || r === "info" && !i))
|
|
95
|
+
if (n !== void 0) {
|
|
96
|
+
const c = ke(n);
|
|
97
|
+
console[l](a, c);
|
|
98
|
+
} else n !== void 0 ? console[l](a, n) : console[l](a);
|
|
99
|
+
}, ke = (r) => {
|
|
100
|
+
const e = {}, t = ["token", "password", "secret", "key", "apikey", "api_key", "sessionid", "session_id"];
|
|
101
|
+
for (const [s, n] of Object.entries(r)) {
|
|
102
|
+
const i = s.toLowerCase();
|
|
103
|
+
t.some((a) => i.includes(a)) ? e[s] = "[REDACTED]" : e[s] = n;
|
|
104
|
+
}
|
|
105
|
+
return e;
|
|
86
106
|
};
|
|
87
|
-
let
|
|
107
|
+
let W, pe;
|
|
88
108
|
const Ue = () => {
|
|
89
|
-
typeof window < "u" && !
|
|
109
|
+
typeof window < "u" && !W && (W = window.matchMedia("(pointer: coarse)"), pe = window.matchMedia("(hover: none)"));
|
|
90
110
|
}, He = () => {
|
|
91
111
|
try {
|
|
92
112
|
const r = navigator;
|
|
93
113
|
if (r.userAgentData && typeof r.userAgentData.mobile == "boolean")
|
|
94
114
|
return r.userAgentData.platform && /ipad|tablet/i.test(r.userAgentData.platform) ? _.Tablet : r.userAgentData.mobile ? _.Mobile : _.Desktop;
|
|
95
115
|
Ue();
|
|
96
|
-
const e = window.innerWidth, t =
|
|
97
|
-
return e <= 767 || a && n ? _.Mobile : e >= 768 && e <= 1024 ||
|
|
116
|
+
const e = window.innerWidth, t = W?.matches ?? !1, s = pe?.matches ?? !1, n = "ontouchstart" in window || navigator.maxTouchPoints > 0, i = navigator.userAgent.toLowerCase(), a = /mobile|android|iphone|ipod|blackberry|iemobile|opera mini/.test(i), l = /tablet|ipad|android(?!.*mobile)/.test(i);
|
|
117
|
+
return e <= 767 || a && n ? _.Mobile : e >= 768 && e <= 1024 || l || t && s && n ? _.Tablet : _.Desktop;
|
|
98
118
|
} catch (r) {
|
|
99
|
-
return
|
|
119
|
+
return o("warn", "Device detection failed, defaulting to desktop", { error: r }), _.Desktop;
|
|
100
120
|
}
|
|
101
121
|
}, T = "tlog", le = `${T}:qa_mode`, xe = `${T}:uid`, Ve = (r) => r ? `${T}:${r}:queue` : `${T}:queue`, Fe = (r) => r ? `${T}:${r}:session` : `${T}:session`, Ge = (r) => r ? `${T}:${r}:broadcast` : `${T}:broadcast`, _e = {
|
|
102
122
|
LCP: 4e3,
|
|
@@ -105,7 +125,7 @@ const Ue = () => {
|
|
|
105
125
|
INP: 200,
|
|
106
126
|
TTFB: 800,
|
|
107
127
|
LONG_TASK: 50
|
|
108
|
-
},
|
|
128
|
+
}, ze = 1e3, Te = [
|
|
109
129
|
// Email addresses
|
|
110
130
|
/\b[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\.[A-Z|a-z]{2,}\b/gi,
|
|
111
131
|
// US Phone numbers (various formats)
|
|
@@ -120,17 +140,17 @@ const Ue = () => {
|
|
|
120
140
|
/Bearer\s+[A-Za-z0-9_-]+(?:\.[A-Za-z0-9_-]+)?(?:\.[A-Za-z0-9_-]+)?/gi,
|
|
121
141
|
// Passwords in connection strings (protocol://user:password@host)
|
|
122
142
|
/:\/\/[^:/]+:([^@]+)@/gi
|
|
123
|
-
], ce = 500, ue = 5e3, k = 50, $e = k * 2, de = "tlog_mode",
|
|
143
|
+
], ce = 500, ue = 5e3, k = 50, $e = k * 2, de = "tlog_mode", Qe = "qa", Be = () => {
|
|
124
144
|
if (sessionStorage.getItem(le) === "true")
|
|
125
145
|
return !0;
|
|
126
|
-
const e = new URLSearchParams(window.location.search), s = e.get(de) ===
|
|
146
|
+
const e = new URLSearchParams(window.location.search), s = e.get(de) === Qe;
|
|
127
147
|
if (s) {
|
|
128
148
|
sessionStorage.setItem(le, "true"), e.delete(de);
|
|
129
149
|
const n = e.toString(), i = `${window.location.pathname}${n ? "?" + n : ""}${window.location.hash}`;
|
|
130
150
|
try {
|
|
131
151
|
window.history.replaceState({}, "", i);
|
|
132
152
|
} catch (a) {
|
|
133
|
-
|
|
153
|
+
o("warn", "History API not available, cannot replace URL", { error: a });
|
|
134
154
|
}
|
|
135
155
|
console.log(
|
|
136
156
|
"%c[TraceLog] QA Mode ACTIVE",
|
|
@@ -140,14 +160,14 @@ const Ue = () => {
|
|
|
140
160
|
return s;
|
|
141
161
|
}, he = () => {
|
|
142
162
|
const r = new URLSearchParams(window.location.search), e = {};
|
|
143
|
-
return
|
|
163
|
+
return be.forEach((s) => {
|
|
144
164
|
const n = r.get(s);
|
|
145
165
|
if (n) {
|
|
146
166
|
const i = s.split("utm_")[1];
|
|
147
167
|
e[i] = n;
|
|
148
168
|
}
|
|
149
169
|
}), Object.keys(e).length ? e : void 0;
|
|
150
|
-
},
|
|
170
|
+
}, je = () => typeof crypto < "u" && crypto.randomUUID ? crypto.randomUUID() : "xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx".replace(/[xy]/g, (r) => {
|
|
151
171
|
const e = Math.random() * 16 | 0;
|
|
152
172
|
return (r === "x" ? e : e & 3 | 8).toString(16);
|
|
153
173
|
}), Xe = () => {
|
|
@@ -168,34 +188,34 @@ const Ue = () => {
|
|
|
168
188
|
} catch {
|
|
169
189
|
return !1;
|
|
170
190
|
}
|
|
171
|
-
},
|
|
172
|
-
const e = r.allowHttp ?? !1;
|
|
191
|
+
}, We = (r) => {
|
|
173
192
|
if (r.integrations?.tracelog?.projectId) {
|
|
174
|
-
const
|
|
193
|
+
const n = new URL(window.location.href).hostname.split(".");
|
|
175
194
|
if (n.length === 0)
|
|
176
195
|
throw new Error("Invalid URL");
|
|
177
|
-
const i = r.integrations.tracelog.projectId, a = n.slice(-2).join("."),
|
|
178
|
-
if (!fe(
|
|
196
|
+
const i = r.integrations.tracelog.projectId, a = n.slice(-2).join("."), l = `https://${i}.${a}/collect`;
|
|
197
|
+
if (!fe(l))
|
|
179
198
|
throw new Error("Invalid URL");
|
|
180
|
-
return
|
|
199
|
+
return l;
|
|
181
200
|
}
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
201
|
+
const e = r.integrations?.custom?.collectApiUrl;
|
|
202
|
+
if (e) {
|
|
203
|
+
const t = r.integrations?.custom?.allowHttp ?? !1;
|
|
204
|
+
if (!fe(e, t))
|
|
185
205
|
throw new Error("Invalid URL");
|
|
186
|
-
return
|
|
206
|
+
return e;
|
|
187
207
|
}
|
|
188
208
|
return "";
|
|
189
|
-
},
|
|
209
|
+
}, Y = (r, e = []) => {
|
|
190
210
|
try {
|
|
191
211
|
const t = new URL(r), s = t.searchParams;
|
|
192
212
|
let n = !1;
|
|
193
213
|
const i = [];
|
|
194
|
-
return e.forEach((
|
|
195
|
-
s.has(
|
|
214
|
+
return e.forEach((l) => {
|
|
215
|
+
s.has(l) && (s.delete(l), n = !0, i.push(l));
|
|
196
216
|
}), !n && r.includes("?") ? r : (t.search = s.toString(), t.toString());
|
|
197
217
|
} catch (t) {
|
|
198
|
-
return
|
|
218
|
+
return o("warn", "URL normalization failed, returning original", { error: t, data: { url: r.slice(0, 100) } }), r;
|
|
199
219
|
}
|
|
200
220
|
}, ge = (r) => {
|
|
201
221
|
if (!r || typeof r != "string" || r.trim().length === 0)
|
|
@@ -203,11 +223,11 @@ const Ue = () => {
|
|
|
203
223
|
let e = r;
|
|
204
224
|
r.length > 1e3 && (e = r.slice(0, Math.max(0, 1e3)));
|
|
205
225
|
let t = 0;
|
|
206
|
-
for (const n of
|
|
226
|
+
for (const n of Oe) {
|
|
207
227
|
const i = e;
|
|
208
228
|
e = e.replace(n, ""), i !== e && t++;
|
|
209
229
|
}
|
|
210
|
-
return t > 0 &&
|
|
230
|
+
return t > 0 && o("warn", "XSS patterns detected and removed", {
|
|
211
231
|
data: {
|
|
212
232
|
patternMatches: t,
|
|
213
233
|
originalValue: r.slice(0, 100)
|
|
@@ -227,16 +247,16 @@ const Ue = () => {
|
|
|
227
247
|
if (typeof r == "object") {
|
|
228
248
|
const t = {}, n = Object.entries(r).slice(0, 20);
|
|
229
249
|
for (const [i, a] of n) {
|
|
230
|
-
const
|
|
231
|
-
if (
|
|
250
|
+
const l = ge(i);
|
|
251
|
+
if (l) {
|
|
232
252
|
const c = K(a, e + 1);
|
|
233
|
-
c !== null && (t[
|
|
253
|
+
c !== null && (t[l] = c);
|
|
234
254
|
}
|
|
235
255
|
}
|
|
236
256
|
return t;
|
|
237
257
|
}
|
|
238
258
|
return null;
|
|
239
|
-
},
|
|
259
|
+
}, Ye = (r) => {
|
|
240
260
|
if (typeof r != "object" || r === null)
|
|
241
261
|
return {};
|
|
242
262
|
try {
|
|
@@ -247,25 +267,25 @@ const Ue = () => {
|
|
|
247
267
|
throw new Error(`[TraceLog] Metadata sanitization failed: ${t}`);
|
|
248
268
|
}
|
|
249
269
|
}, Ke = (r) => {
|
|
250
|
-
if (
|
|
251
|
-
throw new
|
|
252
|
-
if (r
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
if (
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
268
|
-
|
|
270
|
+
if (r !== void 0 && (r === null || typeof r != "object"))
|
|
271
|
+
throw new y("Configuration must be an object", "config");
|
|
272
|
+
if (r) {
|
|
273
|
+
if (r.sessionTimeout !== void 0 && (typeof r.sessionTimeout != "number" || r.sessionTimeout < 3e4 || r.sessionTimeout > 864e5))
|
|
274
|
+
throw new Pe(m.INVALID_SESSION_TIMEOUT, "config");
|
|
275
|
+
if (r.globalMetadata !== void 0 && (typeof r.globalMetadata != "object" || r.globalMetadata === null))
|
|
276
|
+
throw new y(m.INVALID_GLOBAL_METADATA, "config");
|
|
277
|
+
if (r.scrollContainerSelectors !== void 0 && Ze(r.scrollContainerSelectors), r.integrations && Je(r.integrations), r.sensitiveQueryParams !== void 0) {
|
|
278
|
+
if (!Array.isArray(r.sensitiveQueryParams))
|
|
279
|
+
throw new y(m.INVALID_SENSITIVE_QUERY_PARAMS, "config");
|
|
280
|
+
for (const e of r.sensitiveQueryParams)
|
|
281
|
+
if (typeof e != "string")
|
|
282
|
+
throw new y("All sensitive query params must be strings", "config");
|
|
283
|
+
}
|
|
284
|
+
if (r.errorSampling !== void 0 && (typeof r.errorSampling != "number" || r.errorSampling < 0 || r.errorSampling > 1))
|
|
285
|
+
throw new oe(m.INVALID_ERROR_SAMPLING_RATE, "config");
|
|
286
|
+
if (r.samplingRate !== void 0 && (typeof r.samplingRate != "number" || r.samplingRate < 0 || r.samplingRate > 1))
|
|
287
|
+
throw new oe(m.INVALID_SAMPLING_RATE, "config");
|
|
288
|
+
}
|
|
269
289
|
}, qe = (r) => {
|
|
270
290
|
if (r.includes("<") || r.includes(">") || /on\w+\s*=/i.test(r) || !/^[a-zA-Z0-9\-_#.[\]="':, >+~*()]+$/.test(r))
|
|
271
291
|
return !1;
|
|
@@ -277,53 +297,67 @@ const Ue = () => {
|
|
|
277
297
|
for (const n of r)
|
|
278
298
|
if (n === "[" && s++, n === "]" && s--, s < 0) return !1;
|
|
279
299
|
return s === 0;
|
|
280
|
-
},
|
|
300
|
+
}, Ze = (r) => {
|
|
281
301
|
const e = Array.isArray(r) ? r : [r];
|
|
282
302
|
for (const t of e) {
|
|
283
303
|
if (typeof t != "string" || t.trim() === "")
|
|
284
|
-
throw
|
|
304
|
+
throw o("error", "Invalid scroll container selector", {
|
|
285
305
|
showToClient: !0,
|
|
286
306
|
data: {
|
|
287
307
|
selector: t,
|
|
288
308
|
type: typeof t,
|
|
289
309
|
isEmpty: t === "" || typeof t == "string" && t.trim() === ""
|
|
290
310
|
}
|
|
291
|
-
}), new
|
|
311
|
+
}), new y(m.INVALID_SCROLL_CONTAINER_SELECTORS, "config");
|
|
292
312
|
if (!qe(t))
|
|
293
|
-
throw
|
|
313
|
+
throw o("error", "Invalid or potentially unsafe CSS selector", {
|
|
294
314
|
showToClient: !0,
|
|
295
315
|
data: {
|
|
296
316
|
selector: t,
|
|
297
317
|
reason: "Failed security validation"
|
|
298
318
|
}
|
|
299
|
-
}), new
|
|
319
|
+
}), new y("Invalid or potentially unsafe CSS selector", "config");
|
|
300
320
|
}
|
|
301
|
-
},
|
|
321
|
+
}, Je = (r) => {
|
|
302
322
|
if (r) {
|
|
303
323
|
if (r.tracelog && (!r.tracelog.projectId || typeof r.tracelog.projectId != "string" || r.tracelog.projectId.trim() === ""))
|
|
304
|
-
throw new
|
|
324
|
+
throw new v(m.INVALID_TRACELOG_PROJECT_ID, "config");
|
|
305
325
|
if (r.custom) {
|
|
306
|
-
if (!r.custom.
|
|
307
|
-
throw new
|
|
308
|
-
if (
|
|
309
|
-
throw new
|
|
326
|
+
if (!r.custom.collectApiUrl || typeof r.custom.collectApiUrl != "string" || r.custom.collectApiUrl.trim() === "")
|
|
327
|
+
throw new v(m.INVALID_CUSTOM_API_URL, "config");
|
|
328
|
+
if (r.custom.allowHttp !== void 0 && typeof r.custom.allowHttp != "boolean")
|
|
329
|
+
throw new v("allowHttp must be a boolean", "config");
|
|
330
|
+
const e = r.custom.collectApiUrl.trim();
|
|
331
|
+
if (!e.startsWith("http://") && !e.startsWith("https://"))
|
|
332
|
+
throw new v('Custom API URL must start with "http://" or "https://"', "config");
|
|
333
|
+
if (!(r.custom.allowHttp ?? !1) && e.startsWith("http://"))
|
|
334
|
+
throw new v(
|
|
335
|
+
"Custom API URL must use HTTPS in production. Set allowHttp: true in integration config to allow HTTP (not recommended)",
|
|
336
|
+
"config"
|
|
337
|
+
);
|
|
310
338
|
}
|
|
311
339
|
if (r.googleAnalytics) {
|
|
312
340
|
if (!r.googleAnalytics.measurementId || typeof r.googleAnalytics.measurementId != "string" || r.googleAnalytics.measurementId.trim() === "")
|
|
313
|
-
throw new
|
|
341
|
+
throw new v(m.INVALID_GOOGLE_ANALYTICS_ID, "config");
|
|
314
342
|
if (!r.googleAnalytics.measurementId.trim().match(/^(G-|UA-)/))
|
|
315
|
-
throw new
|
|
316
|
-
}
|
|
317
|
-
}
|
|
318
|
-
}, et = (r) =>
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
343
|
+
throw new v('Google Analytics measurement ID must start with "G-" or "UA-"', "config");
|
|
344
|
+
}
|
|
345
|
+
}
|
|
346
|
+
}, et = (r) => {
|
|
347
|
+
Ke(r);
|
|
348
|
+
const e = {
|
|
349
|
+
...r ?? {},
|
|
350
|
+
sessionTimeout: r?.sessionTimeout ?? 9e5,
|
|
351
|
+
globalMetadata: r?.globalMetadata ?? {},
|
|
352
|
+
sensitiveQueryParams: r?.sensitiveQueryParams ?? [],
|
|
353
|
+
errorSampling: r?.errorSampling ?? 1,
|
|
354
|
+
samplingRate: r?.samplingRate ?? 1
|
|
355
|
+
};
|
|
356
|
+
return e.integrations?.custom && (e.integrations.custom = {
|
|
357
|
+
...e.integrations.custom,
|
|
358
|
+
allowHttp: e.integrations.custom.allowHttp ?? !1
|
|
359
|
+
}), e;
|
|
360
|
+
}, tt = (r) => {
|
|
327
361
|
if (typeof r == "string")
|
|
328
362
|
return !0;
|
|
329
363
|
if (typeof r == "object" && r !== null && !Array.isArray(r)) {
|
|
@@ -378,7 +412,7 @@ const Ue = () => {
|
|
|
378
412
|
valid: !1,
|
|
379
413
|
error: "Event name cannot be a reserved word"
|
|
380
414
|
} : { valid: !0 }, Se = (r, e, t) => {
|
|
381
|
-
const s =
|
|
415
|
+
const s = Ye(e), n = `${t} "${r}" metadata error`;
|
|
382
416
|
if (!rt(s))
|
|
383
417
|
return {
|
|
384
418
|
valid: !1,
|
|
@@ -403,24 +437,24 @@ const Ue = () => {
|
|
|
403
437
|
valid: !1,
|
|
404
438
|
error: `${n}: object has too many keys (max 10 keys).`
|
|
405
439
|
};
|
|
406
|
-
for (const [
|
|
440
|
+
for (const [l, c] of Object.entries(s)) {
|
|
407
441
|
if (Array.isArray(c)) {
|
|
408
442
|
if (c.length > 10)
|
|
409
443
|
return {
|
|
410
444
|
valid: !1,
|
|
411
|
-
error: `${n}: array property "${
|
|
445
|
+
error: `${n}: array property "${l}" is too large (max 10 items).`
|
|
412
446
|
};
|
|
413
447
|
for (const u of c)
|
|
414
448
|
if (typeof u == "string" && u.length > 500)
|
|
415
449
|
return {
|
|
416
450
|
valid: !1,
|
|
417
|
-
error: `${n}: array property "${
|
|
451
|
+
error: `${n}: array property "${l}" contains strings that are too long (max 500 characters).`
|
|
418
452
|
};
|
|
419
453
|
}
|
|
420
454
|
if (typeof c == "string" && c.length > 1e3)
|
|
421
455
|
return {
|
|
422
456
|
valid: !1,
|
|
423
|
-
error: `${n}: property "${
|
|
457
|
+
error: `${n}: property "${l}" is too long (max 1000 characters).`
|
|
424
458
|
};
|
|
425
459
|
}
|
|
426
460
|
return {
|
|
@@ -437,13 +471,13 @@ const Ue = () => {
|
|
|
437
471
|
valid: !1,
|
|
438
472
|
error: `${n}: array item at index ${i} must be an object.`
|
|
439
473
|
};
|
|
440
|
-
const
|
|
441
|
-
if (!
|
|
474
|
+
const l = Se(r, a, t);
|
|
475
|
+
if (!l.valid)
|
|
442
476
|
return {
|
|
443
477
|
valid: !1,
|
|
444
|
-
error: `${n}: array item at index ${i} is invalid: ${
|
|
478
|
+
error: `${n}: array item at index ${i} is invalid: ${l.error}`
|
|
445
479
|
};
|
|
446
|
-
|
|
480
|
+
l.sanitizedMetadata && s.push(l.sanitizedMetadata);
|
|
447
481
|
}
|
|
448
482
|
return {
|
|
449
483
|
valid: !0,
|
|
@@ -454,14 +488,14 @@ const Ue = () => {
|
|
|
454
488
|
}, it = (r, e) => {
|
|
455
489
|
const t = st(r);
|
|
456
490
|
if (!t.valid)
|
|
457
|
-
return
|
|
491
|
+
return o("error", "Event name validation failed", {
|
|
458
492
|
showToClient: !0,
|
|
459
493
|
data: { eventName: r, error: t.error }
|
|
460
494
|
}), t;
|
|
461
495
|
if (!e)
|
|
462
496
|
return { valid: !0 };
|
|
463
497
|
const s = nt(r, e, "customEvent");
|
|
464
|
-
return s.valid ||
|
|
498
|
+
return s.valid || o("error", "Event metadata validation failed", {
|
|
465
499
|
showToClient: !0,
|
|
466
500
|
data: {
|
|
467
501
|
eventName: r,
|
|
@@ -516,15 +550,15 @@ class ot extends f {
|
|
|
516
550
|
sendEventsQueueSync(e) {
|
|
517
551
|
if (this.shouldSkipSend())
|
|
518
552
|
return this.resetRetryState(), !0;
|
|
519
|
-
if (this.get("config")?.integrations?.custom?.
|
|
520
|
-
return
|
|
553
|
+
if (this.get("config")?.integrations?.custom?.collectApiUrl === j.Fail)
|
|
554
|
+
return o("warn", "Fail mode: simulating network failure (sync)", {
|
|
521
555
|
data: { events: e.events.length }
|
|
522
556
|
}), !1;
|
|
523
557
|
const s = this.sendQueueSyncInternal(e);
|
|
524
558
|
return s && this.resetRetryState(), s;
|
|
525
559
|
}
|
|
526
560
|
async sendEventsQueue(e, t) {
|
|
527
|
-
this.shouldSkipSend() || this.persistEvents(e) ||
|
|
561
|
+
this.shouldSkipSend() || this.persistEvents(e) || o("warn", "Failed to persist events, attempting immediate send");
|
|
528
562
|
const s = await this.send(e);
|
|
529
563
|
return s ? (this.clearPersistedEvents(), this.resetRetryState(), t?.onSuccess?.(e.events.length, e.events, e)) : (this.scheduleRetry(e, t), t?.onFailure?.()), s;
|
|
530
564
|
}
|
|
@@ -538,7 +572,7 @@ class ot extends f {
|
|
|
538
572
|
const s = this.createRecoveryBody(t);
|
|
539
573
|
await this.send(s) ? (this.clearPersistedEvents(), this.resetRetryState(), e?.onSuccess?.(t.events.length, t.events, s)) : (this.scheduleRetry(s, e), e?.onFailure?.());
|
|
540
574
|
} catch (t) {
|
|
541
|
-
|
|
575
|
+
o("error", "Failed to recover persisted events", { error: t }), this.clearPersistedEvents();
|
|
542
576
|
}
|
|
543
577
|
}
|
|
544
578
|
persistEventsForRecovery(e) {
|
|
@@ -553,15 +587,15 @@ class ot extends f {
|
|
|
553
587
|
async send(e) {
|
|
554
588
|
if (this.shouldSkipSend())
|
|
555
589
|
return this.simulateSuccessfulSend();
|
|
556
|
-
if (this.get("config")?.integrations?.custom?.
|
|
557
|
-
return
|
|
590
|
+
if (this.get("config")?.integrations?.custom?.collectApiUrl === j.Fail)
|
|
591
|
+
return o("warn", "Fail mode: simulating network failure", {
|
|
558
592
|
data: { events: e.events.length }
|
|
559
593
|
}), !1;
|
|
560
594
|
const { url: s, payload: n } = this.prepareRequest(e);
|
|
561
595
|
try {
|
|
562
596
|
return (await this.sendWithTimeout(s, n)).ok;
|
|
563
597
|
} catch (i) {
|
|
564
|
-
return
|
|
598
|
+
return o("error", "Send request failed", {
|
|
565
599
|
error: i,
|
|
566
600
|
data: {
|
|
567
601
|
events: e.events.length,
|
|
@@ -595,13 +629,13 @@ class ot extends f {
|
|
|
595
629
|
if (this.isSendBeaconAvailable()) {
|
|
596
630
|
if (navigator.sendBeacon(t, n))
|
|
597
631
|
return !0;
|
|
598
|
-
|
|
632
|
+
o("warn", "sendBeacon failed, persisting events for recovery");
|
|
599
633
|
} else
|
|
600
|
-
|
|
634
|
+
o("warn", "sendBeacon not available, persisting events for recovery");
|
|
601
635
|
return this.persistEventsForRecovery(e), !1;
|
|
602
636
|
}
|
|
603
637
|
prepareRequest(e) {
|
|
604
|
-
const t =
|
|
638
|
+
const t = {
|
|
605
639
|
...e,
|
|
606
640
|
_metadata: {
|
|
607
641
|
referer: typeof window < "u" ? window.location.href : void 0,
|
|
@@ -609,8 +643,8 @@ class ot extends f {
|
|
|
609
643
|
}
|
|
610
644
|
};
|
|
611
645
|
return {
|
|
612
|
-
url:
|
|
613
|
-
payload: JSON.stringify(
|
|
646
|
+
url: this.get("collectApiUrl"),
|
|
647
|
+
payload: JSON.stringify(t)
|
|
614
648
|
};
|
|
615
649
|
}
|
|
616
650
|
getPersistedData() {
|
|
@@ -619,7 +653,7 @@ class ot extends f {
|
|
|
619
653
|
if (t)
|
|
620
654
|
return JSON.parse(t);
|
|
621
655
|
} catch (e) {
|
|
622
|
-
|
|
656
|
+
o("warn", "Failed to parse persisted data", { error: e }), this.clearPersistedEvents();
|
|
623
657
|
}
|
|
624
658
|
return null;
|
|
625
659
|
}
|
|
@@ -647,7 +681,7 @@ class ot extends f {
|
|
|
647
681
|
}, s = this.getQueueStorageKey();
|
|
648
682
|
return this.storeManager.setItem(s, JSON.stringify(t)), !!this.storeManager.getItem(s);
|
|
649
683
|
} catch (t) {
|
|
650
|
-
return
|
|
684
|
+
return o("warn", "Failed to persist events", { error: t }), !1;
|
|
651
685
|
}
|
|
652
686
|
}
|
|
653
687
|
clearPersistedEvents() {
|
|
@@ -655,7 +689,7 @@ class ot extends f {
|
|
|
655
689
|
const e = this.getQueueStorageKey();
|
|
656
690
|
this.storeManager.removeItem(e);
|
|
657
691
|
} catch (e) {
|
|
658
|
-
|
|
692
|
+
o("warn", "Failed to clear persisted events", { error: e });
|
|
659
693
|
}
|
|
660
694
|
}
|
|
661
695
|
resetRetryState() {
|
|
@@ -665,7 +699,7 @@ class ot extends f {
|
|
|
665
699
|
if (this.retryTimeoutId !== null || this.isRetrying)
|
|
666
700
|
return;
|
|
667
701
|
if (this.retryCount >= 3) {
|
|
668
|
-
|
|
702
|
+
o("warn", "Max retries reached, giving up", { data: { retryCount: this.retryCount } }), this.clearPersistedEvents(), this.resetRetryState(), t?.onFailure?.();
|
|
669
703
|
return;
|
|
670
704
|
}
|
|
671
705
|
const s = 5e3 * Math.pow(2, this.retryCount);
|
|
@@ -679,7 +713,7 @@ class ot extends f {
|
|
|
679
713
|
}, s);
|
|
680
714
|
}
|
|
681
715
|
shouldSkipSend() {
|
|
682
|
-
return !this.get("
|
|
716
|
+
return !this.get("collectApiUrl");
|
|
683
717
|
}
|
|
684
718
|
async simulateSuccessfulSend() {
|
|
685
719
|
const e = Math.random() * 400 + 100;
|
|
@@ -701,6 +735,8 @@ class lt extends f {
|
|
|
701
735
|
lastEventFingerprint = null;
|
|
702
736
|
lastEventTime = 0;
|
|
703
737
|
sendIntervalId = null;
|
|
738
|
+
rateLimitCounter = 0;
|
|
739
|
+
rateLimitWindowStart = 0;
|
|
704
740
|
constructor(e, t = null, s = null) {
|
|
705
741
|
super(), this.googleAnalytics = t, this.dataSender = new ot(e), this.emitter = s;
|
|
706
742
|
}
|
|
@@ -713,7 +749,7 @@ class lt extends f {
|
|
|
713
749
|
}
|
|
714
750
|
},
|
|
715
751
|
onFailure: async () => {
|
|
716
|
-
|
|
752
|
+
o("warn", "Failed to recover persisted events");
|
|
717
753
|
}
|
|
718
754
|
});
|
|
719
755
|
}
|
|
@@ -724,68 +760,73 @@ class lt extends f {
|
|
|
724
760
|
scroll_data: n,
|
|
725
761
|
click_data: i,
|
|
726
762
|
custom_event: a,
|
|
727
|
-
web_vitals:
|
|
763
|
+
web_vitals: l,
|
|
728
764
|
error_data: c,
|
|
729
765
|
session_end_reason: u
|
|
730
766
|
}) {
|
|
731
767
|
if (!e) {
|
|
732
|
-
|
|
768
|
+
o("error", "Event type is required - event will be ignored");
|
|
733
769
|
return;
|
|
734
770
|
}
|
|
735
771
|
if (!this.get("sessionId")) {
|
|
736
|
-
this.pendingEventsBuffer.
|
|
772
|
+
this.pendingEventsBuffer.length >= 100 && (this.pendingEventsBuffer.shift(), o("warn", "Pending events buffer full - dropping oldest event", {
|
|
773
|
+
data: { maxBufferSize: 100 }
|
|
774
|
+
})), this.pendingEventsBuffer.push({
|
|
737
775
|
type: e,
|
|
738
776
|
page_url: t,
|
|
739
777
|
from_page_url: s,
|
|
740
778
|
scroll_data: n,
|
|
741
779
|
click_data: i,
|
|
742
780
|
custom_event: a,
|
|
743
|
-
web_vitals:
|
|
781
|
+
web_vitals: l,
|
|
744
782
|
error_data: c,
|
|
745
783
|
session_end_reason: u
|
|
746
784
|
});
|
|
747
785
|
return;
|
|
748
786
|
}
|
|
749
|
-
const
|
|
750
|
-
|
|
751
|
-
|
|
787
|
+
const p = e === d.SESSION_START || e === d.SESSION_END;
|
|
788
|
+
if (!p && !this.checkRateLimit())
|
|
789
|
+
return;
|
|
790
|
+
const N = e, Le = N === d.SESSION_START, Re = t || this.get("pageUrl"), z = this.buildEventPayload({
|
|
791
|
+
type: N,
|
|
792
|
+
page_url: Re,
|
|
752
793
|
from_page_url: s,
|
|
753
794
|
scroll_data: n,
|
|
754
795
|
click_data: i,
|
|
755
796
|
custom_event: a,
|
|
756
|
-
web_vitals:
|
|
797
|
+
web_vitals: l,
|
|
757
798
|
error_data: c,
|
|
758
799
|
session_end_reason: u
|
|
759
800
|
});
|
|
760
|
-
if (!(!
|
|
761
|
-
if (
|
|
801
|
+
if (!(!p && !this.shouldSample())) {
|
|
802
|
+
if (Le) {
|
|
762
803
|
const ae = this.get("sessionId");
|
|
763
804
|
if (!ae) {
|
|
764
|
-
|
|
805
|
+
o("error", "Session start event requires sessionId - event will be ignored");
|
|
765
806
|
return;
|
|
766
807
|
}
|
|
767
808
|
if (this.get("hasStartSession")) {
|
|
768
|
-
|
|
809
|
+
o("warn", "Duplicate session_start detected", {
|
|
769
810
|
data: { sessionId: ae }
|
|
770
811
|
});
|
|
771
812
|
return;
|
|
772
813
|
}
|
|
773
814
|
this.set("hasStartSession", !0);
|
|
774
815
|
}
|
|
775
|
-
if (!this.isDuplicateEvent(
|
|
776
|
-
if (this.get("mode") === R.QA &&
|
|
816
|
+
if (!this.isDuplicateEvent(z)) {
|
|
817
|
+
if (this.get("mode") === R.QA && N === d.CUSTOM && a) {
|
|
777
818
|
console.log("[TraceLog] Event", {
|
|
778
819
|
name: a.name,
|
|
779
820
|
...a.metadata && { metadata: a.metadata }
|
|
780
|
-
}), this.emitEvent(
|
|
821
|
+
}), this.emitEvent(z);
|
|
781
822
|
return;
|
|
782
823
|
}
|
|
783
|
-
this.addToQueue(
|
|
824
|
+
this.addToQueue(z);
|
|
784
825
|
}
|
|
785
826
|
}
|
|
786
827
|
}
|
|
787
828
|
stop() {
|
|
788
|
-
this.sendIntervalId && (clearInterval(this.sendIntervalId), this.sendIntervalId = null), this.eventsQueue = [], this.pendingEventsBuffer = [], this.lastEventFingerprint = null, this.lastEventTime = 0, this.dataSender.stop();
|
|
829
|
+
this.sendIntervalId && (clearInterval(this.sendIntervalId), this.sendIntervalId = null), this.eventsQueue = [], this.pendingEventsBuffer = [], this.lastEventFingerprint = null, this.lastEventTime = 0, this.rateLimitCounter = 0, this.rateLimitWindowStart = 0, this.dataSender.stop();
|
|
789
830
|
}
|
|
790
831
|
async flushImmediately() {
|
|
791
832
|
return this.flushEvents(!1);
|
|
@@ -800,12 +841,14 @@ class lt extends f {
|
|
|
800
841
|
if (this.pendingEventsBuffer.length === 0)
|
|
801
842
|
return;
|
|
802
843
|
if (!this.get("sessionId")) {
|
|
803
|
-
|
|
844
|
+
o("warn", "Cannot flush pending events: session not initialized - keeping in buffer", {
|
|
845
|
+
data: { bufferedEventCount: this.pendingEventsBuffer.length }
|
|
846
|
+
});
|
|
804
847
|
return;
|
|
805
848
|
}
|
|
806
|
-
const
|
|
807
|
-
this.pendingEventsBuffer = [],
|
|
808
|
-
this.track(
|
|
849
|
+
const t = [...this.pendingEventsBuffer];
|
|
850
|
+
this.pendingEventsBuffer = [], t.forEach((s) => {
|
|
851
|
+
this.track(s);
|
|
809
852
|
});
|
|
810
853
|
}
|
|
811
854
|
clearSendInterval() {
|
|
@@ -824,7 +867,7 @@ class lt extends f {
|
|
|
824
867
|
this.removeProcessedEvents(n), this.clearSendInterval(), this.emitEventsQueue(t);
|
|
825
868
|
},
|
|
826
869
|
onFailure: () => {
|
|
827
|
-
|
|
870
|
+
o("warn", "Async flush failed", {
|
|
828
871
|
data: { eventCount: s.length }
|
|
829
872
|
});
|
|
830
873
|
}
|
|
@@ -839,7 +882,7 @@ class lt extends f {
|
|
|
839
882
|
this.removeProcessedEvents(s), this.emitEventsQueue(e);
|
|
840
883
|
},
|
|
841
884
|
onFailure: async () => {
|
|
842
|
-
|
|
885
|
+
o("warn", "Events send failed, keeping in queue", {
|
|
843
886
|
data: { eventCount: t.length }
|
|
844
887
|
});
|
|
845
888
|
}
|
|
@@ -898,7 +941,7 @@ class lt extends f {
|
|
|
898
941
|
const t = this.eventsQueue.findIndex(
|
|
899
942
|
(n) => n.type !== d.SESSION_START && n.type !== d.SESSION_END
|
|
900
943
|
), s = t >= 0 ? this.eventsQueue.splice(t, 1)[0] : this.eventsQueue.shift();
|
|
901
|
-
|
|
944
|
+
o("warn", "Event queue overflow, oldest non-critical event removed", {
|
|
902
945
|
data: {
|
|
903
946
|
maxLength: 100,
|
|
904
947
|
currentLength: this.eventsQueue.length,
|
|
@@ -925,6 +968,10 @@ class lt extends f {
|
|
|
925
968
|
const e = this.get("config")?.samplingRate ?? 1;
|
|
926
969
|
return Math.random() < e;
|
|
927
970
|
}
|
|
971
|
+
checkRateLimit() {
|
|
972
|
+
const e = Date.now();
|
|
973
|
+
return e - this.rateLimitWindowStart > 1e3 && (this.rateLimitCounter = 0, this.rateLimitWindowStart = e), this.rateLimitCounter >= 200 ? !1 : (this.rateLimitCounter++, !0);
|
|
974
|
+
}
|
|
928
975
|
removeProcessedEvents(e) {
|
|
929
976
|
const t = new Set(e);
|
|
930
977
|
this.eventsQueue = this.eventsQueue.filter((s) => !t.has(s.id));
|
|
@@ -949,7 +996,7 @@ class ct {
|
|
|
949
996
|
const t = xe, s = e.getItem(t);
|
|
950
997
|
if (s)
|
|
951
998
|
return s;
|
|
952
|
-
const n =
|
|
999
|
+
const n = je();
|
|
953
1000
|
return e.setItem(t, n), n;
|
|
954
1001
|
}
|
|
955
1002
|
}
|
|
@@ -968,7 +1015,7 @@ class ut extends f {
|
|
|
968
1015
|
}
|
|
969
1016
|
initCrossTabSync() {
|
|
970
1017
|
if (typeof BroadcastChannel > "u") {
|
|
971
|
-
|
|
1018
|
+
o("warn", "BroadcastChannel not supported");
|
|
972
1019
|
return;
|
|
973
1020
|
}
|
|
974
1021
|
const e = this.getProjectId();
|
|
@@ -1043,7 +1090,7 @@ class ut extends f {
|
|
|
1043
1090
|
}
|
|
1044
1091
|
async startTracking() {
|
|
1045
1092
|
if (this.isTracking) {
|
|
1046
|
-
|
|
1093
|
+
o("warn", "Session tracking already active");
|
|
1047
1094
|
return;
|
|
1048
1095
|
}
|
|
1049
1096
|
const e = this.recoverSession(), t = e ?? this.generateSessionId(), s = !!e;
|
|
@@ -1093,7 +1140,7 @@ class ut extends f {
|
|
|
1093
1140
|
async endSession(e) {
|
|
1094
1141
|
const t = this.get("sessionId");
|
|
1095
1142
|
if (!t) {
|
|
1096
|
-
|
|
1143
|
+
o("warn", "endSession called without active session", { data: { reason: e } }), this.resetSessionState(e);
|
|
1097
1144
|
return;
|
|
1098
1145
|
}
|
|
1099
1146
|
this.eventManager.track({
|
|
@@ -1110,7 +1157,7 @@ class ut extends f {
|
|
|
1110
1157
|
try {
|
|
1111
1158
|
await this.eventManager.flushImmediately(), s();
|
|
1112
1159
|
} catch (i) {
|
|
1113
|
-
|
|
1160
|
+
o("warn", "Async flush failed during session end", { error: i }), s();
|
|
1114
1161
|
}
|
|
1115
1162
|
}
|
|
1116
1163
|
resetSessionState(e) {
|
|
@@ -1135,10 +1182,10 @@ class dt extends f {
|
|
|
1135
1182
|
if (this.isActive())
|
|
1136
1183
|
return;
|
|
1137
1184
|
if (this.destroyed) {
|
|
1138
|
-
|
|
1185
|
+
o("warn", "Cannot start tracking on destroyed handler");
|
|
1139
1186
|
return;
|
|
1140
1187
|
}
|
|
1141
|
-
const e = this.get("config"), t = e?.integrations?.tracelog?.projectId ?? e?.integrations?.custom?.
|
|
1188
|
+
const e = this.get("config"), t = e?.integrations?.tracelog?.projectId ?? e?.integrations?.custom?.collectApiUrl ?? "default";
|
|
1142
1189
|
if (!t)
|
|
1143
1190
|
throw new Error("Cannot start session tracking: config not available");
|
|
1144
1191
|
try {
|
|
@@ -1151,7 +1198,7 @@ class dt extends f {
|
|
|
1151
1198
|
}
|
|
1152
1199
|
this.sessionManager = null;
|
|
1153
1200
|
}
|
|
1154
|
-
throw
|
|
1201
|
+
throw o("error", "Failed to start session tracking", { error: s }), s;
|
|
1155
1202
|
}
|
|
1156
1203
|
}
|
|
1157
1204
|
isActive() {
|
|
@@ -1188,7 +1235,7 @@ class ht extends f {
|
|
|
1188
1235
|
};
|
|
1189
1236
|
}
|
|
1190
1237
|
trackCurrentPage = async () => {
|
|
1191
|
-
const e = window.location.href, t =
|
|
1238
|
+
const e = window.location.href, t = Y(e, this.get("config").sensitiveQueryParams);
|
|
1192
1239
|
if (this.get("pageUrl") === t)
|
|
1193
1240
|
return;
|
|
1194
1241
|
this.onTrack();
|
|
@@ -1203,7 +1250,7 @@ class ht extends f {
|
|
|
1203
1250
|
});
|
|
1204
1251
|
};
|
|
1205
1252
|
trackInitialPageView() {
|
|
1206
|
-
const e =
|
|
1253
|
+
const e = Y(window.location.href, this.get("config").sensitiveQueryParams), t = this.extractPageViewData();
|
|
1207
1254
|
this.eventManager.track({
|
|
1208
1255
|
type: d.PAGE_VIEW,
|
|
1209
1256
|
page_url: e,
|
|
@@ -1229,26 +1276,26 @@ class ft extends f {
|
|
|
1229
1276
|
}
|
|
1230
1277
|
startTracking() {
|
|
1231
1278
|
this.clickHandler || (this.clickHandler = (e) => {
|
|
1232
|
-
const t = e, s = t.target, n = s instanceof HTMLElement ? s : s instanceof Node && s.parentElement instanceof HTMLElement ? s.parentElement : null;
|
|
1279
|
+
const t = e, s = t.target, n = typeof HTMLElement < "u" && s instanceof HTMLElement ? s : typeof HTMLElement < "u" && s instanceof Node && s.parentElement instanceof HTMLElement ? s.parentElement : null;
|
|
1233
1280
|
if (!n) {
|
|
1234
|
-
|
|
1281
|
+
o("warn", "Click target not found or not an element");
|
|
1235
1282
|
return;
|
|
1236
1283
|
}
|
|
1237
|
-
const i = this.findTrackingElement(n), a = this.getRelevantClickElement(n),
|
|
1284
|
+
const i = this.findTrackingElement(n), a = this.getRelevantClickElement(n), l = this.calculateClickCoordinates(t, n);
|
|
1238
1285
|
if (i) {
|
|
1239
1286
|
const u = this.extractTrackingData(i);
|
|
1240
1287
|
if (u) {
|
|
1241
|
-
const
|
|
1288
|
+
const p = this.createCustomEventData(u);
|
|
1242
1289
|
this.eventManager.track({
|
|
1243
1290
|
type: d.CUSTOM,
|
|
1244
1291
|
custom_event: {
|
|
1245
|
-
name:
|
|
1246
|
-
...
|
|
1292
|
+
name: p.name,
|
|
1293
|
+
...p.value && { metadata: { value: p.value } }
|
|
1247
1294
|
}
|
|
1248
1295
|
});
|
|
1249
1296
|
}
|
|
1250
1297
|
}
|
|
1251
|
-
const c = this.generateClickData(n, a,
|
|
1298
|
+
const c = this.generateClickData(n, a, l);
|
|
1252
1299
|
this.eventManager.track({
|
|
1253
1300
|
type: d.CLICK,
|
|
1254
1301
|
click_data: c
|
|
@@ -1262,7 +1309,7 @@ class ft extends f {
|
|
|
1262
1309
|
return e.hasAttribute(`${O}-name`) ? e : e.closest(`[${O}-name]`) || void 0;
|
|
1263
1310
|
}
|
|
1264
1311
|
getRelevantClickElement(e) {
|
|
1265
|
-
for (const t of
|
|
1312
|
+
for (const t of Ce)
|
|
1266
1313
|
try {
|
|
1267
1314
|
if (e.matches(t))
|
|
1268
1315
|
return e;
|
|
@@ -1270,7 +1317,7 @@ class ft extends f {
|
|
|
1270
1317
|
if (s)
|
|
1271
1318
|
return s;
|
|
1272
1319
|
} catch (s) {
|
|
1273
|
-
|
|
1320
|
+
o("warn", "Invalid selector in element search", { error: s, data: { selector: t } });
|
|
1274
1321
|
continue;
|
|
1275
1322
|
}
|
|
1276
1323
|
return e;
|
|
@@ -1279,8 +1326,8 @@ class ft extends f {
|
|
|
1279
1326
|
return Math.max(0, Math.min(1, Number(e.toFixed(3))));
|
|
1280
1327
|
}
|
|
1281
1328
|
calculateClickCoordinates(e, t) {
|
|
1282
|
-
const s = t.getBoundingClientRect(), n = e.clientX, i = e.clientY, a = s.width > 0 ? this.clamp((n - s.left) / s.width) : 0,
|
|
1283
|
-
return { x: n, y: i, relativeX: a, relativeY:
|
|
1329
|
+
const s = t.getBoundingClientRect(), n = e.clientX, i = e.clientY, a = s.width > 0 ? this.clamp((n - s.left) / s.width) : 0, l = s.height > 0 ? this.clamp((i - s.top) / s.height) : 0;
|
|
1330
|
+
return { x: n, y: i, relativeX: a, relativeY: l };
|
|
1284
1331
|
}
|
|
1285
1332
|
extractTrackingData(e) {
|
|
1286
1333
|
const t = e.getAttribute(`${O}-name`), s = e.getAttribute(`${O}-value`);
|
|
@@ -1292,12 +1339,12 @@ class ft extends f {
|
|
|
1292
1339
|
};
|
|
1293
1340
|
}
|
|
1294
1341
|
generateClickData(e, t, s) {
|
|
1295
|
-
const { x: n, y: i, relativeX: a, relativeY:
|
|
1342
|
+
const { x: n, y: i, relativeX: a, relativeY: l } = s, c = this.getRelevantText(e, t), u = this.extractElementAttributes(t);
|
|
1296
1343
|
return {
|
|
1297
1344
|
x: n,
|
|
1298
1345
|
y: i,
|
|
1299
1346
|
relativeX: a,
|
|
1300
|
-
relativeY:
|
|
1347
|
+
relativeY: l,
|
|
1301
1348
|
tag: t.tagName.toLowerCase(),
|
|
1302
1349
|
...t.id && { id: t.id },
|
|
1303
1350
|
...t.className && { class: t.className },
|
|
@@ -1361,7 +1408,9 @@ class gt extends f {
|
|
|
1361
1408
|
this.containers.length = 0, this.set("scrollEventCount", 0), this.limitWarningLogged = !1;
|
|
1362
1409
|
}
|
|
1363
1410
|
trySetupContainers(e, t) {
|
|
1364
|
-
const s = e.map((n) => this.safeQuerySelector(n)).filter(
|
|
1411
|
+
const s = e.map((n) => this.safeQuerySelector(n)).filter(
|
|
1412
|
+
(n) => n != null && typeof HTMLElement < "u" && n instanceof HTMLElement
|
|
1413
|
+
);
|
|
1365
1414
|
if (s.length > 0) {
|
|
1366
1415
|
for (const n of s)
|
|
1367
1416
|
this.containers.some((a) => a.element === n) || this.setupScrollContainer(n);
|
|
@@ -1423,7 +1472,7 @@ class gt extends f {
|
|
|
1423
1472
|
return Math.abs(t - e.lastDepth) >= this.minDepthChange;
|
|
1424
1473
|
}
|
|
1425
1474
|
logLimitOnce() {
|
|
1426
|
-
this.limitWarningLogged || (this.limitWarningLogged = !0,
|
|
1475
|
+
this.limitWarningLogged || (this.limitWarningLogged = !0, o("warn", "Max scroll events per session reached", {
|
|
1427
1476
|
data: { limit: this.maxEventsPerSession }
|
|
1428
1477
|
}));
|
|
1429
1478
|
}
|
|
@@ -1449,7 +1498,7 @@ class gt extends f {
|
|
|
1449
1498
|
const { element: t, lastScrollPos: s } = e, n = this.getScrollTop(t);
|
|
1450
1499
|
if (Math.abs(n - s) < 10 || t === window && !this.isWindowScrollable())
|
|
1451
1500
|
return null;
|
|
1452
|
-
const a = this.getViewportHeight(t),
|
|
1501
|
+
const a = this.getViewportHeight(t), l = this.getScrollHeight(t), c = this.getScrollDirection(n, s), u = this.calculateScrollDepth(n, l, a);
|
|
1453
1502
|
return e.lastScrollPos = n, { depth: u, direction: c };
|
|
1454
1503
|
}
|
|
1455
1504
|
getScrollTop(e) {
|
|
@@ -1469,7 +1518,7 @@ class gt extends f {
|
|
|
1469
1518
|
try {
|
|
1470
1519
|
return document.querySelector(e);
|
|
1471
1520
|
} catch (t) {
|
|
1472
|
-
return
|
|
1521
|
+
return o("warn", "Invalid CSS selector", {
|
|
1473
1522
|
error: t,
|
|
1474
1523
|
data: { selector: e },
|
|
1475
1524
|
showToClient: !0
|
|
@@ -1491,7 +1540,7 @@ class St extends f {
|
|
|
1491
1540
|
}
|
|
1492
1541
|
await this.loadScript(e), this.configureGtag(e, t), this.isInitialized = !0;
|
|
1493
1542
|
} catch (s) {
|
|
1494
|
-
|
|
1543
|
+
o("error", "Google Analytics initialization failed", { error: s });
|
|
1495
1544
|
}
|
|
1496
1545
|
}
|
|
1497
1546
|
trackEvent(e, t) {
|
|
@@ -1500,7 +1549,7 @@ class St extends f {
|
|
|
1500
1549
|
const s = Array.isArray(t) ? { items: t } : t;
|
|
1501
1550
|
window.gtag("event", e, s);
|
|
1502
1551
|
} catch (s) {
|
|
1503
|
-
|
|
1552
|
+
o("error", "Google Analytics event tracking failed", { error: s });
|
|
1504
1553
|
}
|
|
1505
1554
|
}
|
|
1506
1555
|
cleanup() {
|
|
@@ -1536,7 +1585,7 @@ class Et {
|
|
|
1536
1585
|
fallbackSessionStorage = /* @__PURE__ */ new Map();
|
|
1537
1586
|
hasQuotaExceededError = !1;
|
|
1538
1587
|
constructor() {
|
|
1539
|
-
this.storage = this.initializeStorage("localStorage"), this.sessionStorageRef = this.initializeStorage("sessionStorage"), this.storage ||
|
|
1588
|
+
this.storage = this.initializeStorage("localStorage"), this.sessionStorageRef = this.initializeStorage("sessionStorage"), this.storage || o("warn", "localStorage not available, using memory fallback"), this.sessionStorageRef || o("warn", "sessionStorage not available, using memory fallback");
|
|
1540
1589
|
}
|
|
1541
1590
|
/**
|
|
1542
1591
|
* Retrieves an item from storage
|
|
@@ -1552,18 +1601,34 @@ class Et {
|
|
|
1552
1601
|
* Stores an item in storage
|
|
1553
1602
|
*/
|
|
1554
1603
|
setItem(e, t) {
|
|
1604
|
+
this.fallbackStorage.set(e, t);
|
|
1555
1605
|
try {
|
|
1556
1606
|
if (this.storage) {
|
|
1557
1607
|
this.storage.setItem(e, t);
|
|
1558
1608
|
return;
|
|
1559
1609
|
}
|
|
1560
1610
|
} catch (s) {
|
|
1561
|
-
s instanceof DOMException && s.name === "QuotaExceededError"
|
|
1562
|
-
|
|
1563
|
-
|
|
1564
|
-
|
|
1611
|
+
if (s instanceof DOMException && s.name === "QuotaExceededError")
|
|
1612
|
+
if (this.hasQuotaExceededError = !0, o("warn", "localStorage quota exceeded, attempting cleanup", {
|
|
1613
|
+
data: { key: e, valueSize: t.length }
|
|
1614
|
+
}), this.cleanupOldData())
|
|
1615
|
+
try {
|
|
1616
|
+
if (this.storage) {
|
|
1617
|
+
this.storage.setItem(e, t);
|
|
1618
|
+
return;
|
|
1619
|
+
}
|
|
1620
|
+
} catch (i) {
|
|
1621
|
+
o("error", "localStorage quota exceeded even after cleanup - data will not persist", {
|
|
1622
|
+
error: i,
|
|
1623
|
+
data: { key: e, valueSize: t.length }
|
|
1624
|
+
});
|
|
1625
|
+
}
|
|
1626
|
+
else
|
|
1627
|
+
o("error", "localStorage quota exceeded and no data to cleanup - data will not persist", {
|
|
1628
|
+
error: s,
|
|
1629
|
+
data: { key: e, valueSize: t.length }
|
|
1630
|
+
});
|
|
1565
1631
|
}
|
|
1566
|
-
this.fallbackStorage.set(e, t);
|
|
1567
1632
|
}
|
|
1568
1633
|
/**
|
|
1569
1634
|
* Removes an item from storage
|
|
@@ -1591,7 +1656,7 @@ class Et {
|
|
|
1591
1656
|
}
|
|
1592
1657
|
e.forEach((t) => this.storage.removeItem(t)), this.fallbackStorage.clear();
|
|
1593
1658
|
} catch (e) {
|
|
1594
|
-
|
|
1659
|
+
o("error", "Failed to clear storage", { error: e }), this.fallbackStorage.clear();
|
|
1595
1660
|
}
|
|
1596
1661
|
}
|
|
1597
1662
|
/**
|
|
@@ -1607,6 +1672,37 @@ class Et {
|
|
|
1607
1672
|
hasQuotaError() {
|
|
1608
1673
|
return this.hasQuotaExceededError;
|
|
1609
1674
|
}
|
|
1675
|
+
/**
|
|
1676
|
+
* Attempts to cleanup old TraceLog data from storage to free up space
|
|
1677
|
+
* Returns true if any data was removed, false otherwise
|
|
1678
|
+
*/
|
|
1679
|
+
cleanupOldData() {
|
|
1680
|
+
if (!this.storage)
|
|
1681
|
+
return !1;
|
|
1682
|
+
try {
|
|
1683
|
+
const e = [], t = [];
|
|
1684
|
+
for (let i = 0; i < this.storage.length; i++) {
|
|
1685
|
+
const a = this.storage.key(i);
|
|
1686
|
+
a?.startsWith("tracelog_") && (e.push(a), a.startsWith("tracelog_persisted_events_") && t.push(a));
|
|
1687
|
+
}
|
|
1688
|
+
if (t.length > 0)
|
|
1689
|
+
return t.forEach((i) => {
|
|
1690
|
+
try {
|
|
1691
|
+
this.storage.removeItem(i);
|
|
1692
|
+
} catch {
|
|
1693
|
+
}
|
|
1694
|
+
}), !0;
|
|
1695
|
+
const s = ["tracelog_session_", "tracelog_user_id", "tracelog_device_id", "tracelog_config"], n = e.filter((i) => !s.some((a) => i.startsWith(a)));
|
|
1696
|
+
return n.length > 0 ? (n.slice(0, 5).forEach((a) => {
|
|
1697
|
+
try {
|
|
1698
|
+
this.storage.removeItem(a);
|
|
1699
|
+
} catch {
|
|
1700
|
+
}
|
|
1701
|
+
}), !0) : !1;
|
|
1702
|
+
} catch (e) {
|
|
1703
|
+
return o("error", "Failed to cleanup old data", { error: e }), !1;
|
|
1704
|
+
}
|
|
1705
|
+
}
|
|
1610
1706
|
/**
|
|
1611
1707
|
* Initialize storage (localStorage or sessionStorage) with feature detection
|
|
1612
1708
|
*/
|
|
@@ -1634,18 +1730,18 @@ class Et {
|
|
|
1634
1730
|
* Stores an item in sessionStorage
|
|
1635
1731
|
*/
|
|
1636
1732
|
setSessionItem(e, t) {
|
|
1733
|
+
this.fallbackSessionStorage.set(e, t);
|
|
1637
1734
|
try {
|
|
1638
1735
|
if (this.sessionStorageRef) {
|
|
1639
1736
|
this.sessionStorageRef.setItem(e, t);
|
|
1640
1737
|
return;
|
|
1641
1738
|
}
|
|
1642
1739
|
} catch (s) {
|
|
1643
|
-
s instanceof DOMException && s.name === "QuotaExceededError" &&
|
|
1740
|
+
s instanceof DOMException && s.name === "QuotaExceededError" && o("error", "sessionStorage quota exceeded - data will not persist", {
|
|
1644
1741
|
error: s,
|
|
1645
1742
|
data: { key: e, valueSize: t.length }
|
|
1646
1743
|
});
|
|
1647
1744
|
}
|
|
1648
|
-
this.fallbackSessionStorage.set(e, t);
|
|
1649
1745
|
}
|
|
1650
1746
|
/**
|
|
1651
1747
|
* Removes an item from sessionStorage
|
|
@@ -1658,7 +1754,7 @@ class Et {
|
|
|
1658
1754
|
this.fallbackSessionStorage.delete(e);
|
|
1659
1755
|
}
|
|
1660
1756
|
}
|
|
1661
|
-
class
|
|
1757
|
+
class mt extends f {
|
|
1662
1758
|
eventManager;
|
|
1663
1759
|
reportedByNav = /* @__PURE__ */ new Map();
|
|
1664
1760
|
observers = [];
|
|
@@ -1675,7 +1771,7 @@ class pt extends f {
|
|
|
1675
1771
|
try {
|
|
1676
1772
|
e.disconnect();
|
|
1677
1773
|
} catch (s) {
|
|
1678
|
-
|
|
1774
|
+
o("warn", "Failed to disconnect performance observer", { error: s, data: { observerIndex: t } });
|
|
1679
1775
|
}
|
|
1680
1776
|
}), this.observers.length = 0, this.reportedByNav.clear();
|
|
1681
1777
|
}
|
|
@@ -1699,8 +1795,8 @@ class pt extends f {
|
|
|
1699
1795
|
for (const a of i) {
|
|
1700
1796
|
if (a.hadRecentInput === !0)
|
|
1701
1797
|
continue;
|
|
1702
|
-
const
|
|
1703
|
-
e +=
|
|
1798
|
+
const l = typeof a.value == "number" ? a.value : 0;
|
|
1799
|
+
e += l;
|
|
1704
1800
|
}
|
|
1705
1801
|
this.sendVital({ type: "CLS", value: Number(e.toFixed(2)) });
|
|
1706
1802
|
},
|
|
@@ -1719,8 +1815,8 @@ class pt extends f {
|
|
|
1719
1815
|
let n = 0;
|
|
1720
1816
|
const i = s.getEntries();
|
|
1721
1817
|
for (const a of i) {
|
|
1722
|
-
const
|
|
1723
|
-
n = Math.max(n,
|
|
1818
|
+
const l = (a.processingEnd ?? 0) - (a.startTime ?? 0);
|
|
1819
|
+
n = Math.max(n, l);
|
|
1724
1820
|
}
|
|
1725
1821
|
n > 0 && this.sendVital({ type: "INP", value: Number(n.toFixed(2)) });
|
|
1726
1822
|
},
|
|
@@ -1729,13 +1825,13 @@ class pt extends f {
|
|
|
1729
1825
|
}
|
|
1730
1826
|
async initWebVitals() {
|
|
1731
1827
|
try {
|
|
1732
|
-
const { onLCP: e, onCLS: t, onFCP: s, onTTFB: n, onINP: i } = await Promise.resolve().then(() => Ht), a = (
|
|
1828
|
+
const { onLCP: e, onCLS: t, onFCP: s, onTTFB: n, onINP: i } = await Promise.resolve().then(() => Ht), a = (l) => (c) => {
|
|
1733
1829
|
const u = Number(c.value.toFixed(2));
|
|
1734
|
-
this.sendVital({ type:
|
|
1830
|
+
this.sendVital({ type: l, value: u });
|
|
1735
1831
|
};
|
|
1736
1832
|
e(a("LCP")), t(a("CLS")), s(a("FCP")), n(a("TTFB")), i(a("INP"));
|
|
1737
1833
|
} catch (e) {
|
|
1738
|
-
|
|
1834
|
+
o("warn", "Failed to load web-vitals library, using fallback", { error: e }), this.observeWebVitalsFallback();
|
|
1739
1835
|
}
|
|
1740
1836
|
}
|
|
1741
1837
|
reportTTFB() {
|
|
@@ -1746,7 +1842,7 @@ class pt extends f {
|
|
|
1746
1842
|
const t = e.responseStart;
|
|
1747
1843
|
typeof t == "number" && Number.isFinite(t) && this.sendVital({ type: "TTFB", value: Number(t.toFixed(2)) });
|
|
1748
1844
|
} catch (e) {
|
|
1749
|
-
|
|
1845
|
+
o("warn", "Failed to report TTFB", { error: e });
|
|
1750
1846
|
}
|
|
1751
1847
|
}
|
|
1752
1848
|
observeLongTasks() {
|
|
@@ -1756,7 +1852,7 @@ class pt extends f {
|
|
|
1756
1852
|
const t = e.getEntries();
|
|
1757
1853
|
for (const s of t) {
|
|
1758
1854
|
const n = Number(s.duration.toFixed(2)), i = Date.now();
|
|
1759
|
-
i - this.lastLongTaskSentAt >=
|
|
1855
|
+
i - this.lastLongTaskSentAt >= ze && (this.shouldSendVital("LONG_TASK", n) && this.trackWebVital("LONG_TASK", n), this.lastLongTaskSentAt = i);
|
|
1760
1856
|
}
|
|
1761
1857
|
},
|
|
1762
1858
|
{ type: "longtask", buffered: !0 }
|
|
@@ -1776,7 +1872,7 @@ class pt extends f {
|
|
|
1776
1872
|
}
|
|
1777
1873
|
trackWebVital(e, t) {
|
|
1778
1874
|
if (!Number.isFinite(t)) {
|
|
1779
|
-
|
|
1875
|
+
o("warn", "Invalid web vital value", { data: { type: e, value: t } });
|
|
1780
1876
|
return;
|
|
1781
1877
|
}
|
|
1782
1878
|
this.eventManager.track({
|
|
@@ -1795,7 +1891,7 @@ class pt extends f {
|
|
|
1795
1891
|
const t = e.startTime || performance.now(), s = Math.random().toString(36).substr(2, 5);
|
|
1796
1892
|
return `${t.toFixed(2)}_${window.location.pathname}_${s}`;
|
|
1797
1893
|
} catch (e) {
|
|
1798
|
-
return
|
|
1894
|
+
return o("warn", "Failed to get navigation ID", { error: e }), null;
|
|
1799
1895
|
}
|
|
1800
1896
|
}
|
|
1801
1897
|
isObserverSupported(e) {
|
|
@@ -1807,24 +1903,24 @@ class pt extends f {
|
|
|
1807
1903
|
try {
|
|
1808
1904
|
if (!this.isObserverSupported(e))
|
|
1809
1905
|
return !1;
|
|
1810
|
-
const i = new PerformanceObserver((a,
|
|
1906
|
+
const i = new PerformanceObserver((a, l) => {
|
|
1811
1907
|
try {
|
|
1812
|
-
t(a,
|
|
1908
|
+
t(a, l);
|
|
1813
1909
|
} catch (c) {
|
|
1814
|
-
|
|
1910
|
+
o("warn", "Observer callback failed", {
|
|
1815
1911
|
error: c,
|
|
1816
1912
|
data: { type: e }
|
|
1817
1913
|
});
|
|
1818
1914
|
}
|
|
1819
1915
|
if (n)
|
|
1820
1916
|
try {
|
|
1821
|
-
|
|
1917
|
+
l.disconnect();
|
|
1822
1918
|
} catch {
|
|
1823
1919
|
}
|
|
1824
1920
|
});
|
|
1825
1921
|
return i.observe(s ?? { type: e, buffered: !0 }), n || this.observers.push(i), !0;
|
|
1826
1922
|
} catch (i) {
|
|
1827
|
-
return
|
|
1923
|
+
return o("warn", "Failed to create performance observer", {
|
|
1828
1924
|
error: i,
|
|
1829
1925
|
data: { type: e }
|
|
1830
1926
|
}), !1;
|
|
@@ -1832,12 +1928,12 @@ class pt extends f {
|
|
|
1832
1928
|
}
|
|
1833
1929
|
shouldSendVital(e, t) {
|
|
1834
1930
|
if (typeof t != "number" || !Number.isFinite(t))
|
|
1835
|
-
return
|
|
1931
|
+
return o("warn", "Invalid web vital value", { data: { type: e, value: t } }), !1;
|
|
1836
1932
|
const s = this.vitalThresholds[e];
|
|
1837
1933
|
return !(typeof s == "number" && t <= s);
|
|
1838
1934
|
}
|
|
1839
1935
|
}
|
|
1840
|
-
class
|
|
1936
|
+
class pt extends f {
|
|
1841
1937
|
eventManager;
|
|
1842
1938
|
recentErrors = /* @__PURE__ */ new Map();
|
|
1843
1939
|
constructor(e) {
|
|
@@ -1857,10 +1953,10 @@ class mt extends f {
|
|
|
1857
1953
|
if (!this.shouldSample())
|
|
1858
1954
|
return;
|
|
1859
1955
|
const t = this.sanitize(e.message || "Unknown error");
|
|
1860
|
-
this.shouldSuppressError(
|
|
1956
|
+
this.shouldSuppressError(L.JS_ERROR, t) || this.eventManager.track({
|
|
1861
1957
|
type: d.ERROR,
|
|
1862
1958
|
error_data: {
|
|
1863
|
-
type:
|
|
1959
|
+
type: L.JS_ERROR,
|
|
1864
1960
|
message: t,
|
|
1865
1961
|
...e.filename && { filename: e.filename },
|
|
1866
1962
|
...e.lineno && { line: e.lineno },
|
|
@@ -1872,10 +1968,10 @@ class mt extends f {
|
|
|
1872
1968
|
if (!this.shouldSample())
|
|
1873
1969
|
return;
|
|
1874
1970
|
const t = this.extractRejectionMessage(e.reason), s = this.sanitize(t);
|
|
1875
|
-
this.shouldSuppressError(
|
|
1971
|
+
this.shouldSuppressError(L.PROMISE_REJECTION, s) || this.eventManager.track({
|
|
1876
1972
|
type: d.ERROR,
|
|
1877
1973
|
error_data: {
|
|
1878
|
-
type:
|
|
1974
|
+
type: L.PROMISE_REJECTION,
|
|
1879
1975
|
message: s
|
|
1880
1976
|
}
|
|
1881
1977
|
});
|
|
@@ -1928,12 +2024,12 @@ class _t extends f {
|
|
|
1928
2024
|
get initialized() {
|
|
1929
2025
|
return this.isInitialized;
|
|
1930
2026
|
}
|
|
1931
|
-
async init(e) {
|
|
2027
|
+
async init(e = {}) {
|
|
1932
2028
|
if (!this.isInitialized) {
|
|
1933
2029
|
this.managers.storage = new Et();
|
|
1934
2030
|
try {
|
|
1935
2031
|
this.setupState(e), await this.setupIntegrations(), this.managers.event = new lt(this.managers.storage, this.integrations.googleAnalytics, this.emitter), await this.initializeHandlers(), await this.managers.event.recoverPersistedEvents().catch((t) => {
|
|
1936
|
-
|
|
2032
|
+
o("warn", "Failed to recover persisted events", { error: t });
|
|
1937
2033
|
}), this.isInitialized = !0;
|
|
1938
2034
|
} catch (t) {
|
|
1939
2035
|
await this.destroy(!0);
|
|
@@ -1973,22 +2069,22 @@ class _t extends f {
|
|
|
1973
2069
|
try {
|
|
1974
2070
|
await s.stopTracking();
|
|
1975
2071
|
} catch (n) {
|
|
1976
|
-
|
|
2072
|
+
o("warn", "Failed to stop tracking", { error: n });
|
|
1977
2073
|
}
|
|
1978
2074
|
});
|
|
1979
2075
|
await Promise.allSettled(t), this.suppressNextScrollTimer && (clearTimeout(this.suppressNextScrollTimer), this.suppressNextScrollTimer = null), this.managers.event?.flushImmediatelySync(), this.managers.event?.stop(), this.emitter.removeAllListeners(), this.set("hasStartSession", !1), this.set("suppressNextScroll", !1), this.set("sessionId", null), this.isInitialized = !1, this.handlers = {};
|
|
1980
2076
|
}
|
|
1981
|
-
setupState(e) {
|
|
2077
|
+
setupState(e = {}) {
|
|
1982
2078
|
this.set("config", e);
|
|
1983
2079
|
const t = ct.getId(this.managers.storage);
|
|
1984
2080
|
this.set("userId", t);
|
|
1985
|
-
const s =
|
|
1986
|
-
this.set("
|
|
2081
|
+
const s = We(e);
|
|
2082
|
+
this.set("collectApiUrl", s);
|
|
1987
2083
|
const n = He();
|
|
1988
2084
|
this.set("device", n);
|
|
1989
|
-
const i =
|
|
2085
|
+
const i = Y(window.location.href, e.sensitiveQueryParams);
|
|
1990
2086
|
this.set("pageUrl", i);
|
|
1991
|
-
const a =
|
|
2087
|
+
const a = Be() ? R.QA : void 0;
|
|
1992
2088
|
a && this.set("mode", a);
|
|
1993
2089
|
}
|
|
1994
2090
|
async setupIntegrations() {
|
|
@@ -2009,36 +2105,42 @@ class _t extends f {
|
|
|
2009
2105
|
this.set("suppressNextScroll", !1);
|
|
2010
2106
|
}, 250 * 2);
|
|
2011
2107
|
};
|
|
2012
|
-
this.handlers.pageView = new ht(this.managers.event, e), this.handlers.pageView.startTracking(), this.handlers.click = new ft(this.managers.event), this.handlers.click.startTracking(), this.handlers.scroll = new gt(this.managers.event), this.handlers.scroll.startTracking(), this.handlers.performance = new
|
|
2013
|
-
|
|
2014
|
-
}), this.handlers.error = new
|
|
2108
|
+
this.handlers.pageView = new ht(this.managers.event, e), this.handlers.pageView.startTracking(), this.handlers.click = new ft(this.managers.event), this.handlers.click.startTracking(), this.handlers.scroll = new gt(this.managers.event), this.handlers.scroll.startTracking(), this.handlers.performance = new mt(this.managers.event), this.handlers.performance.startTracking().catch((t) => {
|
|
2109
|
+
o("warn", "Failed to start performance tracking", { error: t });
|
|
2110
|
+
}), this.handlers.error = new pt(this.managers.event), this.handlers.error.startTracking();
|
|
2015
2111
|
}
|
|
2016
2112
|
}
|
|
2017
2113
|
const I = [];
|
|
2018
|
-
let h = null,
|
|
2114
|
+
let h = null, w = !1, U = !1;
|
|
2019
2115
|
const Tt = async (r) => {
|
|
2020
2116
|
if (typeof window > "u" || typeof document > "u")
|
|
2021
2117
|
throw new Error("[TraceLog] This library can only be used in a browser environment");
|
|
2022
|
-
if (!window.__traceLogDisabled && !h && !
|
|
2023
|
-
|
|
2118
|
+
if (!window.__traceLogDisabled && !h && !w) {
|
|
2119
|
+
w = !0;
|
|
2024
2120
|
try {
|
|
2025
|
-
const e = et(r), t = new _t();
|
|
2121
|
+
const e = et(r ?? {}), t = new _t();
|
|
2026
2122
|
try {
|
|
2027
|
-
I.forEach(({ event:
|
|
2028
|
-
t.on(
|
|
2029
|
-
}), I.length = 0
|
|
2123
|
+
I.forEach(({ event: i, callback: a }) => {
|
|
2124
|
+
t.on(i, a);
|
|
2125
|
+
}), I.length = 0;
|
|
2126
|
+
const s = t.init(e), n = new Promise((i, a) => {
|
|
2127
|
+
setTimeout(() => {
|
|
2128
|
+
a(new Error("[TraceLog] Initialization timeout after 10000ms"));
|
|
2129
|
+
}, 1e4);
|
|
2130
|
+
});
|
|
2131
|
+
await Promise.race([s, n]), h = t;
|
|
2030
2132
|
} catch (s) {
|
|
2031
2133
|
try {
|
|
2032
2134
|
await t.destroy(!0);
|
|
2033
2135
|
} catch (n) {
|
|
2034
|
-
|
|
2136
|
+
o("error", "Failed to cleanup partially initialized app", { error: n });
|
|
2035
2137
|
}
|
|
2036
2138
|
throw s;
|
|
2037
2139
|
}
|
|
2038
2140
|
} catch (e) {
|
|
2039
2141
|
throw h = null, e;
|
|
2040
2142
|
} finally {
|
|
2041
|
-
|
|
2143
|
+
w = !1;
|
|
2042
2144
|
}
|
|
2043
2145
|
}
|
|
2044
2146
|
}, vt = (r, e) => {
|
|
@@ -2048,7 +2150,7 @@ const Tt = async (r) => {
|
|
|
2048
2150
|
throw new Error("[TraceLog] Cannot send events while TraceLog is being destroyed");
|
|
2049
2151
|
h.sendCustomEvent(r, e);
|
|
2050
2152
|
}, It = (r, e) => {
|
|
2051
|
-
if (!h ||
|
|
2153
|
+
if (!h || w) {
|
|
2052
2154
|
I.push({ event: r, callback: e });
|
|
2053
2155
|
return;
|
|
2054
2156
|
}
|
|
@@ -2067,9 +2169,9 @@ const Tt = async (r) => {
|
|
|
2067
2169
|
throw new Error("[TraceLog] Destroy operation already in progress");
|
|
2068
2170
|
U = !0;
|
|
2069
2171
|
try {
|
|
2070
|
-
await h.destroy(), h = null,
|
|
2172
|
+
await h.destroy(), h = null, w = !1, I.length = 0;
|
|
2071
2173
|
} catch (r) {
|
|
2072
|
-
|
|
2174
|
+
h = null, w = !1, I.length = 0, o("warn", "Error during destroy, forced cleanup completed", { error: r });
|
|
2073
2175
|
} finally {
|
|
2074
2176
|
U = !1;
|
|
2075
2177
|
}
|
|
@@ -2089,7 +2191,7 @@ const Tt = async (r) => {
|
|
|
2089
2191
|
MIN_ENGAGED_SESSION_DURATION_MS: 30 * 1e3,
|
|
2090
2192
|
MIN_SCROLL_DEPTH_ENGAGEMENT: 25
|
|
2091
2193
|
// 25% scroll depth for engagement
|
|
2092
|
-
},
|
|
2194
|
+
}, zt = {
|
|
2093
2195
|
INACTIVITY_TIMEOUT_MS: 30 * 60 * 1e3,
|
|
2094
2196
|
// 30min for analytics (vs 15min client)
|
|
2095
2197
|
SHORT_SESSION_THRESHOLD_MS: 30 * 1e3,
|
|
@@ -2103,14 +2205,14 @@ const Tt = async (r) => {
|
|
|
2103
2205
|
MOBILE_PERFORMANCE_FACTOR: 1.5,
|
|
2104
2206
|
// Mobile typically 1.5x slower
|
|
2105
2207
|
TABLET_PERFORMANCE_FACTOR: 1.2
|
|
2106
|
-
},
|
|
2208
|
+
}, Qt = {
|
|
2107
2209
|
MIN_TEXT_LENGTH_FOR_ANALYSIS: 10,
|
|
2108
2210
|
MIN_CLICKS_FOR_HOT_ELEMENT: 10,
|
|
2109
2211
|
// Popular element threshold
|
|
2110
2212
|
MIN_SCROLL_COMPLETION_PERCENT: 80,
|
|
2111
2213
|
// Page consumption threshold
|
|
2112
2214
|
MIN_TIME_ON_PAGE_FOR_READ_MS: 15 * 1e3
|
|
2113
|
-
},
|
|
2215
|
+
}, Bt = {
|
|
2114
2216
|
SIGNIFICANT_CHANGE_PERCENT: 20,
|
|
2115
2217
|
MAJOR_CHANGE_PERCENT: 50,
|
|
2116
2218
|
MIN_EVENTS_FOR_INSIGHT: 100,
|
|
@@ -2120,7 +2222,7 @@ const Tt = async (r) => {
|
|
|
2120
2222
|
LOW_ERROR_RATE_PERCENT: 1,
|
|
2121
2223
|
HIGH_ERROR_RATE_PERCENT: 5,
|
|
2122
2224
|
CRITICAL_ERROR_RATE_PERCENT: 10
|
|
2123
|
-
},
|
|
2225
|
+
}, jt = {
|
|
2124
2226
|
SHORT_TERM_TREND_HOURS: 24,
|
|
2125
2227
|
MEDIUM_TERM_TREND_DAYS: 7,
|
|
2126
2228
|
LONG_TERM_TREND_DAYS: 30,
|
|
@@ -2132,7 +2234,7 @@ const Tt = async (r) => {
|
|
|
2132
2234
|
MIN_COHORT_SIZE: 5,
|
|
2133
2235
|
COHORT_ANALYSIS_DAYS: [1, 3, 7, 14, 30],
|
|
2134
2236
|
MIN_FUNNEL_EVENTS: 20
|
|
2135
|
-
},
|
|
2237
|
+
}, Wt = {
|
|
2136
2238
|
DEFAULT_EVENTS_LIMIT: 5,
|
|
2137
2239
|
DEFAULT_SESSIONS_LIMIT: 5,
|
|
2138
2240
|
DEFAULT_PAGES_LIMIT: 5,
|
|
@@ -2140,7 +2242,7 @@ const Tt = async (r) => {
|
|
|
2140
2242
|
MAX_TIME_RANGE_DAYS: 365,
|
|
2141
2243
|
ANALYTICS_BATCH_SIZE: 1e3
|
|
2142
2244
|
// For historical analysis
|
|
2143
|
-
},
|
|
2245
|
+
}, Yt = {
|
|
2144
2246
|
ANOMALY_THRESHOLD_SIGMA: 2.5,
|
|
2145
2247
|
STRONG_ANOMALY_THRESHOLD_SIGMA: 3,
|
|
2146
2248
|
TRAFFIC_DROP_ALERT_PERCENT: -30,
|
|
@@ -2158,7 +2260,7 @@ const Tt = async (r) => {
|
|
|
2158
2260
|
isInitialized: At,
|
|
2159
2261
|
destroy: wt
|
|
2160
2262
|
};
|
|
2161
|
-
var q, ve = -1,
|
|
2263
|
+
var q, ve = -1, M = function(r) {
|
|
2162
2264
|
addEventListener("pageshow", function(e) {
|
|
2163
2265
|
e.persisted && (ve = e.timeStamp, r(e));
|
|
2164
2266
|
}, !0);
|
|
@@ -2168,10 +2270,10 @@ var q, ve = -1, w = function(r) {
|
|
|
2168
2270
|
}, V = function() {
|
|
2169
2271
|
var r = se();
|
|
2170
2272
|
return r && r.activationStart || 0;
|
|
2171
|
-
},
|
|
2273
|
+
}, S = function(r, e) {
|
|
2172
2274
|
var t = se(), s = "navigate";
|
|
2173
2275
|
return ve >= 0 ? s = "back-forward-cache" : t && (document.prerendering || V() > 0 ? s = "prerender" : document.wasDiscarded ? s = "restore" : t.type && (s = t.type.replace(/_/g, "-"))), { name: r, value: e === void 0 ? -1 : e, rating: "good", delta: 0, entries: [], id: "v4-".concat(Date.now(), "-").concat(Math.floor(8999999999999 * Math.random()) + 1e12), navigationType: s };
|
|
2174
|
-
},
|
|
2276
|
+
}, b = function(r, e, t) {
|
|
2175
2277
|
try {
|
|
2176
2278
|
if (PerformanceObserver.supportedEntryTypes.includes(r)) {
|
|
2177
2279
|
var s = new PerformanceObserver(function(n) {
|
|
@@ -2183,11 +2285,11 @@ var q, ve = -1, w = function(r) {
|
|
|
2183
2285
|
}
|
|
2184
2286
|
} catch {
|
|
2185
2287
|
}
|
|
2186
|
-
},
|
|
2288
|
+
}, E = function(r, e, t, s) {
|
|
2187
2289
|
var n, i;
|
|
2188
2290
|
return function(a) {
|
|
2189
|
-
e.value >= 0 && (a || s) && ((i = e.value - (n || 0)) || n === void 0) && (n = e.value, e.delta = i, e.rating = function(
|
|
2190
|
-
return
|
|
2291
|
+
e.value >= 0 && (a || s) && ((i = e.value - (n || 0)) || n === void 0) && (n = e.value, e.delta = i, e.rating = function(l, c) {
|
|
2292
|
+
return l > c[1] ? "poor" : l > c[0] ? "needs-improvement" : "good";
|
|
2191
2293
|
}(e.value, t), r(e));
|
|
2192
2294
|
};
|
|
2193
2295
|
}, ne = function(r) {
|
|
@@ -2205,82 +2307,82 @@ var q, ve = -1, w = function(r) {
|
|
|
2205
2307
|
return function() {
|
|
2206
2308
|
e || (r(), e = !0);
|
|
2207
2309
|
};
|
|
2208
|
-
},
|
|
2310
|
+
}, A = -1, Ee = function() {
|
|
2209
2311
|
return document.visibilityState !== "hidden" || document.prerendering ? 1 / 0 : 0;
|
|
2210
2312
|
}, x = function(r) {
|
|
2211
|
-
document.visibilityState === "hidden" &&
|
|
2212
|
-
},
|
|
2313
|
+
document.visibilityState === "hidden" && A > -1 && (A = r.type === "visibilitychange" ? r.timeStamp : 0, Mt());
|
|
2314
|
+
}, me = function() {
|
|
2213
2315
|
addEventListener("visibilitychange", x, !0), addEventListener("prerenderingchange", x, !0);
|
|
2214
2316
|
}, Mt = function() {
|
|
2215
2317
|
removeEventListener("visibilitychange", x, !0), removeEventListener("prerenderingchange", x, !0);
|
|
2216
2318
|
}, Ie = function() {
|
|
2217
|
-
return
|
|
2319
|
+
return A < 0 && (A = Ee(), me(), M(function() {
|
|
2218
2320
|
setTimeout(function() {
|
|
2219
|
-
|
|
2321
|
+
A = Ee(), me();
|
|
2220
2322
|
}, 0);
|
|
2221
2323
|
})), { get firstHiddenTime() {
|
|
2222
|
-
return
|
|
2324
|
+
return A;
|
|
2223
2325
|
} };
|
|
2224
2326
|
}, G = function(r) {
|
|
2225
2327
|
document.prerendering ? addEventListener("prerenderingchange", function() {
|
|
2226
2328
|
return r();
|
|
2227
2329
|
}, !0) : r();
|
|
2228
|
-
},
|
|
2330
|
+
}, Z = [1800, 3e3], ye = function(r, e) {
|
|
2229
2331
|
e = e || {}, G(function() {
|
|
2230
|
-
var t, s = Ie(), n =
|
|
2231
|
-
a.forEach(function(
|
|
2232
|
-
|
|
2332
|
+
var t, s = Ie(), n = S("FCP"), i = b("paint", function(a) {
|
|
2333
|
+
a.forEach(function(l) {
|
|
2334
|
+
l.name === "first-contentful-paint" && (i.disconnect(), l.startTime < s.firstHiddenTime && (n.value = Math.max(l.startTime - V(), 0), n.entries.push(l), t(!0)));
|
|
2233
2335
|
});
|
|
2234
2336
|
});
|
|
2235
|
-
i && (t =
|
|
2236
|
-
n =
|
|
2337
|
+
i && (t = E(r, n, Z, e.reportAllChanges), M(function(a) {
|
|
2338
|
+
n = S("FCP"), t = E(r, n, Z, e.reportAllChanges), ne(function() {
|
|
2237
2339
|
n.value = performance.now() - a.timeStamp, t(!0);
|
|
2238
2340
|
});
|
|
2239
2341
|
}));
|
|
2240
2342
|
});
|
|
2241
|
-
},
|
|
2343
|
+
}, J = [0.1, 0.25], Nt = function(r, e) {
|
|
2242
2344
|
e = e || {}, ye(ie(function() {
|
|
2243
|
-
var t, s =
|
|
2345
|
+
var t, s = S("CLS", 0), n = 0, i = [], a = function(c) {
|
|
2244
2346
|
c.forEach(function(u) {
|
|
2245
2347
|
if (!u.hadRecentInput) {
|
|
2246
|
-
var
|
|
2247
|
-
n && u.startTime -
|
|
2348
|
+
var p = i[0], N = i[i.length - 1];
|
|
2349
|
+
n && u.startTime - N.startTime < 1e3 && u.startTime - p.startTime < 5e3 ? (n += u.value, i.push(u)) : (n = u.value, i = [u]);
|
|
2248
2350
|
}
|
|
2249
2351
|
}), n > s.value && (s.value = n, s.entries = i, t());
|
|
2250
|
-
},
|
|
2251
|
-
|
|
2252
|
-
a(
|
|
2253
|
-
}),
|
|
2254
|
-
n = 0, s =
|
|
2352
|
+
}, l = b("layout-shift", a);
|
|
2353
|
+
l && (t = E(r, s, J, e.reportAllChanges), F(function() {
|
|
2354
|
+
a(l.takeRecords()), t(!0);
|
|
2355
|
+
}), M(function() {
|
|
2356
|
+
n = 0, s = S("CLS", 0), t = E(r, s, J, e.reportAllChanges), ne(function() {
|
|
2255
2357
|
return t();
|
|
2256
2358
|
});
|
|
2257
2359
|
}), setTimeout(t, 0));
|
|
2258
2360
|
}));
|
|
2259
|
-
}, Ae = 0,
|
|
2361
|
+
}, Ae = 0, Q = 1 / 0, P = 0, Lt = function(r) {
|
|
2260
2362
|
r.forEach(function(e) {
|
|
2261
|
-
e.interactionId && (
|
|
2363
|
+
e.interactionId && (Q = Math.min(Q, e.interactionId), P = Math.max(P, e.interactionId), Ae = P ? (P - Q) / 7 + 1 : 0);
|
|
2262
2364
|
});
|
|
2263
2365
|
}, we = function() {
|
|
2264
2366
|
return q ? Ae : performance.interactionCount || 0;
|
|
2265
|
-
},
|
|
2266
|
-
"interactionCount" in performance || q || (q =
|
|
2267
|
-
},
|
|
2268
|
-
var r = Math.min(
|
|
2269
|
-
return
|
|
2367
|
+
}, Rt = function() {
|
|
2368
|
+
"interactionCount" in performance || q || (q = b("event", Lt, { type: "event", buffered: !0, durationThreshold: 0 }));
|
|
2369
|
+
}, g = [], H = /* @__PURE__ */ new Map(), Me = 0, Ct = function() {
|
|
2370
|
+
var r = Math.min(g.length - 1, Math.floor((we() - Me) / 50));
|
|
2371
|
+
return g[r];
|
|
2270
2372
|
}, bt = [], Ot = function(r) {
|
|
2271
2373
|
if (bt.forEach(function(n) {
|
|
2272
2374
|
return n(r);
|
|
2273
2375
|
}), r.interactionId || r.entryType === "first-input") {
|
|
2274
|
-
var e =
|
|
2275
|
-
if (t ||
|
|
2376
|
+
var e = g[g.length - 1], t = H.get(r.interactionId);
|
|
2377
|
+
if (t || g.length < 10 || r.duration > e.latency) {
|
|
2276
2378
|
if (t) r.duration > t.latency ? (t.entries = [r], t.latency = r.duration) : r.duration === t.latency && r.startTime === t.entries[0].startTime && t.entries.push(r);
|
|
2277
2379
|
else {
|
|
2278
2380
|
var s = { id: r.interactionId, latency: r.duration, entries: [r] };
|
|
2279
|
-
H.set(s.id, s),
|
|
2381
|
+
H.set(s.id, s), g.push(s);
|
|
2280
2382
|
}
|
|
2281
|
-
|
|
2383
|
+
g.sort(function(n, i) {
|
|
2282
2384
|
return i.latency - n.latency;
|
|
2283
|
-
}),
|
|
2385
|
+
}), g.length > 10 && g.splice(10).forEach(function(n) {
|
|
2284
2386
|
return H.delete(n.id);
|
|
2285
2387
|
});
|
|
2286
2388
|
}
|
|
@@ -2291,39 +2393,39 @@ var q, ve = -1, w = function(r) {
|
|
|
2291
2393
|
}, ee = [200, 500], Pt = function(r, e) {
|
|
2292
2394
|
"PerformanceEventTiming" in self && "interactionId" in PerformanceEventTiming.prototype && (e = e || {}, G(function() {
|
|
2293
2395
|
var t;
|
|
2294
|
-
|
|
2295
|
-
var s, n =
|
|
2396
|
+
Rt();
|
|
2397
|
+
var s, n = S("INP"), i = function(l) {
|
|
2296
2398
|
Ne(function() {
|
|
2297
|
-
|
|
2399
|
+
l.forEach(Ot);
|
|
2298
2400
|
var c = Ct();
|
|
2299
2401
|
c && c.latency !== n.value && (n.value = c.latency, n.entries = c.entries, s());
|
|
2300
2402
|
});
|
|
2301
|
-
}, a =
|
|
2302
|
-
s =
|
|
2403
|
+
}, a = b("event", i, { durationThreshold: (t = e.durationThreshold) !== null && t !== void 0 ? t : 40 });
|
|
2404
|
+
s = E(r, n, ee, e.reportAllChanges), a && (a.observe({ type: "first-input", buffered: !0 }), F(function() {
|
|
2303
2405
|
i(a.takeRecords()), s(!0);
|
|
2304
|
-
}),
|
|
2305
|
-
Me = we(),
|
|
2406
|
+
}), M(function() {
|
|
2407
|
+
Me = we(), g.length = 0, H.clear(), n = S("INP"), s = E(r, n, ee, e.reportAllChanges);
|
|
2306
2408
|
}));
|
|
2307
2409
|
}));
|
|
2308
|
-
}, te = [2500, 4e3],
|
|
2410
|
+
}, te = [2500, 4e3], B = {}, Dt = function(r, e) {
|
|
2309
2411
|
e = e || {}, G(function() {
|
|
2310
|
-
var t, s = Ie(), n =
|
|
2412
|
+
var t, s = Ie(), n = S("LCP"), i = function(c) {
|
|
2311
2413
|
e.reportAllChanges || (c = c.slice(-1)), c.forEach(function(u) {
|
|
2312
2414
|
u.startTime < s.firstHiddenTime && (n.value = Math.max(u.startTime - V(), 0), n.entries = [u], t());
|
|
2313
2415
|
});
|
|
2314
|
-
}, a =
|
|
2416
|
+
}, a = b("largest-contentful-paint", i);
|
|
2315
2417
|
if (a) {
|
|
2316
|
-
t =
|
|
2317
|
-
var
|
|
2318
|
-
|
|
2418
|
+
t = E(r, n, te, e.reportAllChanges);
|
|
2419
|
+
var l = ie(function() {
|
|
2420
|
+
B[n.id] || (i(a.takeRecords()), a.disconnect(), B[n.id] = !0, t(!0));
|
|
2319
2421
|
});
|
|
2320
2422
|
["keydown", "click"].forEach(function(c) {
|
|
2321
2423
|
addEventListener(c, function() {
|
|
2322
|
-
return Ne(
|
|
2424
|
+
return Ne(l);
|
|
2323
2425
|
}, { once: !0, capture: !0 });
|
|
2324
|
-
}), F(
|
|
2325
|
-
n =
|
|
2326
|
-
n.value = performance.now() - c.timeStamp,
|
|
2426
|
+
}), F(l), M(function(c) {
|
|
2427
|
+
n = S("LCP"), t = E(r, n, te, e.reportAllChanges), ne(function() {
|
|
2428
|
+
n.value = performance.now() - c.timeStamp, B[n.id] = !0, t(!0);
|
|
2327
2429
|
});
|
|
2328
2430
|
});
|
|
2329
2431
|
}
|
|
@@ -2336,18 +2438,18 @@ var q, ve = -1, w = function(r) {
|
|
|
2336
2438
|
}, !0) : setTimeout(e, 0);
|
|
2337
2439
|
}, Ut = function(r, e) {
|
|
2338
2440
|
e = e || {};
|
|
2339
|
-
var t =
|
|
2441
|
+
var t = S("TTFB"), s = E(r, t, re, e.reportAllChanges);
|
|
2340
2442
|
kt(function() {
|
|
2341
2443
|
var n = se();
|
|
2342
|
-
n && (t.value = Math.max(n.responseStart - V(), 0), t.entries = [n], s(!0),
|
|
2343
|
-
t =
|
|
2444
|
+
n && (t.value = Math.max(n.responseStart - V(), 0), t.entries = [n], s(!0), M(function() {
|
|
2445
|
+
t = S("TTFB", 0), (s = E(r, t, re, e.reportAllChanges))(!0);
|
|
2344
2446
|
}));
|
|
2345
2447
|
});
|
|
2346
2448
|
};
|
|
2347
2449
|
const Ht = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
2348
2450
|
__proto__: null,
|
|
2349
|
-
CLSThresholds:
|
|
2350
|
-
FCPThresholds:
|
|
2451
|
+
CLSThresholds: J,
|
|
2452
|
+
FCPThresholds: Z,
|
|
2351
2453
|
INPThresholds: ee,
|
|
2352
2454
|
LCPThresholds: te,
|
|
2353
2455
|
TTFBThresholds: re,
|
|
@@ -2358,30 +2460,30 @@ const Ht = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
|
|
|
2358
2460
|
onTTFB: Ut
|
|
2359
2461
|
}, Symbol.toStringTag, { value: "Module" }));
|
|
2360
2462
|
export {
|
|
2361
|
-
|
|
2362
|
-
|
|
2363
|
-
|
|
2364
|
-
|
|
2463
|
+
Wt as ANALYTICS_QUERY_LIMITS,
|
|
2464
|
+
Yt as ANOMALY_DETECTION,
|
|
2465
|
+
y as AppConfigValidationError,
|
|
2466
|
+
Qt as CONTENT_ANALYTICS,
|
|
2365
2467
|
Ft as DATA_PROTECTION,
|
|
2366
2468
|
$t as DEVICE_ANALYTICS,
|
|
2367
2469
|
_ as DeviceType,
|
|
2368
2470
|
Gt as ENGAGEMENT_THRESHOLDS,
|
|
2369
2471
|
X as EmitterEvent,
|
|
2370
|
-
|
|
2472
|
+
L as ErrorType,
|
|
2371
2473
|
d as EventType,
|
|
2372
|
-
|
|
2474
|
+
Bt as INSIGHT_THRESHOLDS,
|
|
2373
2475
|
xt as InitializationTimeoutError,
|
|
2374
|
-
|
|
2476
|
+
v as IntegrationValidationError,
|
|
2375
2477
|
R as Mode,
|
|
2376
2478
|
Vt as PERFORMANCE_CONFIG,
|
|
2377
2479
|
Xt as SEGMENTATION_ANALYTICS,
|
|
2378
|
-
|
|
2480
|
+
zt as SESSION_ANALYTICS,
|
|
2379
2481
|
Kt as SPECIAL_PAGE_URLS,
|
|
2380
2482
|
oe as SamplingRateValidationError,
|
|
2381
2483
|
D as ScrollDirection,
|
|
2382
|
-
|
|
2383
|
-
|
|
2384
|
-
|
|
2385
|
-
|
|
2484
|
+
Pe as SessionTimeoutValidationError,
|
|
2485
|
+
j as SpecialApiUrl,
|
|
2486
|
+
jt as TEMPORAL_ANALYSIS,
|
|
2487
|
+
C as TraceLogValidationError,
|
|
2386
2488
|
qt as tracelog
|
|
2387
2489
|
};
|