Source code

Revision control

Copy as Markdown

Other Tools

const BEHAVIOR_ACCEPT = 0;
const BEHAVIOR_REJECT_FOREIGN = 1;
const BEHAVIOR_REJECT = 2;
const BEHAVIOR_LIMIT_FOREIGN = 3;
const kPrefName = "network.cookie.cookieBehavior";
// Check if we are in frame, and declare ok and finishTest appropriately
const inFrame = ("" + location).match(/frame/);
if (inFrame) {
ok = function (a, message) {
if (!a) {
parent.postMessage("FAILURE: " + message, "http://mochi.test:8888");
} else {
parent.postMessage(message, "http://mochi.test:8888");
}
};
finishTest = function () {
parent.postMessage("done", "http://mochi.test:8888");
};
} else {
finishTest = function () {
SimpleTest.finish();
};
}
function setCookieBehavior(behavior) {
return SpecialPowers.pushPrefEnv({ set: [[kPrefName, behavior]] });
}
function runIFrame(url) {
return new Promise((resolve, reject) => {
function onMessage(e) {
if (e.data == "done") {
resolve();
window.removeEventListener("message", onMessage);
return;
}
ok(!e.data.match(/^FAILURE/), e.data + " (IFRAME = " + url + ")");
}
window.addEventListener("message", onMessage);
document.querySelector("iframe").src = url;
});
}
function runWorker(url) {
return new Promise((resolve, reject) => {
var worker = new Worker(url);
worker.addEventListener("message", function (e) {
if (e.data == "done") {
resolve();
return;
}
ok(!e.data.match(/^FAILURE/), e.data + " (WORKER = " + url + ")");
});
});
}
function chromePower(allowed, blockSessionStorage) {
// localStorage is affected by storage policy.
try {
SpecialPowers.wrap(window).localStorage.getItem("X");
ok(allowed, "getting localStorage from chrome didn't throw");
} catch (e) {
ok(!allowed, "getting localStorage from chrome threw");
}
// sessionStorage is not. See bug 1183968.
try {
SpecialPowers.wrap(window).sessionStorage.getItem("X");
ok(!blockSessionStorage, "getting sessionStorage from chrome didn't throw");
} catch (e) {
ok(blockSessionStorage, "getting sessionStorage from chrome threw");
}
// indexedDB is affected by storage policy.
try {
SpecialPowers.wrap(window).indexedDB;
ok(allowed, "getting indexedDB from chrome didn't throw");
} catch (e) {
ok(!allowed, "getting indexedDB from chrome threw");
}
// Same with caches, along with the additional https-only requirement.
try {
var shouldResolve = allowed && location.protocol == "https:";
var promise = SpecialPowers.wrap(window).caches.keys();
ok(true, "getting caches from chrome should never throw");
return new Promise((resolve, reject) => {
promise.then(
function () {
ok(shouldResolve, "The promise was resolved for chrome");
resolve();
},
function (e) {
ok(!shouldResolve, "The promise was rejected for chrome: " + e);
resolve();
}
);
});
} catch (e) {
ok(false, "getting caches from chrome threw");
return undefined;
}
}
function storageAllowed() {
try {
localStorage.getItem("X");
ok(true, "getting localStorage didn't throw");
} catch (e) {
ok(false, "getting localStorage should not throw");
}
try {
sessionStorage.getItem("X");
ok(true, "getting sessionStorage didn't throw");
} catch (e) {
ok(false, "getting sessionStorage should not throw");
}
try {
indexedDB;
ok(true, "getting indexedDB didn't throw");
} catch (e) {
ok(false, "getting indexedDB should not throw");
}
try {
var promise = caches.keys();
ok(true, "getting caches didn't throw");
return new Promise((resolve, reject) => {
promise.then(
function () {
ok(location.protocol == "https:", "The promise was not rejected");
resolve();
},
function () {
ok(
location.protocol !== "https:",
"The promise should not have been rejected"
);
resolve();
}
);
});
} catch (e) {
ok(location.protocol !== "https:", "getting caches should not have thrown");
return Promise.resolve();
}
}
function storagePrevented() {
try {
localStorage.getItem("X");
ok(false, "getting localStorage should have thrown");
} catch (e) {
ok(true, "getting localStorage threw");
}
if (location.hash == "#thirdparty") {
// No matter what the user's preferences are, we don't block
// sessionStorage in 3rd-party iframes. We do block them everywhere
// else however.
try {
sessionStorage.getItem("X");
ok(true, "getting sessionStorage didn't throw");
} catch (e) {
ok(false, "getting sessionStorage should not have thrown");
}
} else {
try {
sessionStorage.getItem("X");
ok(false, "getting sessionStorage should have thrown");
} catch (e) {
ok(true, "getting sessionStorage threw");
}
}
try {
indexedDB;
ok(false, "getting indexedDB should have thrown");
} catch (e) {
ok(true, "getting indexedDB threw");
}
try {
var promise = caches.keys();
ok(true, "getting caches didn't throw");
return new Promise((resolve, reject) => {
promise.then(
function () {
ok(false, "The promise should have rejected");
resolve();
},
function () {
ok(true, "The promise was rejected");
resolve();
}
);
});
} catch (e) {
ok(location.protocol !== "https:", "getting caches should not have thrown");
return Promise.resolve();
}
}
function task(fn) {
if (!inFrame) {
SimpleTest.waitForExplicitFinish();
}
var gen = fn();
function next_step(val, e) {
var it;
try {
if (typeof e !== "undefined") {
it = gen.throw(e);
} else {
it = gen.next(val);
}
} catch (e) {
ok(false, "An error was thrown while stepping: " + e);
ok(false, "Stack: " + e.stack);
finishTest();
}
if (it.done) {
finishTest();
return;
}
it.value.then(next_step, e => next_step(null, e));
}
if (!gen.then) {
next_step();
} else {
gen.then(finishTest, e => {
ok(false, "An error was thrown while stepping: " + e);
ok(false, "Stack: " + e.stack);
finishTest();
});
}
}
// The test will run on a separate window in order to apply the new cookie jar settings.
async function runTestInWindow(test) {
let w = window.open("window_storagePermissions.html");
await new Promise(resolve => {
w.onload = e => {
resolve();
};
});
await new Promise(resolve => {
onmessage = e => {
if (e.data.type == "finish") {
w.close();
resolve();
return;
}
if (e.data.type == "check") {
ok(e.data.test, e.data.msg);
return;
}
ok(false, "Unknown message");
};
w.postMessage(test.toString(), "*");
});
}