Refactor extension whitelist module

This commit is contained in:
hensm
2021-04-24 08:01:29 +01:00
parent 2edbfce2e4
commit 378ed90b21

View File

@@ -9,27 +9,58 @@ import { CAST_FRAMEWORK_LOADER_SCRIPT_URL
, CAST_LOADER_SCRIPT_URL } from "../lib/endpoints"; , CAST_LOADER_SCRIPT_URL } from "../lib/endpoints";
// Missing on @types/firefox-webext-browser
type OnBeforeSendHeadersDetails = Parameters<Parameters<
typeof browser.webRequest.onBeforeSendHeaders.addListener>[0]>[0] & {
frameAncestors?: Array<{ url: string, frameId: number }>
};
type OnBeforeRequestDetails = Parameters<Parameters<
typeof browser.webRequest.onBeforeRequest.addListener>[0]>[0] & {
frameAncestors?: Array<{ url: string, frameId: number }>
};
const originUrlCache: string[] = [];
let platform: string;
let chromeUserAgent: string | undefined;
let chromeUserAgentHybrid: string | undefined;
export async function initWhitelist () { export async function initWhitelist () {
logger.info("init (whitelist)"); logger.info("init (whitelist)");
// Missing on @types/firefox-webext-browser if (!platform) {
type OnBeforeSendHeadersDetails = Parameters<Parameters<
typeof browser.webRequest.onBeforeSendHeaders.addListener>[0]>[0] & {
frameAncestors?: Array<{ url: string, frameId: number }>
};
type OnBeforeRequestDetails = Parameters<Parameters<
typeof browser.webRequest.onBeforeRequest.addListener>[0]>[0] & {
frameAncestors?: Array<{ url: string, frameId: number }>
};
const originUrlCache: string[] = [];
// TODO: Allow hybrid UA to be configurable // TODO: Allow hybrid UA to be configurable
const platform = (await browser.runtime.getPlatformInfo()).os; platform = (await browser.runtime.getPlatformInfo()).os;
const chromeUserAgent = getChromeUserAgent(platform); chromeUserAgent = getChromeUserAgent(platform);
chromeUserAgentHybrid = getChromeUserAgent(platform, true);
/** /**
* If a UA string can't be obtained, don't bother continuing
* extension initialization
*/
if (!chromeUserAgent) {
throw logger.error("Failed to get Chrome UA string");
}
}
// Register on first run
await registerUserAgentWhitelist();
// Re-register when options change
options.addEventListener("changed", ev => {
const alteredOpts = ev.detail;
if (alteredOpts.includes("userAgentWhitelist")
|| alteredOpts.includes("userAgentWhitelistEnabled")) {
unregisterUserAgentWhitelist();
registerUserAgentWhitelist();
}
});
}
/**
* Web apps usually only load the sender library and * Web apps usually only load the sender library and
* provide cast functionality if the browser is detected * provide cast functionality if the browser is detected
* as Chrome, so we should rewrite the User-Agent header * as Chrome, so we should rewrite the User-Agent header
@@ -52,7 +83,7 @@ export async function initWhitelist () {
for (const header of details.requestHeaders) { for (const header of details.requestHeaders) {
if (header.name === "User-Agent") { if (header.name === "User-Agent") {
header.value = host?.value === "www.youtube.com" header.value = host?.value === "www.youtube.com"
? getChromeUserAgent(platform, true) ? chromeUserAgentHybrid
: chromeUserAgent; : chromeUserAgent;
break; break;
} }
@@ -61,15 +92,15 @@ export async function initWhitelist () {
return { return {
requestHeaders: details.requestHeaders requestHeaders: details.requestHeaders
}; };
} }
/** /**
* Requests from within child frames should also adopt * Requests from within child frames should also adopt
* the modified User-Agent header to support embedded * the modified User-Agent header to support embedded
* players on other origins (like CDN domains) when the * players on other origins (like CDN domains) when the
* main site is whitelisted. * main site is whitelisted.
*/ */
function onWhitelistedChildBeforeSendHeaders ( function onWhitelistedChildBeforeSendHeaders (
details: OnBeforeSendHeadersDetails) { details: OnBeforeSendHeadersDetails) {
if (!details.requestHeaders || !details.frameAncestors) { if (!details.requestHeaders || !details.frameAncestors) {
@@ -84,7 +115,7 @@ export async function initWhitelist () {
for (const header of details.requestHeaders) { for (const header of details.requestHeaders) {
if (header.name === "User-Agent") { if (header.name === "User-Agent") {
header.value = host?.value === "www.youtube.com" header.value = host?.value === "www.youtube.com"
? getChromeUserAgent(platform, true) ? chromeUserAgentHybrid
: chromeUserAgent; : chromeUserAgent;
break; break;
} }
@@ -95,10 +126,10 @@ export async function initWhitelist () {
}; };
} }
} }
} }
/** /**
* Sender applications load a cast_sender.js script that * Sender applications load a cast_sender.js script that
* functions as a loader for the internal chrome-extension: * functions as a loader for the internal chrome-extension:
* hosted script. * hosted script.
@@ -106,7 +137,7 @@ export async function initWhitelist () {
* We can redirect this and inject our own script to setup * We can redirect this and inject our own script to setup
* the API shim. * the API shim.
*/ */
async function onBeforeCastSDKRequest (details: OnBeforeRequestDetails) { async function onBeforeCastSDKRequest (details: OnBeforeRequestDetails) {
if (!details.originUrl) { if (!details.originUrl) {
return {}; return {};
} }
@@ -149,10 +180,10 @@ export async function initWhitelist () {
return { return {
redirectUrl: browser.runtime.getURL("shim/bundle.js") redirectUrl: browser.runtime.getURL("shim/bundle.js")
}; };
} }
async function registerUserAgentWhitelist () { async function registerUserAgentWhitelist () {
const { userAgentWhitelist const { userAgentWhitelist
, userAgentWhitelistEnabled } = await options.getAll(); , userAgentWhitelistEnabled } = await options.getAll();
@@ -176,9 +207,9 @@ export async function initWhitelist () {
onWhitelistedChildBeforeSendHeaders onWhitelistedChildBeforeSendHeaders
, { urls: [ "<all_urls>" ] } , { urls: [ "<all_urls>" ] }
, [ "blocking", "requestHeaders" ]); , [ "blocking", "requestHeaders" ]);
} }
function unregisterUserAgentWhitelist () { function unregisterUserAgentWhitelist () {
originUrlCache.length = 0; originUrlCache.length = 0;
browser.webRequest.onBeforeSendHeaders browser.webRequest.onBeforeSendHeaders
@@ -187,19 +218,4 @@ export async function initWhitelist () {
.removeListener(onWhitelistedChildBeforeSendHeaders); .removeListener(onWhitelistedChildBeforeSendHeaders);
browser.webRequest.onBeforeRequest browser.webRequest.onBeforeRequest
.removeListener(onBeforeCastSDKRequest); .removeListener(onBeforeCastSDKRequest);
}
// Register on first run
await registerUserAgentWhitelist();
// Re-register when options change
options.addEventListener("changed", ev => {
const alteredOpts = ev.detail;
if (alteredOpts.includes("userAgentWhitelist")
|| alteredOpts.includes("userAgentWhitelistEnabled")) {
unregisterUserAgentWhitelist();
registerUserAgentWhitelist();
}
});
} }