@newtalaria/browser 0.1.15 → 0.1.16

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 CHANGED
@@ -175,7 +175,7 @@ Segment payloads are a **gzip-compressed JSON array** of rrweb events.
175
175
  Custom rrweb events:
176
176
 
177
177
  - `talaria-console` — console level + message/args (truncated)
178
- - `talaria-network` — method, redacted URL, status, duration (no bodies / no auth headers)
178
+ - `talaria-network` — method, sanitized URL (no query by default), status, duration, failure metadata (no bodies / no auth headers)
179
179
 
180
180
  Privacy defaults: `maskAllInputs: true`, password fields masked, `[data-talaria-mask]` blocked.
181
181
 
@@ -191,9 +191,11 @@ By default, completed `fetch` / XHR responses with status **500–599** are sent
191
191
 
192
192
  Transport failures (CORS, offline, DNS — browser `TypeError: Failed to fetch`) are also promoted by default as:
193
193
 
194
- `Network error: GET https://… — TypeError: Failed to fetch`
194
+ `Network error: POST https://www.google-analytics.com/g/collect — TypeError: Failed to fetch`
195
195
 
196
- Replay `talaria-network` breadcrumbs include method, redacted URL, status (when present), duration, and on failures `errorName` / `errorMessage` / `aborted`. Request/response bodies and auth headers are never captured.
196
+ **URL privacy:** network telemetry stores `origin + pathname` only (plus `hostname` / `pathname` fields). Query strings and fragments are stripped by default — analytics/ads URLs often carry `cid`, `sid`, `dl`, etc. Set `includeNetworkUrlQuery: true` to keep query params after sensitive-key redaction (`token`, `api_key`, …).
197
+
198
+ Replay `talaria-network` breadcrumbs include method, sanitized URL, status (when an HTTP response exists), duration, and on failures `errorName` / `errorMessage` / `aborted` / `failureKind`. Request/response bodies and auth headers are never captured.
197
199
 
