gecko/browser/devtools/shared/test/head.js

149 lines
4.5 KiB
JavaScript

/* 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/. */
let {devtools} = Cu.import("resource://gre/modules/devtools/Loader.jsm", {});
let {console} = Cu.import("resource://gre/modules/devtools/Console.jsm", {});
let TargetFactory = devtools.TargetFactory;
gDevTools.testing = true;
SimpleTest.registerCleanupFunction(() => {
gDevTools.testing = false;
});
const TEST_URI_ROOT = "http://example.com/browser/browser/devtools/shared/test/";
/**
* Open a new tab at a URL and call a callback on load
*/
function addTab(aURL, aCallback)
{
waitForExplicitFinish();
gBrowser.selectedTab = gBrowser.addTab();
content.location = aURL;
let tab = gBrowser.selectedTab;
let browser = gBrowser.getBrowserForTab(tab);
function onTabLoad() {
browser.removeEventListener("load", onTabLoad, true);
aCallback(browser, tab, browser.contentDocument);
}
browser.addEventListener("load", onTabLoad, true);
}
function promiseTab(aURL) {
let deferred = Promise.defer();
addTab(aURL, deferred.resolve);
return deferred.promise;
}
registerCleanupFunction(function tearDown() {
while (gBrowser.tabs.length > 1) {
gBrowser.removeCurrentTab();
}
console = undefined;
});
function catchFail(func) {
return function() {
try {
return func.apply(null, arguments);
}
catch (ex) {
ok(false, ex);
console.error(ex);
finish();
throw ex;
}
};
}
/**
* Polls a given function waiting for the given value.
*
* @param object aOptions
* Options object with the following properties:
* - validator
* A validator function that should return the expected value. This is
* called every few milliseconds to check if the result is the expected
* one. When the returned result is the expected one, then the |success|
* function is called and polling stops. If |validator| never returns
* the expected value, then polling timeouts after several tries and
* a failure is recorded - the given |failure| function is invoked.
* - success
* A function called when the validator function returns the expected
* value.
* - failure
* A function called if the validator function timeouts - fails to return
* the expected value in the given time.
* - name
* Name of test. This is used to generate the success and failure
* messages.
* - timeout
* Timeout for validator function, in milliseconds. Default is 5000 ms.
* - value
* The expected value. If this option is omitted then the |validator|
* function must return a trueish value.
* Each of the provided callback functions will receive two arguments:
* the |aOptions| object and the last value returned by |validator|.
*/
function waitForValue(aOptions)
{
let start = Date.now();
let timeout = aOptions.timeout || 5000;
let lastValue;
function wait(validatorFn, successFn, failureFn)
{
if ((Date.now() - start) > timeout) {
// Log the failure.
ok(false, "Timed out while waiting for: " + aOptions.name);
let expected = "value" in aOptions ?
"'" + aOptions.value + "'" :
"a trueish value";
info("timeout info :: got '" + lastValue + "', expected " + expected);
failureFn(aOptions, lastValue);
return;
}
lastValue = validatorFn(aOptions, lastValue);
let successful = "value" in aOptions ?
lastValue == aOptions.value :
lastValue;
if (successful) {
ok(true, aOptions.name);
successFn(aOptions, lastValue);
}
else {
setTimeout(function() wait(validatorFn, successFn, failureFn), 100);
}
}
wait(aOptions.validator, aOptions.success, aOptions.failure);
}
function oneTimeObserve(name, callback) {
var func = function() {
Services.obs.removeObserver(func, name);
callback();
};
Services.obs.addObserver(func, name, false);
}
function* createHost(type = "bottom", src = "data:text/html;charset=utf-8,") {
let host = new Hosts[type](gBrowser.selectedTab);
let iframe = yield host.create();
let loaded = Promise.defer();
let domHelper = new DOMHelpers(iframe.contentWindow);
iframe.setAttribute("src", src);
domHelper.onceDOMReady(loaded.resolve);
yield loaded.promise;
return [host, iframe.contentWindow, iframe.contentDocument];
}