Bug 1322383 - getCurrentWindow() has to only return the currently selected window. r=ato+446296,maja_zf
☠☠ backed out by c4bbcb3d7737 ☠ ☠
authorHenrik Skupin <mail@hskupin.info>
Tue, 28 Feb 2017 12:19:29 +0100
changeset 394338 890130185456c469b38b7ef0973a8b0c5b07bb86
parent 394337 74b0c928a23e261b8976fbbdbcf8e1ab49c57a7c
child 394339 20f6edaec61ee22350354dbed3f684802fdcee3b
push id1468
push userasasaki@mozilla.com
push dateMon, 05 Jun 2017 19:31:07 +0000
treeherdermozilla-release@0641fc6ee9d1 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersato
bugs1322383, 446296
milestone54.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1322383 - getCurrentWindow() has to only return the currently selected window. r=ato+446296,maja_zf Given that this method will be used in each command for checks of a valid window, we have to return the currently active window. It means the window mediator should only be used during setting up the session to find the first browser window. At the same time the code in this method is getting split-up for chrome and content scopes. MozReview-Commit-ID: KyzxYk63RgA
testing/marionette/driver.js
testing/marionette/harness/marionette_harness/tests/unit/test_window_handles_content.py
testing/marionette/harness/marionette_harness/tests/unit/test_window_management.py
testing/marionette/harness/marionette_harness/www/blob_download.html
--- a/testing/marionette/driver.js
+++ b/testing/marionette/driver.js
@@ -305,43 +305,61 @@ GeckoDriver.prototype.sendTargettedAsync
 
       default:
         throw new WebDriverError(e);
     }
   }
 };
 
 /**
- * Gets the current active window.
+ * Get the session's current top-level browsing context.
+ *
+ * It will return the outer {@ChromeWindow} previously selected by window handle
+ * through {@code #switchToWindow}, or the first window that was registered.
  *
  * @param {Context=} forcedContext
- *     Optional name of the context to use for the checks.
- *     Defaults to the current context.
+ *     Optional name of the context to use for finding the window. It will be required
+ *     if a command always needs a specific context, whether which context is
+ *     currently set. Defaults to the current context.
  *
- * @return {nsIDOMWindow}
+ * @return {ChromeWindow}
+ *     The current top-level browsing context.
  */
 GeckoDriver.prototype.getCurrentWindow = function (forcedContext = undefined) {
   let context = typeof forcedContext == "undefined" ? this.context : forcedContext;
   let win = null;
 
-  if (this.curFrame === null) {
-    if (this.curBrowser === null) {
-      let typ = (context === Context.CONTENT) ? "navigator:browser" : null;
-      win = Services.wm.getMostRecentWindow(typ);
-    } else {
-      if (context === Context.CHROME) {
+  switch (context) {
+    case Context.CHROME:
+      if (this.curFrame !== null) {
+        win = this.curFrame;
+
+      } else if (this.curBrowser !== null) {
         win = this.curBrowser.window;
-      } else {
-        if (this.curBrowser.tab && browser.getBrowserForTab(this.curBrowser.tab)) {
+      }
+
+      break;
+
+    case Context.CONTENT:
+      if (this.curFrame !== null) {
+        win = this.curFrame;
+
+      } else if (this.curBrowser !== null) {
+        if (browser.getTabBrowser(this.curBrowser.window)) {
+          // For browser windows we have to check if the current tab still exists.
+          if (this.curBrowser.tab && browser.getBrowserForTab(this.curBrowser.tab)) {
+            win = this.curBrowser.window;
+          }
+        } else {
+          // For non-browser windows just return the window.
           win = this.curBrowser.window;
         }
       }
-    }
-  } else {
-    win = this.curFrame;
+
+      break;
   }
 
   return win;
 };
 
 GeckoDriver.prototype.addFrameCloseListener = function (action) {
   let win = this.getCurrentWindow();
   this.mozBrowserClose = e => {
@@ -600,17 +618,17 @@ GeckoDriver.prototype.newSession = funct
   if (this.a11yChecks && accessibility.service) {
     logger.info("Preemptively starting accessibility service in Chrome");
   }
 
   let registerBrowsers = this.registerPromise();
   let browserListening = this.listeningPromise();
 
   let waitForWindow = function() {
-    let win = this.getCurrentWindow();
+    let win = Services.wm.getMostRecentWindow("navigator:browser");
     if (!win) {
       // if the window isn't even created, just poll wait for it
       let checkTimer = Cc["@mozilla.org/timer;1"].createInstance(Ci.nsITimer);
       checkTimer.initWithCallback(waitForWindow.bind(this), 100,
           Ci.nsITimer.TYPE_ONE_SHOT);
     } else if (win.document.readyState != "complete") {
       // otherwise, wait for it to be fully loaded before proceeding
       let listener = ev => {
@@ -620,20 +638,18 @@ GeckoDriver.prototype.newSession = funct
           return;
         }
         win.removeEventListener("load", listener);
         waitForWindow.call(this);
       };
       win.addEventListener("load", listener, true);
     } else {
       let clickToStart = Preferences.get(CLICK_TO_START_PREF);
-      if (clickToStart && (this.appName != "B2G")) {
-        let pService = Cc["@mozilla.org/embedcomp/prompt-service;1"]
-            .getService(Ci.nsIPromptService);
-        pService.alert(win, "", "Click to start execution of marionette tests");
+      if (clickToStart) {
+        Services.prompt.alert(win, "", "Click to start execution of marionette tests");
       }
       this.startBrowser(win, true);
     }
   };
 
   let runSessionStart = function() {
     if (!Preferences.get(CONTENT_LISTENER_PREF)) {
       waitForWindow.call(this);
--- a/testing/marionette/harness/marionette_harness/tests/unit/test_window_handles_content.py
+++ b/testing/marionette/harness/marionette_harness/tests/unit/test_window_handles_content.py
@@ -1,15 +1,15 @@
 # This Source Code Form is subject to the terms of the Mozilla Public
 # License, v. 2.0. If a copy of the MPL was not distributed with this
 # file, You can obtain one at http://mozilla.org/MPL/2.0/.
 
 from marionette_driver import By, Wait
 
-from marionette_harness import MarionetteTestCase, WindowManagerMixin
+from marionette_harness import MarionetteTestCase, skip_if_mobile, WindowManagerMixin
 
 
 class TestWindowHandles(WindowManagerMixin, MarionetteTestCase):
 
     def setUp(self):
         super(TestWindowHandles, self).setUp()
 
         self.empty_page = self.marionette.absolute_url("empty.html")
@@ -42,17 +42,17 @@ class TestWindowHandles(WindowManagerMix
 
         self.marionette.switch_to_window(new_tab)
         self.marionette.close()
         self.assertEqual(len(self.marionette.window_handles), len(self.start_tabs))
 
         self.marionette.switch_to_window(self.start_tab)
         self.assertEqual(self.marionette.current_window_handle, self.start_tab)
 
-    def test_window_handles_after_opening_new_window(self):
+    def test_window_handles_after_opening_new_browser_window(self):
         def open_with_link():
             link = self.marionette.find_element(By.ID, "new-window")
             link.click()
 
         # We open a new window but are actually interested in the new tab
         new_tab = self.open_tab(trigger=open_with_link)
         self.assertEqual(len(self.marionette.window_handles), len(self.start_tabs) + 1)
         self.assertEqual(self.marionette.current_window_handle, self.start_tab)
@@ -70,16 +70,38 @@ class TestWindowHandles(WindowManagerMix
         # Close the opened window and carry on in our original tab.
         self.marionette.close()
         self.assertEqual(len(self.marionette.window_handles), len(self.start_tabs))
 
         self.marionette.switch_to_window(self.start_tab)
         self.assertEqual(self.marionette.current_window_handle, self.start_tab)
         self.assertEqual(self.marionette.get_url(), self.test_page)
 
+    @skip_if_mobile("Fennec doesn't support other chrome windows")
+    def test_window_handles_after_opening_new_non_browser_window(self):
+        def open_with_link():
+            self.marionette.navigate(self.marionette.absolute_url("blob_download.html"))
+            link = self.marionette.find_element(By.ID, "blob-download")
+            link.click()
+
+        # We open a new window but are actually interested in the new tab
+        new_tab = self.open_tab(trigger=open_with_link)
+        self.assertEqual(len(self.marionette.window_handles), len(self.start_tabs) + 1)
+        self.assertEqual(self.marionette.current_window_handle, self.start_tab)
+
+        self.marionette.switch_to_window(new_tab)
+        self.assertEqual(self.marionette.current_window_handle, new_tab)
+
+        # Close the opened window and carry on in our original tab.
+        self.marionette.close()
+        self.assertEqual(len(self.marionette.window_handles), len(self.start_tabs))
+
+        self.marionette.switch_to_window(self.start_tab)
+        self.assertEqual(self.marionette.current_window_handle, self.start_tab)
+
     def test_window_handles_after_closing_original_tab(self):
         def open_with_link():
             link = self.marionette.find_element(By.ID, "new-tab")
             link.click()
 
         new_tab = self.open_tab(trigger=open_with_link)
         self.assertEqual(len(self.marionette.window_handles), len(self.start_tabs) + 1)
         self.assertEqual(self.marionette.current_window_handle, self.start_tab)
--- a/testing/marionette/harness/marionette_harness/tests/unit/test_window_management.py
+++ b/testing/marionette/harness/marionette_harness/tests/unit/test_window_management.py
@@ -9,17 +9,17 @@ from marionette_harness import Marionett
 
 
 class TestNoSuchWindowContent(WindowManagerMixin, MarionetteTestCase):
 
     def setUp(self):
         super(TestNoSuchWindowContent, self).setUp()
 
     def tearDown(self):
-        self.close_all_windows()
+        self.close_all_tabs()
         super(TestNoSuchWindowContent, self).tearDown()
 
     @skip_if_mobile("Fennec doesn't support other chrome windows")
     def test_closed_chrome_window(self):
 
         def open_with_link():
             with self.marionette.using_context("content"):
                 test_page = self.marionette.absolute_url("windowHandles.html")
new file mode 100644
--- /dev/null
+++ b/testing/marionette/harness/marionette_harness/www/blob_download.html
@@ -0,0 +1,11 @@
+<!DOCTYPE html>
+
+<a id="blob-download" download="foo.html">Download</a>
+
+<script>
+  const string = "test";
+  const blob = new Blob([string], { type: "text/html" });
+
+  const link = document.getElementById("blob-download");
+  link.href = URL.createObjectURL(blob);
+</script>