@sailfish-ai/recorder 1.11.0 → 1.11.1
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/dist/chunks/{chunkSerializer-ZzIoYlP2.js → chunkSerializer-BiemuRlf.js} +1 -1
- package/dist/chunks/chunkSerializer-BiemuRlf.js.br +0 -0
- package/dist/chunks/chunkSerializer-BiemuRlf.js.gz +0 -0
- package/dist/chunks/{chunkSerializer-CRDpgzTs.js → chunkSerializer-CJQCxiLD.js} +1 -1
- package/dist/chunks/chunkSerializer-CJQCxiLD.js.br +0 -0
- package/dist/chunks/chunkSerializer-CJQCxiLD.js.gz +0 -0
- package/dist/chunks/{index-BQn1Q-2-.js → index-Cfj4Epfd.js} +120 -94
- package/dist/chunks/index-Cfj4Epfd.js.br +0 -0
- package/dist/chunks/index-Cfj4Epfd.js.gz +0 -0
- package/dist/chunks/{index-Dq_tjmkZ.js → index-CuXHImrI.js} +114 -86
- package/dist/chunks/index-CuXHImrI.js.br +0 -0
- package/dist/chunks/index-CuXHImrI.js.gz +0 -0
- package/dist/inAppReportIssueModal/index.js +15 -14
- package/dist/inAppReportIssueModal/index.js.br +0 -0
- package/dist/inAppReportIssueModal/index.js.gz +0 -0
- package/dist/inAppReportIssueModal/integrations.js +56 -4
- package/dist/inAppReportIssueModal/integrations.js.br +0 -0
- package/dist/inAppReportIssueModal/integrations.js.gz +0 -0
- package/dist/index.js +55 -40
- package/dist/index.js.br +0 -0
- package/dist/index.js.gz +0 -0
- package/dist/recorder.cjs +2 -2
- package/dist/recorder.cjs.br +0 -0
- package/dist/recorder.cjs.gz +0 -0
- package/dist/recorder.js +26 -25
- package/dist/recorder.js.br +0 -0
- package/dist/recorder.js.gz +0 -0
- package/dist/recorder.umd.cjs +287 -261
- package/dist/recorder.umd.cjs.br +0 -0
- package/dist/recorder.umd.cjs.gz +0 -0
- package/dist/recording.js +2 -2
- package/dist/recording.js.br +0 -0
- package/dist/recording.js.gz +0 -0
- package/dist/sendSailfishMessages.js +4 -0
- package/dist/sendSailfishMessages.js.br +0 -0
- package/dist/sendSailfishMessages.js.gz +0 -0
- package/dist/snippet-auto-init.js +147 -18
- package/dist/snippet-auto-init.js.br +0 -0
- package/dist/snippet-auto-init.js.gz +0 -0
- package/dist/types/inAppReportIssueModal/integrations.d.ts +7 -0
- package/dist/types/index.d.ts +3 -1
- package/dist/types/sendSailfishMessages.d.ts +4 -0
- package/dist/types/snippet-auto-init.d.ts +30 -0
- package/dist/types/types.d.ts +1 -0
- package/package.json +1 -1
- package/dist/chunks/chunkSerializer-CRDpgzTs.js.br +0 -0
- package/dist/chunks/chunkSerializer-CRDpgzTs.js.gz +0 -0
- package/dist/chunks/chunkSerializer-ZzIoYlP2.js.br +0 -0
- package/dist/chunks/chunkSerializer-ZzIoYlP2.js.gz +0 -0
- package/dist/chunks/index-BQn1Q-2-.js.br +0 -0
- package/dist/chunks/index-BQn1Q-2-.js.gz +0 -0
- package/dist/chunks/index-Dq_tjmkZ.js.br +0 -0
- package/dist/chunks/index-Dq_tjmkZ.js.gz +0 -0
package/dist/index.js
CHANGED
|
@@ -293,40 +293,11 @@ function storeCredentialsAndConnection({ apiKey, backendApi, }) {
|
|
|
293
293
|
sessionStorage.setItem("sailfishApiKey", apiKey);
|
|
294
294
|
sessionStorage.setItem("sailfishBackendApi", backendApi);
|
|
295
295
|
}
|
|
296
|
-
//
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
urlStr = input;
|
|
302
|
-
}
|
|
303
|
-
else if (typeof URL !== "undefined" && input instanceof URL) {
|
|
304
|
-
urlStr = input.href;
|
|
305
|
-
}
|
|
306
|
-
else if (typeof Request !== "undefined" && input instanceof Request) {
|
|
307
|
-
urlStr = input.url;
|
|
308
|
-
}
|
|
309
|
-
else if (input != null && typeof input.toString === "function") {
|
|
310
|
-
// As per web APIs, fetch/open may accept any object with a stringifier.
|
|
311
|
-
urlStr = input.toString();
|
|
312
|
-
}
|
|
313
|
-
if (!urlStr)
|
|
314
|
-
return false;
|
|
315
|
-
// Use WHATWG URL parsing with a base for relative URLs.
|
|
316
|
-
let parsed;
|
|
317
|
-
try {
|
|
318
|
-
const base = typeof window !== "undefined"
|
|
319
|
-
? window.location.href
|
|
320
|
-
: "http://localhost/";
|
|
321
|
-
parsed = new URL(urlStr, base);
|
|
322
|
-
}
|
|
323
|
-
catch {
|
|
324
|
-
return false; // If we can't parse, just say "no match" instead of throwing.
|
|
325
|
-
}
|
|
326
|
-
const { hostname, pathname, port, protocol } = parsed;
|
|
327
|
-
// Only match http(s) hosts/paths; ignore others like data:, blob:, about:.
|
|
328
|
-
if (!/^https?:$/.test(protocol))
|
|
329
|
-
return false;
|
|
296
|
+
// Internal: match a *pre-parsed* URL against patterns. Hot path on the
|
|
297
|
+
// header-propagation gate, called twice per request (deny + allow). Splitting
|
|
298
|
+
// this from matchUrlWithWildcard() lets callers parse the URL once and reuse.
|
|
299
|
+
function matchParsedUrlAgainstPatterns(parsed, patterns) {
|
|
300
|
+
const { hostname, pathname, port } = parsed;
|
|
330
301
|
// Handle stripping 'www.' and port
|
|
331
302
|
const domain = hostname.startsWith("www.")
|
|
332
303
|
? hostname.slice(4).toLowerCase()
|
|
@@ -383,6 +354,38 @@ export function matchUrlWithWildcard(input, patterns) {
|
|
|
383
354
|
return true;
|
|
384
355
|
});
|
|
385
356
|
}
|
|
357
|
+
// Public wrapper: parse + delegate. Preserved for callers outside the gate
|
|
358
|
+
// (interceptor wrappers, tests). Hot paths should call
|
|
359
|
+
// matchParsedUrlAgainstPatterns() directly with a pre-parsed URL.
|
|
360
|
+
export function matchUrlWithWildcard(input, patterns) {
|
|
361
|
+
// Tolerate non-string inputs (Request, URL, etc.); coerce to string when possible.
|
|
362
|
+
let urlStr;
|
|
363
|
+
if (typeof input === "string") {
|
|
364
|
+
urlStr = input;
|
|
365
|
+
}
|
|
366
|
+
else if (typeof URL !== "undefined" && input instanceof URL) {
|
|
367
|
+
urlStr = input.href;
|
|
368
|
+
}
|
|
369
|
+
else if (typeof Request !== "undefined" && input instanceof Request) {
|
|
370
|
+
urlStr = input.url;
|
|
371
|
+
}
|
|
372
|
+
else if (input != null && typeof input.toString === "function") {
|
|
373
|
+
urlStr = input.toString();
|
|
374
|
+
}
|
|
375
|
+
if (!urlStr)
|
|
376
|
+
return false;
|
|
377
|
+
let parsed;
|
|
378
|
+
try {
|
|
379
|
+
const base = typeof window !== "undefined"
|
|
380
|
+
? window.location.href
|
|
381
|
+
: "http://localhost/";
|
|
382
|
+
parsed = new URL(urlStr, base);
|
|
383
|
+
}
|
|
384
|
+
catch {
|
|
385
|
+
return false;
|
|
386
|
+
}
|
|
387
|
+
return matchParsedUrlAgainstPatterns(parsed, patterns);
|
|
388
|
+
}
|
|
386
389
|
export function createSkipHeadersPropagationChecker(domainsToNotPropagateHeaderTo = [], domainsToPropagateHeaderTo = []) {
|
|
387
390
|
// Pre-compute the combined domain exclusion patterns once per interceptor setup
|
|
388
391
|
const combinedPatterns = [
|
|
@@ -392,26 +395,30 @@ export function createSkipHeadersPropagationChecker(domainsToNotPropagateHeaderT
|
|
|
392
395
|
// Pre-compute allowlist presence once (avoids per-request .length check overhead)
|
|
393
396
|
const hasAllowlist = domainsToPropagateHeaderTo.length > 0;
|
|
394
397
|
return function shouldSkipHeadersPropagation(url) {
|
|
395
|
-
|
|
398
|
+
// Parse the URL ONCE and reuse for every subsequent check. URL parsing is
|
|
399
|
+
// the dominant cost on this hot path (called for every fetch/XHR), so
|
|
400
|
+
// calling matchParsedUrlAgainstPatterns() with the cached parse instead of
|
|
401
|
+
// matchUrlWithWildcard() (which would re-parse) is the key perf win.
|
|
402
|
+
let parsed;
|
|
396
403
|
try {
|
|
397
|
-
|
|
404
|
+
parsed = new URL(typeof url === "string" ? url : String(url?.url ?? url), window.location.href);
|
|
398
405
|
}
|
|
399
406
|
catch {
|
|
400
407
|
// If we cannot parse, play it safe and do NOT inject headers.
|
|
401
408
|
return true;
|
|
402
409
|
}
|
|
403
410
|
// 1️⃣ STATIC ASSET EXCLUSIONS (by comprehensive file extension list) — O(1) Set lookup
|
|
404
|
-
const lowerPathname =
|
|
411
|
+
const lowerPathname = parsed.pathname.toLowerCase();
|
|
405
412
|
const lastDotIdx = lowerPathname.lastIndexOf(".");
|
|
406
413
|
if (lastDotIdx !== -1 && STATIC_EXTENSIONS_SET.has(lowerPathname.slice(lastDotIdx))) {
|
|
407
414
|
return true;
|
|
408
415
|
}
|
|
409
416
|
// 2️⃣ ALLOWLIST CHECK — if provided, URL must match at least one allowlist pattern
|
|
410
|
-
if (hasAllowlist && !
|
|
417
|
+
if (hasAllowlist && !matchParsedUrlAgainstPatterns(parsed, domainsToPropagateHeaderTo)) {
|
|
411
418
|
return true;
|
|
412
419
|
}
|
|
413
420
|
// 3️⃣ WILDCARD-BASED EXCLUSION (domain + path) — blocklist still applies even if allowlisted
|
|
414
|
-
if (
|
|
421
|
+
if (matchParsedUrlAgainstPatterns(parsed, combinedPatterns)) {
|
|
415
422
|
return true;
|
|
416
423
|
}
|
|
417
424
|
return false;
|
|
@@ -1028,7 +1035,12 @@ function getMapUuidFromWindow() {
|
|
|
1028
1035
|
// Note - we do NOT send serviceIdentifier because
|
|
1029
1036
|
// it would be 1 serviceIdentifier per frontend user session,
|
|
1030
1037
|
// which is very wasteful
|
|
1031
|
-
export async function startRecording({ apiKey, backendApi = "https://api-service.sailfishqa.com",
|
|
1038
|
+
export async function startRecording({ apiKey, backendApi = "https://api-service.sailfishqa.com",
|
|
1039
|
+
// Default: ["*"] = propagate to every URL (deny list still applies).
|
|
1040
|
+
// Pass [] to fully disable header propagation. Pass exact patterns
|
|
1041
|
+
// (e.g. ["api.myapp.com", "*.internal.com"]) to restrict propagation
|
|
1042
|
+
// to a known set of domains.
|
|
1043
|
+
domainsToPropagateHeaderTo = ["*"], domainsToNotPropagateHeaderTo = [], serviceVersion, serviceIdentifier, gitSha, serviceAdditionalMetadata, enableIpTracking, captureStreamingResponseBody = true, captureResponseBodyMaxMb = 10, captureStreamPrefixKb = 64, captureStreamTimeoutMs = 10000, enableFiberTracking = false, deferRecording, deferRecordingStart, chunkSnapshot, useWsWorker = true, maskTextClass, library, }) {
|
|
1032
1044
|
// Synthetic-environment no-op: Lighthouse/PSI, HeadlessChrome, WebPageTest
|
|
1033
1045
|
// (PTST), Puppeteer/Playwright/Selenium (navigator.webdriver). We skip init
|
|
1034
1046
|
// entirely to avoid WSS retry noise, third-party perf penalties in audits,
|
|
@@ -1170,6 +1182,9 @@ export async function startRecording({ apiKey, backendApi = "https://api-service
|
|
|
1170
1182
|
...DEFAULT_CAPTURE_SETTINGS,
|
|
1171
1183
|
...captureSettingsResponse.data?.captureSettingsFromApiKey,
|
|
1172
1184
|
enableFiberTracking,
|
|
1185
|
+
// Caller-supplied maskTextClass wins over server-fetched value; only
|
|
1186
|
+
// applied when explicitly set so undefined cannot clobber the server.
|
|
1187
|
+
...(maskTextClass !== undefined ? { maskTextClass } : {}),
|
|
1173
1188
|
};
|
|
1174
1189
|
// If a socket is already open now, stop here.
|
|
1175
1190
|
if (g.ws && g.ws.readyState === 1) {
|
package/dist/index.js.br
CHANGED
|
Binary file
|
package/dist/index.js.gz
CHANGED
|
Binary file
|
package/dist/recorder.cjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
3
|
-
const e = require("./chunks/index-
|
|
4
|
-
exports.DEFAULT_CAPTURE_SETTINGS = e.DEFAULT_CAPTURE_SETTINGS, exports.DEFAULT_CONSOLE_RECORDING_SETTINGS = e.DEFAULT_CONSOLE_RECORDING_SETTINGS, exports.STORAGE_VERSION = e.STORAGE_VERSION, exports.addOrUpdateMetadata = e.addOrUpdateMetadata, exports.buildBatches = e.buildBatches, exports.clearStaleFuncSpanState = e.clearStaleFuncSpanState, exports.createSkipHeadersPropagationChecker = e.createSkipHeadersPropagationChecker, exports.createTriageAndIssueFromRecorder = e.createTriageAndIssueFromRecorder, exports.createTriageFromRecorder = e.createTriageFromRecorder, exports.disableFunctionSpanTracking = e.disableFunctionSpanTracking, exports.enableFunctionSpanTracking = e.enableFunctionSpanTracking, exports.ensureHrefCache = e.ensureHrefCache, exports.eventSize = e.eventSize, exports.fetchAndSendIp = e.fetchAndSendIp, exports.fetchCaptureSettings = e.fetchCaptureSettings, exports.fetchEngineeringTicketPlatformIntegrations = e.fetchEngineeringTicketPlatformIntegrations, exports.fetchFunctionSpanTrackingEnabled = e.fetchFunctionSpanTrackingEnabled, exports.flushBufferedEvents = e.flushBufferedEvents, exports.getCachedHref = e.getCachedHref, exports.getCachedHrefNoQuery = e.getCachedHrefNoQuery, exports.getFuncSpanHeader = e.getFuncSpanHeader, exports.getOrSetSessionId = e.getOrSetSessionId, exports.getUrlAndStoredUuids = e.getUrlAndStoredUuids, exports.identify = e.identify, exports.initRecorder = e.initRecorder, exports.initializeConsolePlugin = e.initializeConsolePlugin, exports.initializeDomContentEvents = e.initializeDomContentEvents, exports.initializeFunctionSpanTrackingFromApi = e.initializeFunctionSpanTrackingFromApi, exports.initializeRecording = e.initializeRecording, exports.initializeWebSocket = e.initializeWebSocket, exports.invalidateUrlCache = e.invalidateUrlCache, exports.isFunctionSpanTrackingEnabled = e.isFunctionSpanTrackingEnabled, exports.matchUrlWithWildcard = e.matchUrlWithWildcard, Object.defineProperty(exports, "nowTimestamp", { enumerable: true, get: () => e.nowTimestamp }), exports.onNavigationChange = e.onNavigationChange, exports.openReportIssueModal = e.openReportIssueModal, exports.restoreFuncSpanState = e.restoreFuncSpanState, exports.sendDomainsToNotPropagateHeaderTo = e.sendDomainsToNotPropagateHeaderTo, exports.sendEvent = e.sendEvent, exports.sendGraphQLRequest = e.sendGraphQLRequest, exports.sendMessage = e.sendMessage, exports.startRecording = e.startRecording, exports.startRecordingSession = e.startRecordingSession, exports.trackingEvent = e.trackingEvent, exports.withAppUrlMetadata = e.withAppUrlMetadata;
|
|
3
|
+
const e = require("./chunks/index-Cfj4Epfd.js");
|
|
4
|
+
exports.DEFAULT_CAPTURE_SETTINGS = e.DEFAULT_CAPTURE_SETTINGS, exports.DEFAULT_CONSOLE_RECORDING_SETTINGS = e.DEFAULT_CONSOLE_RECORDING_SETTINGS, exports.STORAGE_VERSION = e.STORAGE_VERSION, exports.addOrUpdateMetadata = e.addOrUpdateMetadata, exports.buildBatches = e.buildBatches, exports.clearStaleFuncSpanState = e.clearStaleFuncSpanState, exports.createSkipHeadersPropagationChecker = e.createSkipHeadersPropagationChecker, exports.createTriageAndIssueFromRecorder = e.createTriageAndIssueFromRecorder, exports.createTriageFromRecorder = e.createTriageFromRecorder, exports.disableFunctionSpanTracking = e.disableFunctionSpanTracking, exports.enableFunctionSpanTracking = e.enableFunctionSpanTracking, exports.ensureHrefCache = e.ensureHrefCache, exports.eventSize = e.eventSize, exports.fetchAndSendIp = e.fetchAndSendIp, exports.fetchCaptureSettings = e.fetchCaptureSettings, exports.fetchEngineeringTicketPlatformIntegrations = e.fetchEngineeringTicketPlatformIntegrations, exports.fetchFunctionSpanTrackingEnabled = e.fetchFunctionSpanTrackingEnabled, exports.flushBufferedEvents = e.flushBufferedEvents, exports.getCachedHref = e.getCachedHref, exports.getCachedHrefNoQuery = e.getCachedHrefNoQuery, exports.getFuncSpanHeader = e.getFuncSpanHeader, exports.getIdentifiedUser = e.getIdentifiedUser, exports.getOrSetSessionId = e.getOrSetSessionId, exports.getUrlAndStoredUuids = e.getUrlAndStoredUuids, exports.identify = e.identify, exports.initRecorder = e.initRecorder, exports.initializeConsolePlugin = e.initializeConsolePlugin, exports.initializeDomContentEvents = e.initializeDomContentEvents, exports.initializeFunctionSpanTrackingFromApi = e.initializeFunctionSpanTrackingFromApi, exports.initializeRecording = e.initializeRecording, exports.initializeWebSocket = e.initializeWebSocket, exports.invalidateUrlCache = e.invalidateUrlCache, exports.isFunctionSpanTrackingEnabled = e.isFunctionSpanTrackingEnabled, exports.matchUrlWithWildcard = e.matchUrlWithWildcard, Object.defineProperty(exports, "nowTimestamp", { enumerable: true, get: () => e.nowTimestamp }), exports.onNavigationChange = e.onNavigationChange, exports.openReportIssueModal = e.openReportIssueModal, exports.restoreFuncSpanState = e.restoreFuncSpanState, exports.sendDomainsToNotPropagateHeaderTo = e.sendDomainsToNotPropagateHeaderTo, exports.sendEvent = e.sendEvent, exports.sendGraphQLRequest = e.sendGraphQLRequest, exports.sendMessage = e.sendMessage, exports.startRecording = e.startRecording, exports.startRecordingSession = e.startRecordingSession, exports.trackingEvent = e.trackingEvent, exports.withAppUrlMetadata = e.withAppUrlMetadata;
|
package/dist/recorder.cjs.br
CHANGED
|
Binary file
|
package/dist/recorder.cjs.gz
CHANGED
|
Binary file
|
package/dist/recorder.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { D, a, S, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x, z, A, B, C, E, F, G, H, I, J, K, L, M, N, O, P, Q, R, T } from "./chunks/index-
|
|
1
|
+
import { D, a, S, b, c, d, e, f, g, h, i, j, k, l, m, n, o, p, q, r, s, t, u, v, w, x, z, A, B, C, E, F, G, H, I, J, K, L, M, N, O, P, Q, R, T, U } from "./chunks/index-CuXHImrI.js";
|
|
2
2
|
export {
|
|
3
3
|
D as DEFAULT_CAPTURE_SETTINGS,
|
|
4
4
|
a as DEFAULT_CONSOLE_RECORDING_SETTINGS,
|
|
@@ -21,28 +21,29 @@ export {
|
|
|
21
21
|
q as getCachedHref,
|
|
22
22
|
r as getCachedHrefNoQuery,
|
|
23
23
|
s as getFuncSpanHeader,
|
|
24
|
-
t as
|
|
25
|
-
u as
|
|
26
|
-
v as
|
|
27
|
-
w as
|
|
28
|
-
x as
|
|
29
|
-
z as
|
|
30
|
-
A as
|
|
31
|
-
B as
|
|
32
|
-
C as
|
|
33
|
-
E as
|
|
34
|
-
F as
|
|
35
|
-
G as
|
|
36
|
-
H as
|
|
37
|
-
I as
|
|
38
|
-
J as
|
|
39
|
-
K as
|
|
40
|
-
L as
|
|
41
|
-
M as
|
|
42
|
-
N as
|
|
43
|
-
O as
|
|
44
|
-
P as
|
|
45
|
-
Q as
|
|
46
|
-
R as
|
|
47
|
-
T as
|
|
24
|
+
t as getIdentifiedUser,
|
|
25
|
+
u as getOrSetSessionId,
|
|
26
|
+
v as getUrlAndStoredUuids,
|
|
27
|
+
w as identify,
|
|
28
|
+
x as initRecorder,
|
|
29
|
+
z as initializeConsolePlugin,
|
|
30
|
+
A as initializeDomContentEvents,
|
|
31
|
+
B as initializeFunctionSpanTrackingFromApi,
|
|
32
|
+
C as initializeRecording,
|
|
33
|
+
E as initializeWebSocket,
|
|
34
|
+
F as invalidateUrlCache,
|
|
35
|
+
G as isFunctionSpanTrackingEnabled,
|
|
36
|
+
H as matchUrlWithWildcard,
|
|
37
|
+
I as nowTimestamp,
|
|
38
|
+
J as onNavigationChange,
|
|
39
|
+
K as openReportIssueModal,
|
|
40
|
+
L as restoreFuncSpanState,
|
|
41
|
+
M as sendDomainsToNotPropagateHeaderTo,
|
|
42
|
+
N as sendEvent,
|
|
43
|
+
O as sendGraphQLRequest,
|
|
44
|
+
P as sendMessage,
|
|
45
|
+
Q as startRecording,
|
|
46
|
+
R as startRecordingSession,
|
|
47
|
+
T as trackingEvent,
|
|
48
|
+
U as withAppUrlMetadata
|
|
48
49
|
};
|
package/dist/recorder.js.br
CHANGED
|
Binary file
|
package/dist/recorder.js.gz
CHANGED
|
Binary file
|