198
200
  ```ts
199
201
  Talaria.init({
@@ -204,6 +206,8 @@ Talaria.init({
204
206
  captureFailedRequests: true,
205
207
  // Default true — CORS/offline/DNS fetch failures
206
208
  captureNetworkErrors: true,
209
+ // Default false — do not store ?query on network URLs
210
+ includeNetworkUrlQuery: false,
207
211
  // Default [[500, 599]]. CMS admin often wants 4xx too:
208
212
  failedRequestStatusCodes: [[400, 599]],
209
213
  // Extra URL substrings to skip (Talaria /events and /replays are always skipped)
@@ -213,6 +217,15 @@ Talaria.init({
213
217
 
214
218
  `AbortError` is never promoted and is ignored by the global `unhandledrejection` handler. If a fetch failure is left unhandled after network-error promotion, the duplicate bare `TypeError` event is suppressed; if promotion is off, the exception is kept and correlated with the recent request URL/method/duration.
215
219
 
220
+ ### Event timestamps
221
+
222
+ | Field | Meaning |
223
+ | --- | --- |
224
+ | `timestamp` | **Occurrence time** on the client (when capture began — before replay flush) |
225
+ | `createdAt` | **Ingest/storage time** on the server |
226
+
227
+ If replay upload runs before event ingest, `extra.sdk.queuedMs` records how long capture waited (ms). A large `createdAt - timestamp` gap is usually flush/queue delay or clock skew — not a wrong failure classification.
228
+
216
229
  ## Public API
217
230
 
218
231
  | API | Description |
@@ -1 +1 @@
1
- {"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EACV,cAAc,EAEd,aAAa,EACb,kBAAkB,EACnB,MAAM,YAAY,CAAC;AAgEpB,OAAO,EACL,0BAA0B,EAC1B,mBAAmB,EACnB,0BAA0B,EAC1B,mBAAmB,EACnB,kBAAkB,GACnB,MAAM,yBAAyB,CAAC;AACjC,OAAO,EACL,uBAAuB,EACvB,+BAA+B,EAC/B,+BAA+B,EAC/B,4BAA4B,GAC7B,MAAM,4BAA4B,CAAC;AACpC,OAAO,EACL,kBAAkB,EAClB,yBAAyB,EACzB,sBAAsB,EACtB,uBAAuB,GACxB,MAAM,6BAA6B,CAAC;AACrC,YAAY,EACV,oBAAoB,EACpB,mBAAmB,EACnB,mBAAmB,GACpB,MAAM,6BAA6B,CAAC;AA0IrC,qBAAa,aAAa;IACxB,OAAO,CAAC,OAAO,CAAgC;IAC/C,OAAO,CAAC,SAAS,CAAmC;IACpD,OAAO,CAAC,QAAQ,CAAuB;IACvC,OAAO,CAAC,SAAS,CAAuB;IACxC,OAAO,CAAC,QAAQ,CAA+B;IAC/C,OAAO,CAAC,MAAM,CAAuB;IACrC,yEAAyE;IACzE,OAAO,CAAC,cAAc,CAAS;IAC/B,OAAO,CAAC,aAAa,CAAS;IAC9B,OAAO,CAAC,eAAe,CAAS;IAChC,OAAO,CAAC,gBAAgB,CAAS;IACjC,OAAO,CAAC,YAAY,CAAK;IACzB,OAAO,CAAC,uBAAuB,CAAK;IACpC,0EAA0E;IAC1E,OAAO,CAAC,iBAAiB,CAAuB;IAChD,4EAA4E;IAC5E,OAAO,CAAC,mBAAmB,CAAuB;IAClD,OAAO,CAAC,UAAU,CAA+C;IACjE,OAAO,CAAC,cAAc,CAA8C;IACpE,OAAO,CAAC,gBAAgB,CAA8C;IACtE,OAAO,CAAC,WAAW,CAAoC;IACvD,OAAO,CAAC,MAAM,CAAS;IACvB,OAAO,CAAC,SAAS,CAAkB;IACnC;;;OAGG;IACH,OAAO,CAAC,gBAAgB,CAAuB;IAC/C,8EAA8E;IAC9E,OAAO,CAAC,wBAAwB,CAAqC;IACrE,iDAAiD;IACjD,OAAO,CAAC,cAAc,CAA+B;IACrD,oFAAoF;IACpF,OAAO,CAAC,SAAS,CAAS;IAC1B;;;OAGG;IACH,OAAO,CAAC,cAAc,CAAS;IAC/B,oEAAoE;IACpE,OAAO,CAAC,qBAAqB,CAA8B;IAE3D,IAAI,CAAC,OAAO,EAAE,kBAAkB,GAAG,IAAI;IA+IvC,WAAW,IAAI,MAAM,GAAG,IAAI;IAKtB,gBAAgB,CACpB,KAAK,EAAE,OAAO,EACd,OAAO,CAAC,EAAE,cAAc,GACvB,OAAO,CAAC,IAAI,CAAC;IAoDV,cAAc,CAClB,OAAO,EAAE,MAAM,EACf,KAAK,GAAE,aAAsB,EAC7B,OAAO,CAAC,EAAE,cAAc,GACvB,OAAO,CAAC,IAAI,CAAC;IAUV,KAAK,CAAC,IAAI,CAAC,EAAE;QACjB,MAAM,CAAC,EAAE,MAAM,CAAC;QAChB,SAAS,CAAC,EAAE,OAAO,CAAC;QACpB,MAAM,CAAC,EAAE,OAAO,CAAC;KAClB,GAAG,OAAO,CAAC,IAAI,CAAC;IA0CjB;;;OAGG;IACG,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IAsD5B,OAAO,CAAC,YAAY;YAwBN,OAAO;IAgKrB;;;OAGG;IACH,OAAO,CAAC,gCAAgC;IAyBxC,OAAO,CAAC,iBAAiB;IAkBzB,OAAO,CAAC,iBAAiB;IAKzB,OAAO,CAAC,uBAAuB;IAK/B,OAAO,CAAC,eAAe;IAQvB,OAAO,CAAC,uBAAuB;IAiB/B,OAAO,CAAC,qBAAqB;YAOf,qBAAqB;IAsBnC;;;OAGG;IACH,OAAO,CAAC,oBAAoB;IAmB5B,OAAO,CAAC,mBAAmB;IAO3B,8EAA8E;YAChE,YAAY;YAgBZ,eAAe;IAW7B,oFAAoF;IACpF,OAAO,CAAC,iBAAiB;IAiBzB,+EAA+E;IAC/E,OAAO,CAAC,oBAAoB;IAI5B;;;;OAIG;IACH,OAAO,CAAC,kBAAkB;IAS1B;;;;OAIG;IACH,OAAO,CAAC,yBAAyB;IAcjC;;;OAGG;YACW,iBAAiB;IAkC/B,OAAO,CAAC,uBAAuB;IAc/B,OAAO,CAAC,0BAA0B;IAMlC,OAAO,CAAC,sBAAsB;IA+B9B;;;OAGG;IACH,OAAO,CAAC,+BAA+B;IA+BvC,OAAO,CAAC,qBAAqB;IA+D7B,OAAO,CAAC,aAAa;YAKP,aAAa;YAkBb,qBAAqB;IAwLnC,OAAO,CAAC,kBAAkB;IAQ1B;;;;;OAKG;YACW,iBAAiB;YAkEjB,cAAc;CAuB7B"}
package/dist/index.js CHANGED
@@ -226,7 +226,7 @@ async function collectBrowserContext() {
226
226
 
227
227
  // src/sdk_meta.ts
228
228
  var SDK_NAME = "@newtalaria/browser";
229
- var SDK_VERSION = "0.1.15";
229
+ var SDK_VERSION = "0.1.16";
230
230
 
231
231
  // src/transport/serverpod.ts
232
232
  var ServerpodTransport = class {
@@ -13450,6 +13450,40 @@ function redactUrl(raw) {
13450
13450
  return raw.replace(SENSITIVE_QUERY, (_m, name) => `${name}=[Filtered]`);
13451
13451
  }
13452
13452
  }
13453
+ function sanitizeNetworkUrl(raw, opts) {
13454
+ const baseHref = opts?.baseHref ?? (typeof location !== "undefined" ? location.href : void 0);
13455
+ try {
13456
+ const parsed = new URL(raw, baseHref);
13457
+ const hostname = parsed.hostname;
13458
+ const pathname = parsed.pathname || "/";
13459
+ const originPath = `${parsed.origin}${pathname}`;
13460
+ if (!opts?.includeQuery) {
13461
+ return { url: originPath, hostname, pathname };
13462
+ }
13463
+ const redacted = new URL(redactUrl(parsed.toString()));
13464
+ const search = redacted.search || void 0;
13465
+ return {
13466
+ url: search ? `${originPath}${search}` : originPath,
13467
+ hostname,
13468
+ pathname,
13469
+ ...search ? { search } : {}
13470
+ };
13471
+ } catch {
13472
+ const stripped = (raw.split(/[?#]/)[0] ?? raw).trim() || raw;
13473
+ if (!opts?.includeQuery) {
13474
+ return { url: stripped, hostname: "", pathname: stripped };
13475
+ }
13476
+ const redacted = redactUrl(raw);
13477
+ const qIndex = redacted.indexOf("?");
13478
+ const search = qIndex >= 0 ? redacted.slice(qIndex) : void 0;
13479
+ return {
13480
+ url: redacted.split("#")[0] || redacted,
13481
+ hostname: "",
13482
+ pathname: stripped,
13483
+ ...search ? { search } : {}
13484
+ };
13485
+ }
13486
+ }
13453
13487
  function defaultBlockSelector(extra) {
13454
13488
  const parts = [
13455
13489
  "[data-talaria-mask]",
@@ -13625,7 +13659,6 @@ function emitNetwork(meta) {
13625
13659
  try {
13626
13660
  record.addCustomEvent("talaria-network", {
13627
13661
  ...meta,
13628
- url: redactUrl(meta.url),
13629
13662
  timestamp: Date.now()
13630
13663
  });
13631
13664
  } catch {
@@ -13697,6 +13730,15 @@ function enrichNetworkMeta(meta) {
13697
13730
  }
13698
13731
  return meta;
13699
13732
  }
13733
+ function networkUrlParts(rawUrl, includeQuery) {
13734
+ const parts = sanitizeNetworkUrl(rawUrl, { includeQuery });
13735
+ return {
13736
+ url: parts.url,
13737
+ hostname: parts.hostname,
13738
+ pathname: parts.pathname,
13739
+ ...parts.search ? { search: parts.search } : {}
13740
+ };
13741
+ }
13700
13742
  function installNetworkHook(options = {}) {
13701
13743
  const originalFetch = typeof fetch === "function" ? fetch.bind(globalThis) : null;
13702
13744
  const XHR = typeof XMLHttpRequest !== "undefined" ? XMLHttpRequest : null;
@@ -13709,8 +13751,13 @@ function installNetworkHook(options = {}) {
13709
13751
  failedRequestIgnoreUrls: options.failedRequestIgnoreUrls ?? [],
13710
13752
  talariaBaseUrl: options.talariaBaseUrl
13711
13753
  };
13754
+ const includeQuery = options.includeNetworkUrlQuery ?? false;
13712
13755
  const handleMeta = (meta) => {
13713
- const enriched = enrichNetworkMeta(meta);
13756
+ const { rawUrl, ...rest } = meta;
13757
+ const enriched = enrichNetworkMeta({
13758
+ ...rest,
13759
+ ...networkUrlParts(rawUrl, includeQuery)
13760
+ });
13714
13761
  try {
13715
13762
  emitNetwork(enriched);
13716
13763
  options.onNetwork?.(enriched);
@@ -13726,12 +13773,13 @@ function installNetworkHook(options = {}) {
13726
13773
  globalThis.fetch = async (input2, init) => {
13727
13774
  const started = Date.now();
13728
13775
  const method = (init?.method ?? (input2 instanceof Request ? input2.method : "GET")).toUpperCase();
13729
- const url = typeof input2 === "string" ? input2 : input2 instanceof URL ? input2.toString() : input2.url;
13776
+ const rawUrl = typeof input2 === "string" ? input2 : input2 instanceof URL ? input2.toString() : input2.url;
13730
13777
  try {
13731
13778
  const response = await originalFetch(input2, init);
13732
13779
  handleMeta({
13733
13780
  method,
13734
- url,
13781
+ rawUrl,
13782
+ url: rawUrl,
13735
13783
  status: response.status,
13736
13784
  durationMs: Date.now() - started,
13737
13785
  ok: response.ok
@@ -13741,7 +13789,8 @@ function installNetworkHook(options = {}) {
13741
13789
  const described = describeUnknownError(error);
13742
13790
  handleMeta({
13743
13791
  method,
13744
- url,
13792
+ rawUrl,
13793
+ url: rawUrl,
13745
13794
  durationMs: Date.now() - started,
13746
13795
  ok: false,
13747
13796
  errorName: described.errorName,
@@ -13764,9 +13813,11 @@ function installNetworkHook(options = {}) {
13764
13813
  const onDone = () => {
13765
13814
  const status = this.status;
13766
13815
  const networkFail = status === 0;
13816
+ const rawUrl = this.__talariaUrl ?? "";
13767
13817
  handleMeta({
13768
13818
  method: this.__talariaMethod ?? "GET",
13769
- url: this.__talariaUrl ?? "",
13819
+ rawUrl,
13820
+ url: rawUrl,
13770
13821
  status,
13771
13822
  durationMs: Date.now() - (this.__talariaStarted ?? Date.now()),
13772
13823
  ok: status >= 200 && status < 400,
@@ -13789,8 +13840,23 @@ function installNetworkHook(options = {}) {
13789
13840
  }
13790
13841
 
13791
13842
  // src/client.ts
13843
+ function networkFailureExtra(failure) {
13844
+ return {
13845
+ method: failure.method || "GET",
13846
+ url: failure.url || "(unknown url)",
13847
+ ...failure.hostname ? { hostname: failure.hostname } : {},
13848
+ ...failure.pathname ? { pathname: failure.pathname } : {},
13849
+ ...failure.search ? { search: failure.search } : {},
13850
+ ...typeof failure.status === "number" ? { status: failure.status } : {},
13851
+ durationMs: failure.durationMs,
13852
+ ok: failure.ok ?? false,
13853
+ failureKind: failure.failureKind ?? "network",
13854
+ aborted: failure.aborted ?? false,
13855
+ ...failure.errorName ? { errorName: failure.errorName } : {},
13856
+ ...failure.errorMessage ? { errorMessage: failure.errorMessage } : {}
13857
+ };
13858
+ }
13792
13859
  function mergeNetworkFailureContext(context, failure) {
13793
- const url = redactUrl(failure.url || "(unknown url)");
13794
13860
  return {
13795
13861
  ...context,
13796
13862
  tags: {
@@ -13801,16 +13867,7 @@ function mergeNetworkFailureContext(context, failure) {
13801
13867
  },
13802
13868
  extra: {
13803
13869
  ...context?.extra ?? {},
13804
- network: {
13805
- method: failure.method,
13806
- url,
13807
- durationMs: failure.durationMs,
13808
- ok: false,
13809
- failureKind: "network",
13810
- errorName: failure.errorName,
13811
- errorMessage: failure.errorMessage,
13812
- aborted: failure.aborted ?? false
13813
- }
13870
+ network: networkFailureExtra(failure)
13814
13871
  }
13815
13872
  };
13816
13873
  }
@@ -13841,6 +13898,7 @@ function resolveOptions(options) {
13841
13898
  disableDefaultIntegrations: options.disableDefaultIntegrations ?? false,
13842
13899
  captureFailedRequests: options.captureFailedRequests ?? true,
13843
13900
  captureNetworkErrors: options.captureNetworkErrors ?? true,
13901
+ includeNetworkUrlQuery: options.includeNetworkUrlQuery ?? false,
13844
13902
  failedRequestStatusCodes: options.failedRequestStatusCodes ?? [[500, 599]],
13845
13903
  failedRequestIgnoreUrls: options.failedRequestIgnoreUrls ?? []
13846
13904
  };
@@ -13969,6 +14027,7 @@ var TalariaClient = class {
13969
14027
  installNetworkHook({
13970
14028
  captureFailedRequests: this.options.captureFailedRequests,
13971
14029
  captureNetworkErrors: this.options.captureNetworkErrors,
14030
+ includeNetworkUrlQuery: this.options.includeNetworkUrlQuery,
13972
14031
  failedRequestStatusCodes: this.options.failedRequestStatusCodes,
13973
14032
  failedRequestIgnoreUrls: this.options.failedRequestIgnoreUrls,
13974
14033
  talariaBaseUrl: this.options.baseUrl,
@@ -13980,7 +14039,7 @@ var TalariaClient = class {
13980
14039
  onFailedRequest: (meta) => {
13981
14040
  const status = meta.status;
13982
14041
  const method = meta.method || "GET";
13983
- const url = redactUrl(meta.url || "(unknown url)");
14042
+ const url = meta.url || "(unknown url)";
13984
14043
  void this.captureMessage(
13985
14044
  `HTTP ${status}: ${method} ${url}`,
13986
14045
  status >= 500 ? "error" : "warning",
@@ -13991,10 +14050,11 @@ var TalariaClient = class {
13991
14050
  "network.failure_kind": "http"
13992
14051
  },
13993
14052
  extra: {
13994
- url,
13995
- durationMs: meta.durationMs,
13996
- ok: meta.ok,
13997
- failureKind: "http"
14053
+ ...networkFailureExtra({
14054
+ ...meta,
14055
+ failureKind: "http",
14056
+ aborted: false
14057
+ })
13998
14058
  }
13999
14059
  }
14000
14060
  );
@@ -14002,7 +14062,7 @@ var TalariaClient = class {
14002
14062
  onNetworkError: (meta) => {
14003
14063
  this.rememberNetworkFailure(meta, { promoted: true });
14004
14064
  const method = meta.method || "GET";
14005
- const url = redactUrl(meta.url || "(unknown url)");
14065
+ const url = meta.url || "(unknown url)";
14006
14066
  const errLabel = meta.errorName && meta.errorMessage ? `${meta.errorName}: ${meta.errorMessage}` : meta.errorMessage || meta.errorName || "Failed to fetch";
14007
14067
  void this.captureMessage(
14008
14068
  `Network error: ${method} ${url} \u2014 ${errLabel}`,
@@ -14013,15 +14073,11 @@ var TalariaClient = class {
14013
14073
  "network.failure_kind": "network",
14014
14074
  ...meta.errorName ? { "network.error_name": meta.errorName } : {}
14015
14075
  },
14016
- extra: {
14017
- url,
14018
- durationMs: meta.durationMs,
14019
- ok: false,
14076
+ extra: networkFailureExtra({
14077
+ ...meta,
14020
14078
  failureKind: "network",
14021
- errorName: meta.errorName,
14022
- errorMessage: meta.errorMessage,
14023
14079
  aborted: false
14024
- }
14080
+ })
14025
14081
  }
14026
14082
  );
14027
14083
  }
@@ -14200,6 +14256,7 @@ var TalariaClient = class {
14200
14256
  throw new Error("@newtalaria/browser: call Talaria.init() first");
14201
14257
  }
14202
14258
  if (this.ingestDisabled) return;
14259
+ const occurredAt = /* @__PURE__ */ new Date();
14203
14260
  const isErrorLike = args.level === "error" || args.level === "fatal";
14204
14261
  let errorClipOutcome = null;
14205
14262
  let attemptedErrorClip = false;
@@ -14257,6 +14314,7 @@ var TalariaClient = class {
14257
14314
  errorClipOutcome = { status: "failed", reason: "buffer_empty" };
14258
14315
  }
14259
14316
  }
14317
+ const queuedMs = Math.max(0, Date.now() - occurredAt.getTime());
14260
14318
  const tags = applyReplayCaptureTags(
14261
14319
  {
14262
14320
  ...this.browserContext ? browserContextTags(this.browserContext) : {},
@@ -14278,7 +14336,12 @@ var TalariaClient = class {
14278
14336
  userAgent: this.browserContext.userAgent
14279
14337
  }
14280
14338
  } : {},
14281
- sdk: { name: SDK_NAME, version: SDK_VERSION },
14339
+ sdk: {
14340
+ name: SDK_NAME,
14341
+ version: SDK_VERSION,
14342
+ // Time spent in capture() before ingest (mostly replay flush).
14343
+ ...queuedMs >= 50 ? { queuedMs } : {}
14344
+ },
14282
14345
  ...args.context?.extra
14283
14346
  },
14284
14347
  errorClipOutcome
@@ -14298,7 +14361,7 @@ var TalariaClient = class {
14298
14361
  url: typeof location !== "undefined" ? location.href : void 0,
14299
14362
  tags: Object.keys(tags).length ? tags : void 0,
14300
14363
  extraJson: extra ? JSON.stringify(extra) : void 0,
14301
- timestamp: (/* @__PURE__ */ new Date()).toISOString(),
14364
+ timestamp: occurredAt.toISOString(),
14302
14365
  keepalive: args.keepalive
14303
14366
  });
14304
14367
  if (replayId && replayId === this.linkableReplayId) {