tor-browser

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

browser_browser_toolbox_evaluation_context.js (6693B)


      1 /* Any copyright is dedicated to the Public Domain.
      2   http://creativecommons.org/publicdomain/zero/1.0/ */
      3 
      4 // There are shutdown issues for which multiple rejections are left uncaught.
      5 // See bug 1018184 for resolving these issues.
      6 const { PromiseTestUtils } = ChromeUtils.importESModule(
      7  "resource://testing-common/PromiseTestUtils.sys.mjs"
      8 );
      9 PromiseTestUtils.allowMatchingRejectionsGlobally(/File closed/);
     10 
     11 // On debug test machine, it takes about 50s to run the test.
     12 requestLongerTimeout(4);
     13 
     14 // This test is used to test fission-like features via the Browser Toolbox:
     15 // - the evaluation context selector in the console show the right targets
     16 // - the iframe dropdown also show the right targets
     17 // - both are updated accordingly when toggle to parent-process only scope
     18 
     19 add_task(async function () {
     20  // Forces the Browser Toolbox to open on the console by default
     21  await pushPref("devtools.browsertoolbox.panel", "webconsole");
     22  // Enable Multiprocess Browser Toolbox
     23  await pushPref("devtools.browsertoolbox.scope", "everything");
     24 
     25  // Open the test *before* opening the Browser toolbox in order to have the right target title.
     26  // Once created, the target won't update its title, and so would be "New Tab", instead of "Test tab"
     27  const tab = await addTab(
     28    "https://example.com/document-builder.sjs?html=<html><title>Test tab</title></html>"
     29  );
     30 
     31  const ToolboxTask = await initBrowserToolboxTask();
     32 
     33  await ToolboxTask.importFunctions({
     34    waitUntil,
     35    getContextLabels,
     36    getFramesLabels,
     37  });
     38 
     39  const tabProcessID =
     40    tab.linkedBrowser.browsingContext.currentWindowGlobal.osPid;
     41 
     42  const decodedTabURI = decodeURI(tab.linkedBrowser.currentURI.spec);
     43 
     44  await ToolboxTask.spawn(
     45    [tabProcessID, decodedTabURI],
     46    async (processID, tabURI) => {
     47      /* global gToolbox */
     48      const { hud } = await gToolbox.getPanel("webconsole");
     49 
     50      const evaluationContextSelectorButton = hud.ui.outputNode.querySelector(
     51        ".webconsole-evaluation-selector-button"
     52      );
     53 
     54      is(
     55        !!evaluationContextSelectorButton,
     56        true,
     57        "The evaluation context selector is visible"
     58      );
     59      is(
     60        evaluationContextSelectorButton.innerText,
     61        "Top",
     62        "The button has the expected 'Top' text"
     63      );
     64 
     65      const labelTexts = getContextLabels(gToolbox);
     66 
     67      const expectedTitle = `(pid ${processID}) https://example.com`;
     68      ok(
     69        labelTexts.includes(expectedTitle),
     70        `${processID} content process visible in the execution context (${labelTexts})`
     71      );
     72 
     73      ok(
     74        labelTexts.includes(`Test tab`),
     75        `Test tab is visible in the execution context (${labelTexts})`
     76      );
     77 
     78      // Also assert the behavior of the iframe dropdown and the mode selector
     79      info("Check the iframe dropdown, start by opening it");
     80      const btn = gToolbox.doc.getElementById("command-button-frames");
     81      btn.click();
     82 
     83      const panel = gToolbox.doc.getElementById("command-button-frames-panel");
     84      ok(panel, "popup panel has created.");
     85      await waitUntil(
     86        () => panel.classList.contains("tooltip-visible"),
     87        "Wait for the menu to be displayed"
     88      );
     89 
     90      is(
     91        getFramesLabels(gToolbox)[0],
     92        "chrome://browser/content/browser.xhtml",
     93        "The iframe dropdown lists first browser.xhtml, running in the parent process"
     94      );
     95      ok(
     96        getFramesLabels(gToolbox).includes(tabURI),
     97        "The iframe dropdown lists the tab document, running in the content process"
     98      );
     99 
    100      // Click on top frame to hide the iframe picker, so clicks on other elements can be registered.
    101      gToolbox.doc.querySelector("#toolbox-frame-menu .command").click();
    102 
    103      await waitUntil(
    104        () => !panel.classList.contains("tooltip-visible"),
    105        "Wait for the menu to be hidden"
    106      );
    107 
    108      info("Check that the ChromeDebugToolbar is displayed");
    109      const chromeDebugToolbar = gToolbox.doc.querySelector(
    110        ".chrome-debug-toolbar"
    111      );
    112      ok(!!chromeDebugToolbar, "ChromeDebugToolbar is displayed");
    113      const chromeDebugToolbarScopeInputs = Array.from(
    114        chromeDebugToolbar.querySelectorAll(`[name="chrome-debug-mode"]`)
    115      );
    116      is(
    117        chromeDebugToolbarScopeInputs.length,
    118        2,
    119        "There are 2 mode inputs in the chromeDebugToolbar"
    120      );
    121      const [
    122        chromeDebugToolbarParentProcessModeInput,
    123        chromeDebugToolbarMultiprocessModeInput,
    124      ] = chromeDebugToolbarScopeInputs;
    125      is(
    126        chromeDebugToolbarParentProcessModeInput.value,
    127        "parent-process",
    128        "Got expected value for the first input"
    129      );
    130      is(
    131        chromeDebugToolbarMultiprocessModeInput.value,
    132        "everything",
    133        "Got expected value for the second input"
    134      );
    135      ok(
    136        chromeDebugToolbarMultiprocessModeInput.checked,
    137        "The multiprocess mode is selected"
    138      );
    139 
    140      info(
    141        "Click on the parent-process input and check that it restricts the targets"
    142      );
    143      chromeDebugToolbarParentProcessModeInput.click();
    144      info("Wait for the iframe dropdown to hide the tab target");
    145      await waitUntil(() => {
    146        return !getFramesLabels(gToolbox).includes(tabURI);
    147      });
    148 
    149      info("Wait for the context selector to hide the tab context");
    150      await waitUntil(() => {
    151        return !getContextLabels(gToolbox).includes(`Test tab`);
    152      });
    153 
    154      ok(
    155        !chromeDebugToolbarMultiprocessModeInput.checked,
    156        "Now, the multiprocess mode is disabled…"
    157      );
    158      ok(
    159        chromeDebugToolbarParentProcessModeInput.checked,
    160        "…and the parent process mode is enabled"
    161      );
    162 
    163      info("Switch back to multiprocess mode");
    164      chromeDebugToolbarMultiprocessModeInput.click();
    165 
    166      info("Wait for the iframe dropdown to show again the tab target");
    167      await waitUntil(() => {
    168        return getFramesLabels(gToolbox).includes(tabURI);
    169      });
    170 
    171      info("Wait for the context selector to show again the tab context");
    172      await waitUntil(() => {
    173        return getContextLabels(gToolbox).includes(`Test tab`);
    174      });
    175    }
    176  );
    177 
    178  await ToolboxTask.destroy();
    179 });
    180 
    181 function getContextLabels(toolbox) {
    182  // Note that the context menu is in the top level chrome document (toolbox.xhtml)
    183  // instead of webconsole.xhtml.
    184  const labels = toolbox.doc.querySelectorAll(
    185    "#webconsole-console-evaluation-context-selector-menu-list li .label"
    186  );
    187  return Array.from(labels).map(item => item.textContent);
    188 }
    189 
    190 function getFramesLabels(toolbox) {
    191  return Array.from(
    192    toolbox.doc.querySelectorAll("#toolbox-frame-menu .command .label")
    193  ).map(el => el.textContent);
    194 }