Skip to content

Commit 3388aff

Browse files
rootPaperclip-Paperclip
andcommitted
fix(posthog): suppress browser-extension exceptions from docs PostHog
PostHog's built-in exception autocapture was recording `prism_bash_exports` errors from PrismJS-based browser extensions as if they were docs-site bugs (13 `$exception` events in 48h). The docs site has no PrismJS dependency — Nextra 4.6 uses shiki server-side — so these were pure extension noise. Adds `capture_exceptions: false` plus custom window error handlers with an IGNORED_PATTERNS filter (matching the pattern the sharpapi-site already uses). Real unhandled errors still reach PostHog; extension-injected garbage does not. Co-Authored-By: Paperclip <noreply@paperclip.ing>
1 parent c5cd4e3 commit 3388aff

1 file changed

Lines changed: 65 additions & 0 deletions

File tree

components/PostHogProvider.tsx

Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,16 +4,81 @@ import posthog from 'posthog-js'
44
import { PostHogProvider as PHProvider } from 'posthog-js/react'
55
import { useEffect } from 'react'
66

7+
// Patterns for errors that are browser/extension noise, not real bugs
8+
const IGNORED_PATTERNS = [
9+
/ResizeObserver loop/,
10+
/^Script error\.?$/,
11+
/chrome-extension:\/\//,
12+
/moz-extension:\/\//,
13+
/ChunkLoadError/,
14+
/Loading chunk/,
15+
/prism_bash_exports/, // browser extension (PrismJS-based dev tools) injecting into the page
16+
]
17+
18+
function shouldIgnore(message: string): boolean {
19+
return IGNORED_PATTERNS.some(p => p.test(message))
20+
}
21+
22+
function extractMessage(value: unknown): string {
23+
if (value instanceof Error)
24+
return value.message || value.name || 'Error'
25+
if (typeof value === 'string')
26+
return value
27+
if (value && typeof value === 'object' && 'message' in value)
28+
return String((value as { message: unknown }).message)
29+
try {
30+
return String(value)
31+
}
32+
catch {
33+
return 'unknown'
34+
}
35+
}
36+
737
if (typeof window !== 'undefined') {
838
posthog.init('phc_NwXZnWwvpuCzrhpjDGcrmh8TVLIx8B20hbXq0gYdz5a', {
939
api_host: '/ingest',
1040
ui_host: 'https://us.posthog.com',
1141
person_profiles: 'identified_only',
1242
capture_pageview: true,
1343
capture_pageleave: true,
44+
capture_exceptions: false,
1445
cross_subdomain_cookie: true,
1546
persistence: 'localStorage+cookie',
1647
})
48+
49+
// Custom exception capture with extension-noise filtering.
50+
// capture_exceptions: false disables PostHog's built-in autocapture,
51+
// which was recording browser-extension errors (e.g. prism_bash_exports)
52+
// as if they were docs-site bugs.
53+
window.addEventListener('error', (event) => {
54+
const error = event.error
55+
const message = error ? extractMessage(error) : (event.message || 'unknown')
56+
if (shouldIgnore(message))
57+
return
58+
59+
posthog.captureException(error ?? new Error(message), {
60+
$exception_message: message,
61+
$exception_source: 'window_onerror',
62+
$exception_lineno: event.lineno,
63+
$exception_colno: event.colno,
64+
$exception_filename: event.filename,
65+
})
66+
})
67+
68+
window.addEventListener('unhandledrejection', (event) => {
69+
const reason = event.reason
70+
const message = extractMessage(reason)
71+
if (shouldIgnore(message))
72+
return
73+
74+
posthog.captureException(
75+
reason instanceof Error ? reason : new Error(message),
76+
{
77+
$exception_message: message,
78+
$exception_source: 'unhandledrejection',
79+
},
80+
)
81+
})
1782
}
1883

1984
function DocsEventCapture() {

0 commit comments

Comments
 (0)