summaryrefslogtreecommitdiffstats
path: root/toolkit/components/url-classifier/tests/mochitest/features.js
diff options
context:
space:
mode:
Diffstat (limited to 'toolkit/components/url-classifier/tests/mochitest/features.js')
-rw-r--r--toolkit/components/url-classifier/tests/mochitest/features.js290
1 files changed, 290 insertions, 0 deletions
diff --git a/toolkit/components/url-classifier/tests/mochitest/features.js b/toolkit/components/url-classifier/tests/mochitest/features.js
new file mode 100644
index 0000000000..03060d3bc6
--- /dev/null
+++ b/toolkit/components/url-classifier/tests/mochitest/features.js
@@ -0,0 +1,290 @@
+var tests = [
+ // Config is an array with 4 elements:
+ // - annotation blocklist
+ // - annotation entitylist
+ // - tracking blocklist
+ // - tracking entitylist
+
+ // All disabled.
+ {
+ config: [false, false, false, false],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+
+ // Just entitylisted.
+ {
+ config: [false, false, false, true],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+
+ // Just blocklisted.
+ {
+ config: [false, false, true, false],
+ loadExpected: false,
+ annotationExpected: false,
+ },
+
+ // entitylist + blocklist => entitylist wins
+ {
+ config: [false, false, true, true],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+
+ // just annotated in entitylist.
+ {
+ config: [false, true, false, false],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+
+ // TP and annotation entitylisted.
+ {
+ config: [false, true, false, true],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+
+ // Annotation entitylisted, but TP blocklisted.
+ {
+ config: [false, true, true, false],
+ loadExpected: false,
+ annotationExpected: false,
+ },
+
+ // Annotation entitylisted. TP blocklisted and entitylisted: entitylist wins.
+ {
+ config: [false, true, true, true],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+
+ // Just blocklist annotated.
+ {
+ config: [true, false, false, false],
+ loadExpected: true,
+ annotationExpected: true,
+ },
+
+ // annotated but TP entitylisted.
+ {
+ config: [true, false, false, true],
+ loadExpected: true,
+ annotationExpected: true,
+ },
+
+ // annotated and blocklisted.
+ {
+ config: [true, false, true, false],
+ loadExpected: false,
+ annotationExpected: false,
+ },
+
+ // annotated, TP blocklisted and entitylisted: entitylist wins.
+ {
+ config: [true, false, true, true],
+ loadExpected: true,
+ annotationExpected: true,
+ },
+
+ // annotated in white and blocklist.
+ {
+ config: [true, true, false, false],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+
+ // annotated in white and blocklist. TP Whiteslited
+ {
+ config: [true, true, false, true],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+
+ // everywhere. TP entitylist wins.
+ {
+ config: [true, true, true, true],
+ loadExpected: true,
+ annotationExpected: false,
+ },
+];
+
+function prefBlacklistValue(value) {
+ return value ? "example.com" : "";
+}
+
+function prefWhitelistValue(value) {
+ return value ? "mochi.test,mochi.xorigin-test" : "";
+}
+
+async function runTest(test, expectedFlag, expectedTrackingResource, prefs) {
+ let config = [
+ [
+ "urlclassifier.trackingAnnotationTable.testEntries",
+ prefBlacklistValue(test.config[0]),
+ ],
+ [
+ "urlclassifier.features.fingerprinting.annotate.blacklistHosts",
+ prefBlacklistValue(test.config[0]),
+ ],
+ [
+ "urlclassifier.features.cryptomining.annotate.blacklistHosts",
+ prefBlacklistValue(test.config[0]),
+ ],
+ [
+ "urlclassifier.features.socialtracking.annotate.blacklistHosts",
+ prefBlacklistValue(test.config[0]),
+ ],
+
+ [
+ "urlclassifier.trackingAnnotationWhitelistTable.testEntries",
+ prefWhitelistValue(test.config[1]),
+ ],
+ [
+ "urlclassifier.features.fingerprinting.annotate.whitelistHosts",
+ prefWhitelistValue(test.config[1]),
+ ],
+ [
+ "urlclassifier.features.cryptomining.annotate.whitelistHosts",
+ prefWhitelistValue(test.config[1]),
+ ],
+ [
+ "urlclassifier.features.socialtracking.annotate.whitelistHosts",
+ prefWhitelistValue(test.config[1]),
+ ],
+
+ [
+ "urlclassifier.trackingTable.testEntries",
+ prefBlacklistValue(test.config[2]),
+ ],
+ [
+ "urlclassifier.features.fingerprinting.blacklistHosts",
+ prefBlacklistValue(test.config[2]),
+ ],
+ [
+ "urlclassifier.features.cryptomining.blacklistHosts",
+ prefBlacklistValue(test.config[2]),
+ ],
+ [
+ "urlclassifier.features.socialtracking.blacklistHosts",
+ prefBlacklistValue(test.config[2]),
+ ],
+
+ [
+ "urlclassifier.trackingWhitelistTable.testEntries",
+ prefWhitelistValue(test.config[3]),
+ ],
+ [
+ "urlclassifier.features.fingerprinting.whitelistHosts",
+ prefWhitelistValue(test.config[3]),
+ ],
+ [
+ "urlclassifier.features.cryptomining.whitelistHosts",
+ prefWhitelistValue(test.config[3]),
+ ],
+ [
+ "urlclassifier.features.socialtracking.whitelistHosts",
+ prefWhitelistValue(test.config[3]),
+ ],
+ ];
+
+ info("Testing: " + JSON.stringify(config) + "\n");
+
+ await SpecialPowers.pushPrefEnv({ set: config.concat(prefs) });
+
+ // This promise will be resolved when the chromeScript knows if the channel
+ // is annotated or not.
+ let annotationPromise;
+ if (test.loadExpected) {
+ info("We want to have annotation information");
+ annotationPromise = new Promise(resolve => {
+ chromeScript.addMessageListener(
+ "last-channel-flags",
+ data => resolve(data),
+ { once: true }
+ );
+ });
+ }
+
+ // Let's load a script with a random query string to avoid network cache.
+ // Using a script as the fingerprinting feature does not block display content
+ let result = await new Promise(resolve => {
+ let script = document.createElement("script");
+ script.setAttribute(
+ "src",
+ "http://example.com/tests/toolkit/components/url-classifier/tests/mochitest/evil.js?" +
+ Math.random()
+ );
+ script.onload = _ => resolve(true);
+ script.onerror = _ => resolve(false);
+ document.body.appendChild(script);
+ });
+
+ is(result, test.loadExpected, "The loading happened correctly");
+
+ if (annotationPromise) {
+ let data = await annotationPromise;
+ is(
+ !!data.classificationFlags,
+ test.annotationExpected,
+ "The annotation happened correctly"
+ );
+ if (test.annotationExpected) {
+ is(data.classificationFlags, expectedFlag, "Correct flag");
+ is(
+ data.isThirdPartyTrackingResource,
+ expectedTrackingResource,
+ "Tracking resource flag matches"
+ );
+ }
+ }
+}
+
+var chromeScript;
+
+function runTests(flag, prefs, trackingResource) {
+ chromeScript = SpecialPowers.loadChromeScript(_ => {
+ /* eslint-env mozilla/chrome-script */
+ function onExamResp(subject, topic, data) {
+ let channel = subject.QueryInterface(Ci.nsIHttpChannel);
+ let classifiedChannel = subject.QueryInterface(Ci.nsIClassifiedChannel);
+ if (
+ !channel ||
+ !classifiedChannel ||
+ !channel.URI.spec.startsWith(
+ "http://example.com/tests/toolkit/components/url-classifier/tests/mochitest/evil.js"
+ )
+ ) {
+ return;
+ }
+
+ sendAsyncMessage("last-channel-flags", {
+ classificationFlags: classifiedChannel.classificationFlags,
+ isThirdPartyTrackingResource: classifiedChannel.isThirdPartyTrackingResource(),
+ });
+ }
+
+ addMessageListener("done", __ => {
+ Services.obs.removeObserver(onExamResp, "http-on-examine-response");
+ });
+
+ Services.obs.addObserver(onExamResp, "http-on-examine-response");
+
+ sendAsyncMessage("start-test");
+ });
+
+ chromeScript.addMessageListener(
+ "start-test",
+ async _ => {
+ for (let test in tests) {
+ await runTest(tests[test], flag, trackingResource, prefs);
+ }
+
+ chromeScript.sendAsyncMessage("done");
+ SimpleTest.finish();
+ },
+ { once: true }
+ );
+}