Bug 1371733 - Encode currentURL as URL object; r?whimboo
Instead of returning a string representation of the current locaton from
GeckoDriver#currentURL, we encode it as a URL object.
browser.Context#currentURL is also renamed to currentURI to reflect that
it now returns an nsIURI object.
The motivation behind this change is that we need to access a URL's port,
protocol, pathname, and hostname separately.
MozReview-Commit-ID: DM7gkrHhFpb
--- a/testing/marionette/browser.js
+++ b/testing/marionette/browser.js
@@ -11,17 +11,16 @@ Cu.import("chrome://marionette/content/e
Cu.import("chrome://marionette/content/frame.js");
this.EXPORTED_SYMBOLS = ["browser"];
this.browser = {};
const XUL_NS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
-
/**
* Get the <xul:browser> for the specified tab.
*
* @param {<xul:tab>} tab
* The tab whose browser needs to be returned.
*
* @return {<xul:browser>}
* The linked browser for the tab or null if no browser can be found.
@@ -141,27 +140,32 @@ browser.Context = class {
let rv = null;
if (this.tab) {
rv = this.getIdForBrowser(this.contentBrowser);
}
return rv;
}
/**
- * Returns the current URL of the content browser.
- * If no browser is available, null will be returned.
+ * Returns the current URI of the content browser.
+ *
+ * @return {nsIURI}
+ * Read-only property containing the currently loaded URL.
+ *
+ * @throws {NoSuchWindowError}
+ * If the current ChromeWindow does not have a content browser.
*/
- get currentURL() {
+ get currentURI() {
// Bug 1363368 - contentBrowser could be null until we wait for its
// initialization been finished
if (this.contentBrowser) {
- return this.contentBrowser.currentURI.spec;
-
+ return this.contentBrowser.currentURI;
} else {
- throw new NoSuchWindowError("Current window does not have a content browser");
+ throw new NoSuchWindowError(
+ "Current window does not have a content browser");
}
}
/**
* Retrieves the current tabmodal UI object. According to the browser
* associated with the currently selected tab.
*/
getTabModalUI() {
--- a/testing/marionette/driver.js
+++ b/testing/marionette/driver.js
@@ -32,16 +32,18 @@ Cu.import("chrome://marionette/content/i
Cu.import("chrome://marionette/content/l10n.js");
Cu.import("chrome://marionette/content/legacyaction.js");
Cu.import("chrome://marionette/content/logging.js");
Cu.import("chrome://marionette/content/modal.js");
Cu.import("chrome://marionette/content/proxy.js");
Cu.import("chrome://marionette/content/session.js");
Cu.import("chrome://marionette/content/wait.js");
+Cu.importGlobalProperties(["URL"]);
+
this.EXPORTED_SYMBOLS = ["GeckoDriver", "Context"];
var FRAME_SCRIPT = "chrome://marionette/content/listener.js";
const CLICK_TO_START_PREF = "marionette.debugging.clicktostart";
const CONTENT_LISTENER_PREF = "marionette.contentListener";
const XUL_NS = "http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul";
@@ -140,24 +142,32 @@ this.GeckoDriver = function (appName, se
};
Object.defineProperty(GeckoDriver.prototype, "a11yChecks", {
get: function () {
return this.capabilities.get("moz:accessibilityChecks");
}
});
+/**
+ * Returns the current URL of the ChromeWindow or content browser,
+ * depending on context.
+ *
+ * @return {URL}
+ * Read-only property containing the currently loaded URL.
+ */
Object.defineProperty(GeckoDriver.prototype, "currentURL", {
get: function () {
switch (this.context) {
case Context.CHROME:
- return this.getCurrentWindow().location.href;
+ let chromeWin = this.getCurrentWindow();
+ return new URL(chromeWin.location.href);
case Context.CONTENT:
- return this.curBrowser.currentURL;
+ return new URL(this.curBrowser.currentURI.spec);
}
}
});
Object.defineProperty(GeckoDriver.prototype, "proxy", {
get: function () {
return this.capabilities.get("proxy");
}
@@ -968,17 +978,17 @@ GeckoDriver.prototype.get = function* (c
* Top-level browsing context has been discarded.
* @throws {UnexpectedAlertOpenError}
* A modal dialog is open, blocking this operation.
*/
GeckoDriver.prototype.getCurrentUrl = function (cmd) {
assert.window(this.getCurrentWindow());
assert.noUserPrompt(this.dialog);
- return this.currentURL;
+ return this.currentURL.toString();
};
/**
* Gets the current title of the window.
*
* @return {string}
* Document title of the top-level browsing context.
*
@@ -1053,27 +1063,27 @@ GeckoDriver.prototype.goBack = function*
assert.contentBrowser(this.curBrowser);
assert.noUserPrompt(this.dialog);
// If there is no history, just return
if (!this.curBrowser.contentBrowser.webNavigation.canGoBack) {
return;
}
- let currentURL = this.currentURL;
+ let lastURL = this.currentURL;
let goBack = this.listener.goBack({pageTimeout: this.timeouts.pageLoad});
// If a remoteness update interrupts our page load, this will never return
// We need to re-issue this request to correctly poll for readyState and
// send errors.
this.curBrowser.pendingCommands.push(() => {
let parameters = {
// TODO(ato): Bug 1242595
command_id: this.listener.activeMessageId,
- lastSeenURL: currentURL,
+ lastSeenURL: lastURL.toString(),
pageTimeout: this.timeouts.pageLoad,
startTime: new Date().getTime(),
};
this.mm.broadcastAsyncMessage(
"Marionette:waitForPageLoaded" + this.curBrowser.curFrameId,
parameters);
});
@@ -1096,27 +1106,27 @@ GeckoDriver.prototype.goForward = functi
assert.contentBrowser(this.curBrowser);
assert.noUserPrompt(this.dialog);
// If there is no history, just return
if (!this.curBrowser.contentBrowser.webNavigation.canGoForward) {
return;
}
- let currentURL = this.currentURL;
+ let lastURL = this.currentURL;
let goForward = this.listener.goForward({pageTimeout: this.timeouts.pageLoad});
// If a remoteness update interrupts our page load, this will never return
// We need to re-issue this request to correctly poll for readyState and
// send errors.
this.curBrowser.pendingCommands.push(() => {
let parameters = {
// TODO(ato): Bug 1242595
command_id: this.listener.activeMessageId,
- lastSeenURL: currentURL,
+ lastSeenURL: lastURL.toString(),
pageTimeout: this.timeouts.pageLoad,
startTime: new Date().getTime(),
};
this.mm.broadcastAsyncMessage(
"Marionette:waitForPageLoaded" + this.curBrowser.curFrameId,
parameters);
});