diff --git a/src/js/background.js b/src/js/background.js index a3cec271b8..66165876d1 100644 --- a/src/js/background.js +++ b/src/js/background.js @@ -844,6 +844,7 @@ Badger.prototype = { learnLocally: false, migrationLevel: 0, preventWebRTCIPLeak: false, + removeXClientDataHeaders: false, seenComic: false, sendDNTSignal: true, showCounter: true, @@ -1125,6 +1126,12 @@ Badger.prototype = { return this.getSettings().getItem("checkForDNTPolicy"); }, + isRemoveXClientDataHeaderEnabled: function() { + if (!chrome.runtime.getBrowserInfo) { + return this.getSettings().getItem("removeXClientDataHeaders"); + } + }, + isFlocOverwriteEnabled: function() { if (document.interestCohort) { return this.getSettings().getItem("disableFloc"); diff --git a/src/js/options.js b/src/js/options.js index 608546e90d..0b5ad34528 100644 --- a/src/js/options.js +++ b/src/js/options.js @@ -168,6 +168,22 @@ function loadOptions() { }); } + // only show the x-client-data header setting if in Chrome & Chromium browsers + // TODO: more accurate way to determine this is a Chrome or Chromium browser + if (!chrome.runtime.getBrowserInfo) { + $("#remove-x-client-data-toggle").show(); + $("#toggle-x-client-data-header-mode") + .prop("checked", OPTIONS_DATA.settings.removeXClientDataHeaders) + .on("click", function () { + const removeXClientDataHeaders = $("#toggle-x-client-data-header-mode").prop("checked"); + + chrome.runtime.sendMessage({ + type: "updateSettings", + data: { removeXClientDataHeaders } + }); + }); + } + if (OPTIONS_DATA.webRTCAvailable && OPTIONS_DATA.legacyWebRtcProtectionUser) { $("#webRTCToggle").show(); $("#toggle_webrtc_mode") diff --git a/src/js/webrequest.js b/src/js/webrequest.js index 057ab319b0..2f38a329d3 100644 --- a/src/js/webrequest.js +++ b/src/js/webrequest.js @@ -203,14 +203,18 @@ function onBeforeSendHeaders(details) { type = details.type, url = details.url; + // option to remove x-client-data headers as well + const removeXClientData = badger.isRemoveXClientDataHeaderEnabled(); + if (_isTabChromeInternal(tab_id)) { // DNT policy requests: strip cookies if (type == "xmlhttprequest" && url.endsWith("/.well-known/dnt-policy.txt")) { - // remove Cookie headers and X-Client-Data headers + // remove Cookie headers let newHeaders = []; + for (let i = 0, count = details.requestHeaders.length; i < count; i++) { let header = details.requestHeaders[i]; - if (header.name.toLowerCase() != "cookie" && header.name.toLowerCase() != "x-client-data") { + if (header.name.toLowerCase() != "cookie" || (removeXClientData && header.name.toLowerCase() != 'x-client-data')) { newHeaders.push(header); } } @@ -256,10 +260,10 @@ function onBeforeSendHeaders(details) { if (action == constants.COOKIEBLOCK || action == constants.USER_COOKIEBLOCK) { let newHeaders; - // GET requests: remove cookie headers and X-client-data headers, reduce referrer header to origin + // GET requests: remove cookie (and x-client-data if option is set) headers, reduce referrer header to origin if (details.method == "GET") { newHeaders = details.requestHeaders.filter(header => { - return (header.name.toLowerCase() != "cookie" && header.name.toLowerCase() != "x-client-data"); + return (header.name.toLowerCase() != "cookie" || (removeXClientData && header.name.toLowerCase() != 'x-client-data')); }).map(header => { if (header.name.toLowerCase() == "referer") { header.value = header.value.slice( @@ -270,10 +274,10 @@ function onBeforeSendHeaders(details) { return header; }); - // remove cookie, referrer, and X-Client-Data headers otherwise + // remove cookie, referrer (and x-client-data if option is set) otherwise } else { newHeaders = details.requestHeaders.filter(header => { - return (header.name.toLowerCase() != "cookie" && header.name.toLowerCase() != "referer" && header.name.toLowerCase() != "x-client-data"); + return (header.name.toLowerCase() != "cookie" && header.name.toLowerCase() != "referer" && (removeXClientData && header.name.toLowerCase() != 'x-client-data')); }); }