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(
);
let testRules = [
// Top-level cookie rule.
{
id: "87815b2d-a840-4155-8713-f8a26d1f483a",
click: {},
cookies: {
optIn: [
{
name: "foo",
value: "bar",
},
],
},
domains: [TEST_DOMAIN_B],
},
// Child click rule.
{
id: "d42bbaee-f96e-47e7-8e81-efc642518e97",
click: {
optOut: "#optOutBtn",
presence: "#cookieBanner",
runContext: "child",
},
cookies: {},
domains: [TEST_DOMAIN_C],
},
// Top level click rule.
{
id: "19dd1f52-f3e6-4a24-a926-d77f553d1b15",
click: {
optOut: "#optOutBtn",
presence: "#cookieBanner",
},
cookies: {},
domains: [TEST_DOMAIN_A],
},
];
/**
* Insert an iframe and wait for it to load.
* @param {BrowsingContext} parentBC - The BC the frame to insert under.
* @param {string} uri - The URI to load in the frame.
* @returns {Promise} - A Promise which resolves once the frame has loaded.
*/
function insertIframe(parentBC, uri) {
return SpecialPowers.spawn(parentBC, [uri], async testURL => {
let iframe = content.document.createElement("iframe");
iframe.src = testURL;
content.document.body.appendChild(iframe);
await ContentTaskUtils.waitForEvent(iframe, "load");
return iframe.browsingContext;
});
}
add_setup(async function () {
// Enable the service and insert the test rules. We only test
// MODE_REJECT_OR_ACCEPT here as the other modes are covered by other tests
// already and hasRuleForBrowsingContextTree mostly shares logic with other
// service getters.
await SpecialPowers.pushPrefEnv({
set: [
[
"cookiebanners.service.mode",
Ci.nsICookieBannerService.MODE_REJECT_OR_ACCEPT,
],
["cookiebanners.listService.testSkipRemoteSettings", true],
["cookiebanners.listService.testRules", JSON.stringify(testRules)],
],
});
// Ensure the test rules have been applied before the first test starts.
Services.cookieBanners.resetRules();
// Visiting sites in this test can set cookies. Clean them up on test exit.
registerCleanupFunction(async () => {
await SiteDataTestUtils.clear();
});
});
add_task(async function test_unsupported() {
let unsupportedURIs = {
"about:preferences": /NS_ERROR_FAILURE/,
"about:blank": false,
};
for (let [key, value] of Object.entries(unsupportedURIs)) {
await BrowserTestUtils.withNewTab(key, async browser => {
if (typeof value == "object") {
// It's an error code.
Assert.throws(
() => {
Services.cookieBanners.hasRuleForBrowsingContextTree(
browser.browsingContext
);
},
value,
`Should throw ${value} for hasRuleForBrowsingContextTree call for '${key}'.`
);
} else {
is(
Services.cookieBanners.hasRuleForBrowsingContextTree(
browser.browsingContext
),
value,
`Should return expected value for hasRuleForBrowsingContextTree for '${key}'`
);
}
});
}
});
add_task(async function test_hasRuleForBCTree() {
info("Test with top level A");
await BrowserTestUtils.withNewTab(TEST_ORIGIN_A, async browser => {
let bcTop = browser.browsingContext;
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should have rule when called with top BC for A"
);
info("inserting frame with TEST_ORIGIN_A");
let bcChildA = await insertIframe(bcTop, TEST_ORIGIN_A);
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should still have rule when called with top BC for A."
);
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcChildA),
"Should not have rule when called with child BC for A, because A has no child click-rule."
);
});
info("Test with top level C");
await BrowserTestUtils.withNewTab(TEST_ORIGIN_C, async browser => {
let bcTop = browser.browsingContext;
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should have no rule when called with top BC for C, because C only has a child click rule."
);
info("inserting frame with TEST_ORIGIN_C");
let bcChildC = await insertIframe(bcTop, TEST_ORIGIN_C);
info("inserting unrelated frames");
await insertIframe(bcTop, "https://itisatracker.org");
await insertIframe(bcChildC, "https://itisatracker.org");
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should have rule when called with top BC for C, because frame C has a child click rule."
);
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcChildC),
"Should have rule when called with child BC for C, because it has a child click rule."
);
});
info("Test with unrelated top level");
await BrowserTestUtils.withNewTab("http://mochi.test:8888", async browser => {
let bcTop = browser.browsingContext;
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should not have rule for unrelated site."
);
info("inserting frame with TEST_ORIGIN_A");
let bcChildA = await insertIframe(bcTop, TEST_ORIGIN_A);
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should still have no rule when called with top BC for A, because click rule for A only applies top-level."
);
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcChildA),
"Should have no rule when called with child BC for A."
);
info("inserting frame with TEST_ORIGIN_B");
let bcChildB = await insertIframe(bcTop, TEST_ORIGIN_B);
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should still have no rule when called with top BC for A, because cookie rule for B only applies top-level."
);
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcChildA),
"Should have no rule when called with child BC for A."
);
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcChildB),
"Should have no rule when called with child BC for B."
);
info("inserting nested frame with TEST_ORIGIN_C");
let bcChildC = await insertIframe(bcChildB, TEST_ORIGIN_C);
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should have rule when called with top level BC because rule for nested iframe C applies."
);
ok(
!Services.cookieBanners.hasRuleForBrowsingContextTree(bcChildA),
"Should have no rule when called with child BC for A."
);
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcChildB),
"Should have rule when called with child BC for B, because C rule for nested iframe C applies."
);
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcChildC),
"Should have rule when called with child BC for C, because C rule for nested iframe C applies."
);
});
});
/**
* Tests that domain prefs are not considered when evaluating whether the
* service has an applicable rule for the given BrowsingContext.
*/
add_task(async function test_hasRuleForBCTree_ignoreDomainPrefs() {
info("Test with top level A");
await BrowserTestUtils.withNewTab(TEST_ORIGIN_A, async browser => {
let bcTop = browser.browsingContext;
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should have rule when called with top BC for A"
);
// Disable for current site per domain pref.
Services.cookieBanners.setDomainPref(
browser.currentURI,
Ci.nsICookieBannerService.MODE_DISABLED,
false
);
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should have rule when called with top BC for A, even if mechanism is disabled for A."
);
// Change mode via domain pref.
Services.cookieBanners.setDomainPref(
browser.currentURI,
Ci.nsICookieBannerService.MODE_REJECT,
false
);
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should still have rule when called with top BC for A, even with custom mode for A"
);
// Cleanup.
Services.cookieBanners.removeAllDomainPrefs(false);
});
info("Test with top level B");
await BrowserTestUtils.withNewTab(TEST_ORIGIN_B, async browser => {
let bcTop = browser.browsingContext;
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should have rule when called with top BC for B"
);
// Change mode via domain pref.
Services.cookieBanners.setDomainPref(
browser.currentURI,
Ci.nsICookieBannerService.MODE_REJECT,
false
);
// Rule for B has no opt-out option. Since the mode is overridden to
// MODE_REJECT for B we don't have any applicable rule for it. This should
// however not be considered for the hasRule getter, it should ignore
// per-domain preferences and evaluate based on the global service mode
// instead.
ok(
Services.cookieBanners.hasRuleForBrowsingContextTree(bcTop),
"Should still have rule when called with top BC for B, even with custom mode for B"
);
// Cleanup.
Services.cookieBanners.removeAllDomainPrefs(false);
});
});