Bug 552761: Switch PFS over to the new API. r=robstrong
--- a/toolkit/mozapps/plugins/content/pluginInstallerService.js
+++ b/toolkit/mozapps/plugins/content/pluginInstallerService.js
@@ -30,17 +30,23 @@
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
-const nsIXPIProgressDialog = Components.interfaces.nsIXPIProgressDialog;
+Components.utils.import("resource://gre/modules/AddonManager.jsm");
+
+const DOWNLOAD_STARTED = 0;
+const DOWNLOAD_FINISHED = 1;
+const INSTALL_STARTED = 2;
+const INSTALL_FINISHED = 3;
+const INSTALLS_COMPLETE = 4;
function getLocalizedError(key)
{
return document.getElementById("xpinstallStrings").getString(key);
}
function binaryToHex(input)
{
@@ -103,38 +109,37 @@ InstallerObserver.prototype = {
var channel = ios.newChannelFromURI(uri);
this._downloader =
Components.classes["@mozilla.org/network/downloader;1"].
createInstance(Components.interfaces.nsIDownloader);
this._downloader.init(this, resultFile);
channel.notificationCallbacks = this;
- this._fireNotification(nsIXPIProgressDialog.DOWNLOAD_START, null);
+ this._fireNotification(DOWNLOAD_STARTED, null);
channel.asyncOpen(this._downloader, null);
}
catch (e) {
Components.utils.reportError(e);
- this._fireNotification(nsIXPIProgressDialog.INSTALL_DONE,
- getLocalizedError("error-228"));
+ this._fireNotification(INSTALL_FINISHED, getLocalizedError("error-228"));
if (resultFile && resultFile.exists())
resultfile.remove(false);
}
},
/**
* Inform the gPluginInstaller about what's going on.
*/
_fireNotification: function(aStatus, aErrorMsg)
{
gPluginInstaller.pluginInstallationProgress(this._plugin.pid,
aStatus, aErrorMsg);
- if (aStatus == nsIXPIProgressDialog.INSTALL_DONE) {
+ if (aStatus == INSTALL_FINISHED) {
--PluginInstallService._installersPending;
PluginInstallService._fireFinishedNotification();
}
},
QueryInterface: function(iid)
{
if (iid.equals(Components.interfaces.nsISupports) ||
@@ -153,66 +158,63 @@ InstallerObserver.prototype = {
return null;
},
onDownloadComplete: function(downloader, request, ctxt, status, result)
{
if (!Components.isSuccessCode(status)) {
// xpinstall error 228 is "Download Error"
- this._fireNotification(nsIXPIProgressDialog.INSTALL_DONE,
- getLocalizedError("error-228"));
+ this._fireNotification(INSTALL_FINISHED, getLocalizedError("error-228"));
result.remove(false);
return;
}
- this._fireNotification(nsIXPIProgressDialog.DOWNLOAD_DONE);
+ this._fireNotification(DOWNLOAD_FINISHED);
if (this._plugin.InstallerHash &&
!verifyHash(result, this._plugin.InstallerHash)) {
// xpinstall error 261 is "Invalid file hash..."
- this._fireNotification(nsIXPIProgressDialog.INSTALL_DONE,
- getLocalizedError("error-261"));
+ this._fireNotification(INSTALL_FINISHED, getLocalizedError("error-261"));
result.remove(false);
return;
}
- this._fireNotification(nsIXPIProgressDialog.INSTALL_START);
+ this._fireNotification(INSTALL_STARTED);
result.QueryInterface(Components.interfaces.nsILocalFile);
try {
// Make sure the file is executable
result.permissions = 0770;
var process = Components.classes["@mozilla.org/process/util;1"]
.createInstance(Components.interfaces.nsIProcess);
process.init(result);
var self = this;
process.runAsync([], 0, {
observe: function(subject, topic, data) {
if (topic != "process-finished") {
Components.utils.reportError("Failed to launch installer");
- self._fireNotification(nsIXPIProgressDialog.INSTALL_DONE,
+ self._fireNotification(INSTALL_FINISHED,
getLocalizedError("error-207"));
}
else if (process.exitValue != 0) {
Components.utils.reportError("Installer returned exit code " + process.exitValue);
- self._fireNotification(nsIXPIProgressDialog.INSTALL_DONE,
+ self._fireNotification(INSTALL_FINISHED,
getLocalizedError("error-203"));
}
else {
- self._fireNotification(nsIXPIProgressDialog.INSTALL_DONE, null);
+ self._fireNotification(INSTALL_FINISHED, null);
}
result.remove(false);
}
});
}
catch (e) {
Components.utils.reportError(e);
- this._fireNotification(nsIXPIProgressDialog.INSTALL_DONE,
- getLocalizedError("error-207"));
+ this._fireNotification(INSTALL_FINISHED, getLocalizedError("error-207"));
result.remove(false);
}
},
onProgress: function(aRequest, aContext, aProgress, aProgressMax)
{
gPluginInstaller.pluginInstallationProgressMeter(this._plugin.pid,
aProgress,
@@ -235,73 +237,96 @@ var PluginInstallService = {
* @param aXPIPlugins An array of objects which should have the
* properties "pid", "XPILocation",
* and "XPIHash"
*/
startPluginInstallation: function (aInstallerPlugins,
aXPIPlugins)
{
this._xpiPlugins = aXPIPlugins;
-
- if (this._xpiPlugins.length > 0) {
- this._xpisDone = false;
+ this._xpisPending = aXPIPlugins.length;
- var xpiManager = Components.classes["@mozilla.org/xpinstall/install-manager;1"]
- .createInstance(Components.interfaces.nsIXPInstallManager);
- xpiManager.initManagerWithHashes(
- [plugin.XPILocation for each (plugin in this._xpiPlugins)],
- [plugin.XPIHash for each (plugin in this._xpiPlugins)],
- this._xpiPlugins.length, this);
- }
- else {
- this._xpisDone = true;
- }
+ aXPIPlugins.forEach(function(plugin) {
+ AddonManager.getInstallForURL(plugin.XPILocation, function(install) {
+ install.addListener(PluginInstallService);
+ install.install();
+ }, "application/x-xpinstall", plugin.XPIHash);
+ });
// InstallerObserver may finish immediately so we must initialise the
// installers after setting the number of installers and xpis pending
this._installersPending = aInstallerPlugins.length;
this._installerPlugins = [new InstallerObserver(plugin)
for each (plugin in aInstallerPlugins)];
},
_fireFinishedNotification: function()
{
- if (this._installersPending == 0 && this._xpisDone)
- gPluginInstaller.
- pluginInstallationProgress(null, nsIXPIProgressDialog.DIALOG_CLOSE,
- null);
+ if (this._installersPending == 0 && this._xpisPending == 0)
+ gPluginInstaller.pluginInstallationProgress(null, INSTALLS_COMPLETE, null);
+ },
+
+ getPidForInstall: function(install) {
+ for (let i = 0; i < this._xpiPlugins.length; i++) {
+ if (install.sourceURL == this._xpiPlugins[i].XPILocation)
+ return this._xpiPlugins[i].pid;
+ }
+ return -1;
+ },
+
+ // InstallListener interface
+ onDownloadStarted: function(install) {
+ var pid = this.getPidForInstall(install);
+ gPluginInstaller.pluginInstallationProgress(pid, DOWNLOAD_STARTED, null);
+ },
+
+ onDownloadProgress: function(install) {
+ var pid = this.getPidForInstall(install);
+ gPluginInstaller.pluginInstallationProgressMeter(pid, install.progress,
+ install.maxProgress);
+ },
+
+ onDownloadEnded: function(install) {
+ var pid = this.getPidForInstall(install);
+ gPluginInstaller.pluginInstallationProgress(pid, DOWNLOAD_FINISHED, null);
},
- // XPI progress listener stuff
- onStateChange: function (aIndex, aState, aValue)
- {
- // get the pid to return to the wizard
- var pid = this._xpiPlugins[aIndex].pid;
- var errorMsg;
+ onDownloadFailed: function(install, error) {
+ var pid = this.getPidForInstall(install);
+ switch (error) {
+ case AddonManager.ERROR_NETWORK_FAILURE:
+ var errorMsg = getLocalizedError("error-228");
+ break;
+ case AddonManager.ERROR_INCORRECT_HASH:
+ var errorMsg = getLocalizedError("error-261");
+ break;
+ case AddonManager.ERROR_CORRUPT_FILE:
+ var errorMsg = getLocalizedError("error-207");
+ break;
+ }
+ gPluginInstaller.pluginInstallationProgress(pid, INSTALL_FINISHED, errorMsg);
- if (aState == nsIXPIProgressDialog.INSTALL_DONE) {
- if (aValue != 0) {
- var xpinstallStrings = document.getElementById("xpinstallStrings");
- try {
- errorMsg = xpinstallStrings.getString("error" + aValue);
- }
- catch (e) {
- errorMsg = xpinstallStrings.getFormattedString("unknown.error", [aValue]);
- }
- }
- }
-
- if (aState == nsIXPIProgressDialog.DIALOG_CLOSE) {
- this._xpisDone = true;
- this._fireFinishedNotification();
- }
- else {
- gPluginInstaller.pluginInstallationProgress(pid, aState, errorMsg);
- }
+ this._xpisPending--;
+ this._fireFinishedNotification();
},
- onProgress: function (aIndex, aValue, aMaxValue)
- {
- // get the pid to return to the wizard
- var pid = this._xpiPlugins[aIndex].pid;
- gPluginInstaller.pluginInstallationProgressMeter(pid, aValue, aMaxValue);
+ onInstallStarted: function(install) {
+ var pid = this.getPidForInstall(install);
+ gPluginInstaller.pluginInstallationProgress(pid, INSTALL_STARTED, null);
+ },
+
+ onInstallEnded: function(install, addon) {
+ var pid = this.getPidForInstall(install);
+ gPluginInstaller.pluginInstallationProgress(pid, INSTALL_FINISHED, null);
+
+ this._xpisPending--;
+ this._fireFinishedNotification();
+ },
+
+ onInstallFailed: function(install, error) {
+ var pid = this.getPidForInstall(install);
+ gPluginInstaller.pluginInstallationProgress(pid, INSTALL_FINISHED,
+ getLocalizedError("error-203"));
+
+ this._xpisPending--;
+ this._fireFinishedNotification();
}
}
--- a/toolkit/mozapps/plugins/tests/browser_bug435788.js
+++ b/toolkit/mozapps/plugins/tests/browser_bug435788.js
@@ -1,13 +1,15 @@
const Cc = Components.classes;
const Ci = Components.interfaces;
const TEST_ROOT = "http://example.com/browser/toolkit/mozapps/plugins/tests/";
+Components.utils.import("resource://gre/modules/AddonManager.jsm");
+
var gPrefs, gPFS, gDS, gSeenAvailable;
function test() {
waitForExplicitFinish();
gPrefs = Cc["@mozilla.org/preferences-service;1"].
getService(Ci.nsIPrefBranch);
gDS = Cc["@mozilla.org/file/directory_service;1"].
@@ -300,22 +302,24 @@ function test_5_available() {
function test_5_complete() {
ok(gSeenAvailable, "Should have seen the list of available plugins");
is(getResultCount(), 1, "Should have attempted to install 1 plugin");
var item = getResultItem("Test extension 1", null);
ok(item, "Should have seen the installed item");
is(item.status, "Installed", "Should have been a successful install");
- var em = Cc["@mozilla.org/extensions/manager;1"].
- getService(Ci.nsIExtensionManager);
- ok(em.getItemForID("bug435788_1@tests.mozilla.org"), "Should have installed the extension");
- em.cancelInstallItem("bug435788_1@tests.mozilla.org");
+ AddonManager.getInstalls(null, function(installs) {
+ is(installs.length, 1, "Should be just one install");
+ is(installs[0].state, AddonManager.STATE_INSTALLED, "Should be fully installed");
+ is(installs[0].addon.id, "bug435788_1@tests.mozilla.org", "Should have installed the extension");
+ installs[0].cancel();
- gPFS.document.documentElement.getButton("finish").click();
+ gPFS.document.documentElement.getButton("finish").click();
+ });
}
// Test a broke xpi (no install.rdf)
function prepare_test_6() {
ok(true, "Test 6");
var missingPluginsArray = {
"application/x-broken-extension": {
mimetype: "application/x-broken-extension",
@@ -407,20 +411,24 @@ function test_7_complete() {
is(getResultCount(), 2, "Should have attempted to install 2 plugins");
var item = getResultItem("Test extension 1", null);
ok(item, "Should have seen the installed item");
is(item.status, "Installed", "Should have been a failed install");
item = getResultItem("Test extension 2", null);
ok(item, "Should have seen the installed item");
is(item.status, "Failed", "Should have been a failed install");
- var em = Cc["@mozilla.org/extensions/manager;1"].
- getService(Ci.nsIExtensionManager);
- ok(em.getItemForID("bug435788_1@tests.mozilla.org"), "Should have installed the extension");
- em.cancelInstallItem("bug435788_1@tests.mozilla.org");
+ AddonManager.getInstalls(null, function(installs) {
+ is(installs.length, 4, "Should be just one install");
+ is(installs[3].state, AddonManager.STATE_DOWNLOAD_FAILED, "Should have failed to download");
+ is(installs[3].addon.id, "bug435788_1@tests.mozilla.org", "Should have installed the extension");
+ installs[3].cancel();
+
+ gPFS.document.documentElement.getButton("finish").click();
+ });
gPFS.document.documentElement.getButton("finish").click();
}
// Test an xpi with a bad hash
function prepare_test_8() {
ok(true, "Test 8");
var missingPluginsArray = {
@@ -459,19 +467,21 @@ function test_8_available() {
function test_8_complete() {
ok(gSeenAvailable, "Should have seen the list of available plugins");
is(getResultCount(), 1, "Should have attempted to install 1 plugin");
var item = getResultItem("Test extension 3", null);
ok(item, "Should have seen the installed item");
is(item.status, "Failed", "Should have not been a successful install");
- var em = Cc["@mozilla.org/extensions/manager;1"].
- getService(Ci.nsIExtensionManager);
- ok(!em.getItemForID("bug435788_1@tests.mozilla.org"), "Should not have installed the extension");
+ AddonManager.getInstalls(null, function(installs) {
+ is(installs.length, 5, "Should not be any installs");
+
+ gPFS.document.documentElement.getButton("finish").click();
+ });
gPFS.document.documentElement.getButton("finish").click();
}
// Test when no plugin exists in the datasource
function prepare_test_9() {
ok(true, "Test 9");
var missingPluginsArray = {