Bug 989137 - Part 10: Add a testing-only JSM for common AddonManager operations; r=Unfocused, r=gfritzsche

There is a lot of boilerplate testing code that performs common
AddonManager operations. Some common operations used for testing
Experiments have been refactored into a testing-only JSM that lives as
part of the Add-ons Manager.

--HG--
extra : rebase_source : f18cf54c7af6d390ed4437bd0ed0eb4beea76b0d
This commit is contained in:
Gregory Szorc 2014-04-04 15:58:29 -07:00
parent 5936409941
commit 4df343f2c1
4 changed files with 120 additions and 61 deletions

View File

@ -147,61 +147,6 @@ function loadAddonManager() {
startupManager();
}
// Install addon and return a Promise<boolean> that is
// resolve with true on success, false otherwise.
function installAddon(url, hash) {
let deferred = Promise.defer();
let success = () => deferred.resolve(true);
let fail = () => deferred.resolve(false);
let listener = {
onDownloadCancelled: fail,
onDownloadFailed: fail,
onInstallCancelled: fail,
onInstallFailed: fail,
onInstallEnded: success,
};
let installCallback = install => {
install.addListener(listener);
install.install();
};
AddonManager.getInstallForURL(url, installCallback,
"application/x-xpinstall", hash);
return deferred.promise;
}
// Uninstall addon and return a Promise<boolean> that is
// resolve with true on success, false otherwise.
function uninstallAddon(id) {
let deferred = Promise.defer();
AddonManager.getAddonByID(id, addon => {
if (!addon) {
deferred.resolve(false);
}
let listener = {};
let handler = addon => {
if (addon.id !== id) {
return;
}
AddonManager.removeAddonListener(listener);
deferred.resolve(true);
};
listener.onUninstalled = handler;
listener.onDisabled = handler;
AddonManager.addAddonListener(listener);
addon.uninstall();
});
return deferred.promise;
}
function getExperimentAddons() {
let deferred = Promise.defer();

View File

@ -4,6 +4,8 @@
"use strict";
Cu.import("resource://testing-common/httpd.js");
Cu.import("resource://testing-common/AddonManagerTesting.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "Experiments",
"resource:///modules/experiments/Experiments.jsm");
@ -330,8 +332,7 @@ add_task(function* test_addonAlreadyInstalled() {
// Install conflicting addon.
let installed = yield installAddon(gDataRoot + EXPERIMENT1_XPI_NAME, EXPERIMENT1_XPI_SHA1);
Assert.ok(installed, "Addon should have been installed.");
yield AddonTestUtils.installXPIFromURL(gDataRoot + EXPERIMENT1_XPI_NAME, EXPERIMENT1_XPI_SHA1);
addons = yield getExperimentAddons();
Assert.equal(addons.length, 1, "1 add-on is installed.");
list = yield experiments.getExperiments();
@ -1345,9 +1346,8 @@ add_task(function* test_unexpectedUninstall() {
// Uninstall the addon through the addon manager instead of stopping it through
// the experiments API.
let success = yield uninstallAddon(EXPERIMENT1_ID);
yield AddonTestUtils.uninstallAddonByID(EXPERIMENT1_ID);
yield experiments._mainTask;
Assert.ok(success, "Addon should have been uninstalled.");
yield experiments.notify();
@ -1373,7 +1373,7 @@ add_task(function* testUnknownExperimentsUninstalled() {
// Simulate us not listening.
experiments._stopWatchingAddons();
yield installAddon(gDataRoot + EXPERIMENT1_XPI_NAME, EXPERIMENT1_XPI_SHA1);
yield AddonTestUtils.installXPIFromURL(gDataRoot + EXPERIMENT1_XPI_NAME, EXPERIMENT1_XPI_SHA1);
experiments._startWatchingAddons();
addons = yield getExperimentAddons();
@ -1410,7 +1410,14 @@ add_task(function* testForeignExperimentInstall() {
let addons = yield getExperimentAddons();
Assert.equal(addons.length, 0, "Precondition: No experiment add-ons present.");
yield installAddon(gDataRoot + EXPERIMENT1_XPI_NAME, EXPERIMENT1_XPI_SHA1);
let failed;
try {
yield AddonTestUtils.installXPIFromURL(gDataRoot + EXPERIMENT1_XPI_NAME, EXPERIMENT1_XPI_SHA1);
} catch (ex) {
failed = true;
}
Assert.ok(failed, "Add-on install should not have completed successfully");
addons = yield getExperimentAddons();
Assert.equal(addons.length, 0, "Add-on install should have been cancelled.");

View File

@ -0,0 +1,105 @@
/* 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/. */
// This file is a test-only JSM containing utility methods for
// interacting with the add-ons manager.
"use strict";
this.EXPORTED_SYMBOLS = [
"AddonTestUtils",
];
const {utils: Cu} = Components;
Cu.import("resource://gre/modules/Promise.jsm");
Cu.import("resource://gre/modules/XPCOMUtils.jsm");
XPCOMUtils.defineLazyModuleGetter(this, "AddonManager",
"resource://gre/modules/AddonManager.jsm");
this.AddonTestUtils = {
/**
* Uninstall an add-on that is specified by its ID.
*
* The returned promise resolves on successful uninstall and rejects
* if the add-on is not unknown.
*
* @return Promise<restartRequired>
*/
uninstallAddonByID: function (id) {
let deferred = Promise.defer();
AddonManager.getAddonByID(id, (addon) => {
if (!addon) {
deferred.reject(new Error("Add-on is not known: " + id));
return;
}
let listener = {
onUninstalling: function (addon, needsRestart) {
if (addon.id != id) {
return;
}
if (needsRestart) {
AddonManager.removeAddonListener(listener);
deferred.resolve(true);
}
},
onUninstalled: function (addon) {
if (addon.id != id) {
return;
}
AddonManager.removeAddonListener(listener);
deferred.resolve(false);
},
onOperationCancelled: function (addon) {
if (addon.id != id) {
return;
}
AddonManager.removeAddonListener(listener);
deferred.reject(new Error("Uninstall cancelled."));
},
};
AddonManager.addAddonListener(listener);
addon.uninstall();
});
return deferred.promise;
},
/**
* Install an XPI add-on from a URL.
*
* @return Promise<addon>
*/
installXPIFromURL: function (url, hash, name, iconURL, version) {
let deferred = Promise.defer();
AddonManager.getInstallForURL(url, (install) => {
let fail = () => { deferred.reject(new Error("Add-on install failed.")) };
let listener = {
onDownloadCancelled: fail,
onDownloadFailed: fail,
onInstallCancelled: fail,
onInstallFailed: fail,
onInstallEnded: function (install, addon) {
deferred.resolve(addon);
},
};
install.addListener(listener);
install.install();
}, "application/x-xpinstall", hash, name, iconURL, version);
return deferred.promise;
},
};

View File

@ -2,6 +2,8 @@
# 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/.
TESTING_JS_MODULES := AddonManagerTesting.jsm
ADDONSRC = $(srcdir)/addons
TESTROOT = $(CURDIR)/$(DEPTH)/_tests/xpcshell/$(relativesrcdir)
TESTXPI = $(TESTROOT)/xpcshell/addons