tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

test_webextension_descriptor.js (5038B)


      1 /* Any copyright is dedicated to the Public Domain.
      2 http://creativecommons.org/publicdomain/zero/1.0/ */
      3 
      4 "use strict";
      5 
      6 const { ExtensionTestUtils } = ChromeUtils.importESModule(
      7  "resource://testing-common/ExtensionXPCShellUtils.sys.mjs"
      8 );
      9 
     10 const DistinctDevToolsServer = getDistinctDevToolsServer();
     11 ExtensionTestUtils.init(this);
     12 
     13 add_setup(async () => {
     14  Services.prefs.setBoolPref("extensions.blocklist.enabled", false);
     15  await startupAddonsManager();
     16 
     17  // We intentionally generate install-time manifest warnings, so don't trigger
     18  // the special test-only mode of converting them to errors.
     19  Services.prefs.setBoolPref(
     20    "extensions.webextensions.warnings-as-errors",
     21    false
     22  );
     23 
     24  DistinctDevToolsServer.init();
     25  DistinctDevToolsServer.registerAllActors();
     26 });
     27 
     28 // Verifies:
     29 // - listAddons
     30 // - WebExtensionDescriptorActor output
     31 // Also a regression test for bug 1837185, that AddonManager.sys.mjs and
     32 // ExtensionParent.sys.mjs are imported from the correct loader.
     33 add_task(async function test_listAddons_and_WebExtensionDescriptor() {
     34  const transport = DistinctDevToolsServer.connectPipe();
     35  const client = new DevToolsClient(transport);
     36  await client.connect();
     37 
     38  const getRootResponse = await client.mainRoot.getRoot();
     39 
     40  ok(getRootResponse, "received a response after calling RootActor::getRoot");
     41  ok(getRootResponse.addonsActor, "getRoot returned an addonsActor id");
     42 
     43  const ADDON_ID = "with@warning";
     44  const extension = ExtensionTestUtils.loadExtension({
     45    useAddonManager: "permanent",
     46    manifest: {
     47      name: "DummyExtensionWithUnknownManifestKey",
     48      unknown_manifest_key: "this is an unknown manifest key",
     49      browser_specific_settings: { gecko: { id: ADDON_ID } },
     50    },
     51    background: `browser.test.sendMessage("background_started");`,
     52  });
     53  await extension.startup();
     54  await extension.awaitMessage("background_started");
     55 
     56  // listAddons: addon after new install.
     57  {
     58    const listAddonsResponse = await client.mainRoot.listAddons();
     59    const addon = listAddonsResponse.find(a => a.id === ADDON_ID);
     60    ok(addon, "listAddons() returns a list of add-ons including with@warning");
     61 
     62    // Inspect all raw properties of the message, to make sure that we always
     63    // have full coverage for all current and future properties.
     64    const { actor, url, warnings, ...addonMinusSomeKeys } = addon._form;
     65    const actorPattern = /^server\d+\.conn\d+\.webExtensionDescriptor\d+$/;
     66    ok(actorPattern.test(actor), `actor is webExtensionDescriptor: ${actor}`);
     67    // We don't care about the exact path, just a dummy check:
     68    ok(url.endsWith(".xpi"), `url is path to the xpi file`);
     69 
     70    deepEqual(
     71      warnings,
     72      [
     73        "Reading manifest: Warning processing unknown_manifest_key: An unexpected property was found in the WebExtension manifest.",
     74      ],
     75      "Can retrieve warnings."
     76    );
     77 
     78    // Verify that the other remaining keys have a meaningful value.
     79    // This is mainly to have some form of verification on the value of the
     80    // properties. If this check ever fails, double-check whether the proposed
     81    // change makes sense and if it does just update the test expectation here.
     82    deepEqual(
     83      addonMinusSomeKeys,
     84      {
     85        backgroundScriptStatus: undefined,
     86        debuggable: true,
     87        hidden: false,
     88        iconDataURL: undefined,
     89        iconURL: null,
     90        id: ADDON_ID,
     91        isSystem: false,
     92        isWebExtension: true,
     93        manifestURL: `moz-extension://${extension.uuid}/manifest.json`,
     94        name: "DummyExtensionWithUnknownManifestKey",
     95        persistentBackgroundScript: true,
     96        temporarilyInstalled: false,
     97        traits: {
     98          supportsReloadDescriptor: true,
     99          watcher: true,
    100        },
    101      },
    102      "WebExtensionDescriptorActor content matches the add-on"
    103    );
    104  }
    105 
    106  await extension.upgrade({
    107    manifest: {
    108      name: "Updated_extension",
    109      new_unknown_manifest_key: "different warning than before",
    110      browser_specific_settings: { gecko: { id: ADDON_ID } },
    111    },
    112    background: `browser.test.sendMessage("updated_done");`,
    113  });
    114  await extension.awaitMessage("updated_done");
    115 
    116  // listAddons: addon after update.
    117  {
    118    const listAddonsResponse = await client.mainRoot.listAddons();
    119    const addon = listAddonsResponse.find(a => a.id === ADDON_ID);
    120    ok(addon, "listAddons() should still list the add-on after update");
    121    equal(addon.name, "Updated_extension", "Got updated name");
    122    deepEqual(
    123      addon.warnings,
    124      [
    125        "Reading manifest: Warning processing new_unknown_manifest_key: An unexpected property was found in the WebExtension manifest.",
    126      ],
    127      "Can retrieve new warnings for updated add-on."
    128    );
    129  }
    130 
    131  await extension.unload();
    132 
    133  // listAddons: addon after removal - gone.
    134  {
    135    const listAddonsResponse = await client.mainRoot.listAddons();
    136    const addon = listAddonsResponse.find(a => a.id === ADDON_ID);
    137    deepEqual(addon, null, "Add-on should be gone after removal");
    138  }
    139 
    140  await client.close();
    141 });