fix: sanitize page URLs recorded into telemetry - #729
Open
mayberryzane wants to merge 2 commits into
Open
Conversation
mayberryzane
force-pushed
the
sanitize-page-urls-in-telemetry
branch
from
August 14, 2026 18:53
770cc64 to
dc66458
Compare
mayberryzane
marked this pull request as ready for review
August 14, 2026 19:13
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes using default effort and found 1 potential issue.
❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, have a team admin enable autofix in the Cursor dashboard.
Reviewed by Cursor Bugbot for commit dc66458. Configure here.
abelonogov-ld
approved these changes
Aug 15, 2026
`ErrorMessage.url` was set from `window.location.href` verbatim, so any secret in the query string or fragment — OAuth `access_token`/`id_token`, magic links, password reset tokens — was uploaded with the error event. `sanitizeUrl` already redacts sensitive query params and strips token-bearing fragments (#595), but it was only wired into the network listener, never the error path. Add `sanitizedLocationHref()` and route every telemetry-bound page URL through it: - error URLs: `Highlight._recordErrorMessage`, `ObserveSDK` (x2), `ErrorListener` (window.onerror / unhandled rejection), and the `console.error` capture in `FirstLoadListeners` - span attributes: `url.full` on user-interaction and `ld.track` spans, `event.url`, and the page-view span's `url.full` / `page_view.url` / `page_view.previous_url` - the history-navigation span name in `_updateInteractionName` - metric `group` attributes across viewport, device, web-vital, performance, and network-performance gauges in both SDK generations - `Navigate` / `Reload` / `Referrer` custom events and the `referrer` session property - the jank listener's emitted `newLocation` Change detection and comparisons keep reading the raw `window.location.href` so redaction never collapses two distinct URLs; only the recorded value is sanitized. `window.location.pathname` sites are left alone — they carry no query or fragment. Note: metric `group` values and page-view URLs are now redacted, so aggregation keys change for URLs that contained sensitive params.
`_patchHistoryMethod` composed the URL as `pathname + hash + search`, which is not a well-formed URL. Passing it to `sanitizeUrl` made the URL parser absorb the query into the fragment, defeating redaction in both directions: - a token-bearing fragment survived whenever a benign query was also present, because `sanitizeFragment` split on the `?` that had been appended after the hash and only inspected the trailing query params - sensitive query keys that are not also fragment-sensitive (`sig`, `signature`, `awsaccesskeyid`) were never redacted when a fragment was present, since `urlObject.search` came back empty Composing `pathname + search + hash` fixes both. The comparison that gates the rename still uses the raw values and both sides use the same order, so change detection is unaffected. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
Vadman97
force-pushed
the
sanitize-page-urls-in-telemetry
branch
from
August 20, 2026 23:24
09f73d4 to
b9a95bb
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.

Summary
ErrorMessage.urlwas set fromwindow.location.hrefverbatim, so any secret sitting in the query string or fragment (OAuthaccess_token/id_token, magic links, password reset tokens) was uploaded to the backend with the error event.sanitizeUrlalready redacts sensitive query params and strips token-bearing fragments — that landed in #595 — but it was only ever wired into the network listener. The error path is separate code (client/index.tsx, notnetwork-sanitizer.ts) and was never covered.This adds
sanitizedLocationHref()next tosanitizeUrland routes every telemetry-bound page URL through it.What changed
Error URLs
Highlight._recordErrorMessage—client/index.tsxObserveSDKerror recording, both call sites —sdk/observe.tsErrorListener—window.onerrorand unhandled rejectionsconsole.errorcapture inFirstLoadListenersSpan attributes and names
url.fullandevent.urlon user-interaction spansurl.fullonld.trackspansurl.full,page_view.url,page_view.previous_urlon the page-view span — this one fires on every SPA navigation, including OAuth callbacks_updateInteractionNameMetric
groupattributes across viewport, device, web-vital, performance, and network-performance gauges, in both SDK generations (client/index.tsxandsdk/observe.ts) plusH.recordMetricCustom events and session properties
Navigate/Reloadcustom eventsReferrercustom event andreferrersession property (document.referrercarries the previous page's query string)newLocationDeliberately unchanged
window.location.href(LocationChangeInstrumentation._lastUrl,jankState.location, the pre/post URLs in_patchHistoryMethod). Sanitizing those would let redaction collapse two distinct URLs into one and silently drop legitimate page views. Only the recorded value is sanitized.window.location.pathnamesites — no query or fragment to leak.SegmentIntegrationListener's initialcallback(window.location.href). Its consumers branch onobj.type, so a bare string is dropped and never recorded.How did you test this change?
error-listener.test.tsdrives the realwindow.onerrorhandler with?access_token=…and#id_token=…in the URL and asserts the secret is absent from the recordedErrorMessage.url, plus a case confirming benign paths, params, and anchors survive.sanitizedLocationHrefcases alongside the existingsanitizeUrlsuite.yarn turbo run lint enforce-size test --filter highlight.run— 25 files, 452 tests pass; bundle 169.83 kB brotli against the 256 kB limit.yarn format-checkandyarn dedupe --checkclean.Are there any deployment considerations?
Patch-level. One behavior change worth flagging: metric
groupvalues and page-view URLs are now redacted, so aggregation keys shift for any URL that contained sensitive params. Metrics from such URLs will group under the redacted form rather than the raw one.🤖 Generated with Claude Code
Note
Overview
Stops the browser SDK from uploading OAuth tokens, magic links, and similar secrets that live in the page query string or fragment.
Adds
sanitizedLocationHref()(wrapping existingsanitizeUrl) and uses it for every telemetry-bound page URL: errorurlfields, metricgroups, span attributes (url.full, page-view, user-interaction,ld.track), Navigate/Reload/Referrer custom events, and janknewLocation. URL comparisons still use the raw href so redaction cannot collapse distinct navigations.Also rebuilds history-patch URLs as
pathname + search + hashso query tokens are not treated as part of the fragment. Tests cover error URLs,sanitizedLocationHref, and history span names. Metric groups for URLs that contained secrets will now aggregate under the redacted form.Reviewed by Cursor Bugbot for commit b9a95bb. Bugbot is set up for automated code reviews on this repo. Configure here.