1// This script is to be called directly in the <head>. It should not import any 2// other file or library, as it cannot be transformed into a module (because a 3// module is deferred): the function should be the very first thing launched on 4// the page to be able to bypass other IIFE of 3rd-party services that inject 5// new scripts client-side. 6 7// eslint-disable-next-line no-unused-vars 8function watch3rdPartyScripts(thirdPartyDomainsBlockList) { 9 const removeWWW = (domain) => (domain.startsWith("www.") ? domain.slice(4) : domain); 10 const blockList = thirdPartyDomainsBlockList.map(removeWWW); 11 const cookieRegex = /(^|(; ))website_cookies_bar=(?<value>[^;]+)/; 12 const scriptSrcDesc = Object.getOwnPropertyDescriptor(HTMLScriptElement.prototype, "src"); 13 Object.defineProperty(HTMLScriptElement.prototype, "_src", scriptSrcDesc); 14 Object.defineProperty(HTMLScriptElement.prototype, "src", { 15 enumerable: true, 16 configurable: true, 17 get() { 18 return this._src; 19 }, 20 set(val) { 21 const cookiesBarCookie = document.cookie.match(cookieRegex)?.groups.value; 22 const host = removeWWW(new URL(val, window.location.origin).host.toLowerCase()); 23 if ( 24 (!cookiesBarCookie || !JSON.parse(cookiesBarCookie).optional) && 25 blockList.some((domain) => host === domain || host.endsWith(`.${domain}`)) 26 ) { 27 this.dataset.nocookieSrc = val; 28 this.dataset.needCookiesApproval = "true"; 29 this._src = "about:blank"; 30 } else { 31 this._src = val; 32 } 33 }, 34 }); 35 document.addEventListener( 36 "optionalCookiesAccepted", 37 () => { 38 for (const scriptEl of document.querySelectorAll( 39 "script[data-need-cookies-approval]" 40 )) { 41 // We have to completely recreate the scripts for them to fire, we 42 // cannot just switch the src. 43 const newScript = document.createElement("script"); 44 newScript._src = scriptEl.dataset.nocookieSrc; 45 scriptEl.insertAdjacentElement("beforebegin", newScript); 46 scriptEl.remove(); 47 } 48 }, 49 { once: true } 50 ); 51}
Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.