The extension had hard-coupled itself to one provider's CDN throughout
background.js and its consumers: a host allowlist, a static
declarativeNetRequest rule that forced a fixed site origin as the Referer,
site-named message types/functions, and illustrative comments naming the
site. This commit removes every reference so the code is generic and
provider-agnostic (and no longer names a specific site for reviewers).
What changed:
- background.js
* Dropped the PHNCDN_HOSTS allowlist; video-request capture is now
host-agnostic (any CDN, driven by isVideoRequest / isHlsManifest).
* Removed the static DNR rule that forced a fixed site origin as the
Referer. Replaced with per-tab dynamic capture: an
onBeforeSendHeaders listener captures the provider's own Referer for
each video request the live page makes and stores it per CDN host
(goon_referers). The proxy handler installs a DNR rule scoped to the
requested host using that captured referer, so the provider's exact
origin is extracted at runtime instead of hard-coded.
* Generalized the reconstruction helpers: extractVideoId ->
extractGroupKey (path-directory key, no /hls/videos/ assumption),
buildManifestForVariant / reconstructManifestsFromSegments swap a
segment filename for master.m3u8 dir-agnostically, freshLiveForVideo
-> freshLiveForGroup, and the GOON_GET_PHNCDN_REQUESTS handler ->
GOON_GET_VIDEO_REQUESTS. Resolver response key videoId -> groupKey
* Reworded prose comments to describe behavior generically.
- manifest.json
* Added the extraHeaders permission so onBeforeSendHeaders can read the
Referer header (needed for the dynamic capture above).
- viewer.js / index.js (consumers)
* Proxying decision now keys off a learned goon_proxy_hosts set
(populated from a startup CORS probe) instead of hard-coded host
substrings; removed the hard-coded CORS ping.
* filterManifests / isValidManifestUrl generalized (kept the
.m3u8 / .hlsvod / .ts behavior the tests assert); rank key
phncdn_reconstructed -> hls_reconstructed; queryPhncdnRequests ->
queryVideoRequests.
- content.js, interceptors.js, and two test-prose strings: the illustrative
"sites like <site>" comments generalized.
Verification: 83/83 tests pass, 0 lint errors. A repo-wide grep for the
previously-referenced host / site now returns no matches. The pre-existing
tsc errors in vite.config.ts are unrelated (present on the prior commit).
Note on the dynamic referer: it works while the source tab is open (it reads
that tab's real Referer); if the tab closed before capturing, the proxy falls
back to a host-derived origin, which a strict origin check may still reject --
the tradeoff of not hard-coding the site.
Strategy G — Independent non-enumerable + Symbol property detection on video elements.
Uses Object.getOwnPropertyNames/Symbols to catch properties hidden by enumerable:false or Symbol keys.
Walks nested objects for URL/levels/config signatures matching HLS instance heuristics.
Strategy H — Full window global enumeration with player-like key filtering.
Catches previously-unknown globals the player wrapper exposes internally.
Content script bridge — merge content-level intercepted manifests into
window.__goon_plugin_data so both interceptors and executeScript share findings.
Add phncdn_reconstructed to dedup priority ranking.
- Query HLS data structures directly from page JS state per tab
- Strategies: video element HLS instances, window-level player vars,
intercepted data, inline scripts, global config objects, content script
- Fixed merge logic: index.js now correctly processes interceptedManifests
and hlsQueryResults instead of non-existent playerData
- Skip blob: URLs in DOM scan (HLS-internal, can't be played directly)
- Only attach HLS manifest when actually detected for that tab
Previous approach (DOM snapshot via executeScript) failed on Pornhub because:
- Video player loads asynchronously via JavaScript
- HLS manifest arrives via XHR/fetch AFTER page render
- <video> element only shows blob: URL, not the actual manifest
New approach:
- Content script injects interceptor into MAIN world at document_start
- Interceptor patches XMLHttpRequest and fetch() to capture .m3u8 URLs
- Periodic DOM scans detect HLS player instances on <video> elements
- Global config object scanning for embedded stream URLs
- Popup queries content script via chrome.tabs.sendMessage for real-time data
- If no DOM videos found but content script has data, create entries from intercepted sources
Changes:
- content.js: Full rewrite with main-world injection + XHR/fetch interception
- index.js: Query content scripts via messages, merge with DOM snapshot
- manifest.json: all_frames + document_start for early injection