Use cookie instead of window.name as a tab-configuration hack.
This commit is contained in:
parent
e44fce3ebd
commit
808fd652be
|
@ -1,6 +1,6 @@
|
||||||
"use strict";
|
"use strict";
|
||||||
{
|
{
|
||||||
let marker = JSON.stringify(uuid());
|
let marker = uuid();
|
||||||
let allUrls = ["<all_urls>"];
|
let allUrls = ["<all_urls>"];
|
||||||
|
|
||||||
let Scripts = {
|
let Scripts = {
|
||||||
|
@ -47,7 +47,7 @@
|
||||||
if (typeof perms !== "string") {
|
if (typeof perms !== "string") {
|
||||||
perms = JSON.stringify(perms);
|
perms = JSON.stringify(perms);
|
||||||
}
|
}
|
||||||
return `ns.setup(${perms}, ${marker});`
|
return `ns.setup(${perms}, "${marker}");`
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -104,18 +104,17 @@
|
||||||
: [];
|
: [];
|
||||||
|
|
||||||
var ChildPolicies = {
|
var ChildPolicies = {
|
||||||
async storeTabInfo(tabId, info) {
|
addTabInfoCookie(request, info) {
|
||||||
try {
|
let h = {
|
||||||
let preamble = info ? `${marker} + ${JSON.stringify(JSON.stringify([info]))} + ${marker} + "," + ` : "";
|
name: "Set-Cookie",
|
||||||
await browser.tabs.executeScript(tabId, {
|
value: `${marker}=${JSON.stringify(info)}`
|
||||||
code: `window.name = ${preamble}window.name.split(${marker} + ",").pop();`,
|
};
|
||||||
allFrames: true,
|
let {responseHeaders} = request;
|
||||||
matchAboutBlank: true,
|
if (responseHeaders.some(({value, name}) => h.value === value && h.name === name)) {
|
||||||
runAt: "document_start",
|
return false;
|
||||||
});
|
|
||||||
} catch (e) {
|
|
||||||
error(e);
|
|
||||||
}
|
}
|
||||||
|
responseHeaders.push(h);
|
||||||
|
return true;
|
||||||
},
|
},
|
||||||
async update(policy, tracing) {
|
async update(policy, tracing) {
|
||||||
if (tracing !== "undefined") Scripts.debug = tracing;
|
if (tracing !== "undefined") Scripts.debug = tracing;
|
||||||
|
@ -123,7 +122,7 @@
|
||||||
await Scripts.init();
|
await Scripts.init();
|
||||||
|
|
||||||
if (!policy.enforced) {
|
if (!policy.enforced) {
|
||||||
await Scripts.register(`ns.setup(null, ${marker});`, allUrls);
|
await Scripts.register(Scripts.buildPerms("null"), allUrls);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -292,6 +292,7 @@ var RequestGuard = (() => {
|
||||||
async onHeadersReceived(request) {
|
async onHeadersReceived(request) {
|
||||||
// called for main_frame, sub_frame and object
|
// called for main_frame, sub_frame and object
|
||||||
// check for duplicate calls
|
// check for duplicate calls
|
||||||
|
let headersModified = false;
|
||||||
let pending = pendingRequests.get(request.requestId);
|
let pending = pendingRequests.get(request.requestId);
|
||||||
if (pending) {
|
if (pending) {
|
||||||
if (pending.headersProcessed) {
|
if (pending.headersProcessed) {
|
||||||
|
@ -319,7 +320,10 @@ var RequestGuard = (() => {
|
||||||
capabilities = perms.capabilities;
|
capabilities = perms.capabilities;
|
||||||
} else {
|
} else {
|
||||||
if (isMainFrame || type === "sub_frame") {
|
if (isMainFrame || type === "sub_frame") {
|
||||||
await Settings.enforceTabRestrictions(tabId);
|
let unrestricted = ns.unrestrictedTabs.has(tabId) && {unrestricted: true};
|
||||||
|
if (unrestricted) {
|
||||||
|
headersModified = ChildPolicies.addTabInfoCookie(request, unrestricted);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (isMainFrame && !TabStatus.map.has(tabId)) {
|
if (isMainFrame && !TabStatus.map.has(tabId)) {
|
||||||
|
@ -331,6 +335,9 @@ var RequestGuard = (() => {
|
||||||
if (header) {
|
if (header) {
|
||||||
pending.cspHeader = header;
|
pending.cspHeader = header;
|
||||||
debug(`CSP blocker on %s:`, url, header.value);
|
debug(`CSP blocker on %s:`, url, header.value);
|
||||||
|
headersModified = true;
|
||||||
|
}
|
||||||
|
if (headersModified) {
|
||||||
return {responseHeaders};
|
return {responseHeaders};
|
||||||
}
|
}
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
|
|
|
@ -90,7 +90,6 @@ var Settings = {
|
||||||
|
|
||||||
if (typeof unrestrictedTab === "boolean") {
|
if (typeof unrestrictedTab === "boolean") {
|
||||||
ns.unrestrictedTabs[unrestrictedTab ? "add" : "delete"](tabId);
|
ns.unrestrictedTabs[unrestrictedTab ? "add" : "delete"](tabId);
|
||||||
this.enforceTabRestrictions(tabId, unrestrictedTab);
|
|
||||||
}
|
}
|
||||||
if (reloadAffected) {
|
if (reloadAffected) {
|
||||||
browser.tabs.reload(tabId);
|
browser.tabs.reload(tabId);
|
||||||
|
|
|
@ -47,33 +47,22 @@
|
||||||
this.config.permissions = permissions;
|
this.config.permissions = permissions;
|
||||||
|
|
||||||
// ugly hack: since now we use registerContentScript instead of the
|
// ugly hack: since now we use registerContentScript instead of the
|
||||||
// filterRequest dynamic script injection hack, we use window.name
|
// filterRequest dynamic script injection hack, we use a session cookie
|
||||||
// to store per-tab information. We don't want web content to
|
// to store per-tab information, erasing it as soon as we see it
|
||||||
// mess with it, though, so we wrap it around auto-hiding accessors
|
// (before any content can access it)
|
||||||
|
|
||||||
if (this.config.MARKER = MARKER) {
|
if (this.config.MARKER = MARKER) {
|
||||||
let splitter = `${MARKER},`;
|
let cookieRx = new RegExp(`(?:^|;\\s*)${MARKER}=([^;]*)`);
|
||||||
this.getWindowName = () => window.name.split(splitter).pop();
|
let match = document.cookie.match(cookieRx);
|
||||||
|
if (match) {
|
||||||
let tabInfoRx = new RegExp(`^${MARKER}\\[([^]*?)\\]${MARKER},`);
|
// delete cookie NOW
|
||||||
|
document.cookie = `${MARKER}=;expires=${new Date(Date.now() - 31536000000).toGMTString()}`;
|
||||||
let tabInfoMatch = window.name.match(tabInfoRx);
|
|
||||||
if (tabInfoMatch) {
|
|
||||||
try {
|
try {
|
||||||
this.config.tabInfo = JSON.parse(tabInfoMatch[1]);
|
this.config.tabInfo = JSON.parse(decodeURIComponent(match[1]));
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
error(e);
|
error(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Reflect.defineProperty(window.wrappedJSObject, "name", {
|
|
||||||
get: exportFunction(() => this.getWindowName(), window.wrappedJSObject),
|
|
||||||
set: exportFunction(value => {
|
|
||||||
let tabInfoMatch = window.name.match(tabInfoRx);
|
|
||||||
window.name = tabInfoMatch ? `${tabInfoMatch[0]}${value}` : value;
|
|
||||||
return value;
|
|
||||||
}, window.wrappedJSObject)
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
if (!this.config.permissions || this.config.tabInfo.unrestricted) {
|
if (!this.config.permissions || this.config.tabInfo.unrestricted) {
|
||||||
debug("%s is loading unrestricted by user's choice (%o).", document.URL, this.config);
|
debug("%s is loading unrestricted by user's choice (%o).", document.URL, this.config);
|
||||||
|
|
Loading…
Reference in New Issue