Source code

Revision control

Copy as Markdown

Other Tools

Test Info:

/* Any copyright is dedicated to the Public Domain.
"use strict";
const { SiteDataTestUtils } = ChromeUtils.importESModule(
);
const uuidGenerator = Services.uuid;
const ORIGIN_A = "https://example.net";
const ORIGIN_B = "https://example.org";
const PREFLIGHT_URL_PATH =
"/browser/toolkit/components/cleardata/tests/browser/file_cors_preflight.sjs";
const PREFLIGHT_URL_A = ORIGIN_A + PREFLIGHT_URL_PATH;
const PREFLIGHT_URL_B = ORIGIN_B + PREFLIGHT_URL_PATH;
function testPreflightCached(browser, url, token, isCached) {
return SpecialPowers.spawn(
browser,
[url, token, isCached],
async (url, token, isCached) => {
let response = await content.fetch(
new content.Request(`${url}?token=${token}`, {
mode: "cors",
method: "GET",
headers: [["x-test-header", "check"]],
})
);
let expected = isCached ? "0" : "1";
is(
await response.text(),
expected,
`Preflight cache for ${url} ${isCached ? "HIT" : "MISS"}.`
);
}
);
}
async function testDeleteAll(
clearDataFlag,
{ deleteBy = "all", hasUserInput = false } = {}
) {
await BrowserTestUtils.withNewTab("https://example.com", async browser => {
let token = uuidGenerator.generateUUID().toString();
// Populate the preflight cache.
await testPreflightCached(browser, PREFLIGHT_URL_A, token, false);
await testPreflightCached(browser, PREFLIGHT_URL_B, token, false);
// Cache should be populated.
await testPreflightCached(browser, PREFLIGHT_URL_A, token, true);
await testPreflightCached(browser, PREFLIGHT_URL_B, token, true);
await new Promise(resolve => {
if (deleteBy == "principal") {
Services.clearData.deleteDataFromPrincipal(
browser.contentPrincipal,
hasUserInput,
clearDataFlag,
value => {
Assert.equal(value, 0);
resolve();
}
);
} else if (deleteBy == "baseDomain") {
Services.clearData.deleteDataFromBaseDomain(
browser.contentPrincipal.baseDomain,
hasUserInput,
clearDataFlag,
value => {
Assert.equal(value, 0);
resolve();
}
);
} else {
Services.clearData.deleteData(clearDataFlag, value => {
Assert.equal(value, 0);
resolve();
});
}
});
// The preflight cache cleaner cannot delete by principal or baseDomain
// (Bug 1727141). If this method is called, it will check whether the used
// requested the clearing. If the user requested clearing, it will
// over-clear (clear all data). If the request didn't come from the user,
// for example from the PurgeTrackerService, it will not clear anything to
// avoid clearing storage unrelated to the baseDomain or principal.
let clearedAll = deleteBy == "all" || hasUserInput;
// Cache should be cleared.
await testPreflightCached(browser, PREFLIGHT_URL_A, token, !clearedAll);
await testPreflightCached(browser, PREFLIGHT_URL_B, token, !clearedAll);
});
SiteDataTestUtils.clear();
}
add_task(async function test_deleteAll() {
// The cleaner should be called when we target all cleaners, all cache
// cleaners, or just the preflight cache.
let { CLEAR_ALL, CLEAR_ALL_CACHES, CLEAR_PREFLIGHT_CACHE } =
Ci.nsIClearDataService;
for (let flag of [CLEAR_ALL, CLEAR_ALL_CACHES, CLEAR_PREFLIGHT_CACHE]) {
await testDeleteAll(flag);
}
});
add_task(async function test_deleteByPrincipal() {
// The cleaner should be called when we target all cleaners, all cache
// cleaners, or just the preflight cache.
let { CLEAR_ALL, CLEAR_ALL_CACHES, CLEAR_PREFLIGHT_CACHE } =
Ci.nsIClearDataService;
for (let flag of [CLEAR_ALL, CLEAR_ALL_CACHES, CLEAR_PREFLIGHT_CACHE]) {
for (let hasUserInput of [true, false]) {
await testDeleteAll(flag, { deleteBy: "principal", hasUserInput });
}
}
});
add_task(async function test_deletePrivateBrowsingCache() {
async function deletePrivateBrowsingCache(token) {
const browser = await BrowserTestUtils.openNewBrowserWindow({
private: true,
});
const tab = (browser.gBrowser.selectedTab = BrowserTestUtils.addTab(
browser.gBrowser,
));
await BrowserTestUtils.browserLoaded(tab.linkedBrowser);
// Populate the preflight cache and make sure it isn't populated right now
await testPreflightCached(tab.linkedBrowser, PREFLIGHT_URL_A, token, false);
await testPreflightCached(tab.linkedBrowser, PREFLIGHT_URL_B, token, false);
// Cache should be populated.
await testPreflightCached(tab.linkedBrowser, PREFLIGHT_URL_A, token, true);
await testPreflightCached(tab.linkedBrowser, PREFLIGHT_URL_B, token, true);
await browser.close();
}
// Disable https_first mode to not upgrade the connection of the main page
// and get "Blocked loading mixed active content" for the CORS request
// making this test case fail. Another solution would be to change all URLs
// to https.
await SpecialPowers.pushPrefEnv({
set: [["dom.security.https_first_pbm", false]],
});
let token = uuidGenerator.generateUUID().toString();
// Make sure the CORS preflight cache is cleared between two private
// browsing sessions. Calling this function twice to see if the cache isn't
// populated anymore after the first call.
await deletePrivateBrowsingCache(token);
await deletePrivateBrowsingCache(token);
await SpecialPowers.clearUserPref("dom.security.https_first_pbm");
});