diff --git a/addon-sdk/source/lib/sdk/addon/installer.js b/addon-sdk/source/lib/sdk/addon/installer.js
index f72b21e0a28..451ad224c0a 100644
--- a/addon-sdk/source/lib/sdk/addon/installer.js
+++ b/addon-sdk/source/lib/sdk/addon/installer.js
@@ -87,20 +87,24 @@ exports.uninstall = function uninstall(addonId) {
AddonManager.addAddonListener(listener);
// Order Addonmanager to uninstall the addon
- AddonManager.getAddonByID(addonId, function (addon) {
- addon.uninstall();
- });
+ getAddon(addonId).then(addon => addon.uninstall(), reject);
return promise;
};
exports.disable = function disable(addonId) {
- let { promise, resolve, reject } = defer();
-
- AddonManager.getAddonByID(addonId, function (addon) {
+ return getAddon(addonId).then(addon => {
addon.userDisabled = true;
- resolve();
+ return addonId;
});
-
- return promise;
};
+
+exports.isActive = function isActive(addonId) {
+ return getAddon(addonId).then(addon => addon.isActive && !addon.appDisabled);
+};
+
+function getAddon (id) {
+ let { promise, resolve, reject } = defer();
+ AddonManager.getAddonByID(id, addon => addon ? resolve(addon) : reject());
+ return promise;
+}
diff --git a/addon-sdk/source/lib/sdk/content/worker.js b/addon-sdk/source/lib/sdk/content/worker.js
index 4d8bceca9fc..d781f39c239 100644
--- a/addon-sdk/source/lib/sdk/content/worker.js
+++ b/addon-sdk/source/lib/sdk/content/worker.js
@@ -130,13 +130,13 @@ const WorkerSandbox = EventEmitter.compose({
// Even if this principal is for a domain that is specified in the multiple
// domain principal.
let principals = window;
- let wantXHRConstructor = false;
+ let wantDOMConstructors = []
if (EXPANDED_PRINCIPALS.length > 0 && !worker._injectInDocument) {
principals = EXPANDED_PRINCIPALS.concat(window);
// We have to replace XHR constructor of the content document
// with a custom cross origin one, automagically added by platform code:
delete proto.XMLHttpRequest;
- wantXHRConstructor = true;
+ wantDOMConstructors.push("XMLHttpRequest");
}
// Instantiate trusted code in another Sandbox in order to prevent content
@@ -149,7 +149,7 @@ const WorkerSandbox = EventEmitter.compose({
let content = this._sandbox = sandbox(principals, {
sandboxPrototype: proto,
wantXrays: true,
- wantXHRConstructor: wantXHRConstructor,
+ wantDOMConstructors: wantDOMConstructors,
sameZoneAs: window
});
// We have to ensure that window.top and window.parent are the exact same
diff --git a/addon-sdk/source/lib/sdk/hotkeys.js b/addon-sdk/source/lib/sdk/hotkeys.js
index ce47191b225..00081455e6a 100644
--- a/addon-sdk/source/lib/sdk/hotkeys.js
+++ b/addon-sdk/source/lib/sdk/hotkeys.js
@@ -24,7 +24,7 @@ const Hotkey = exports.Hotkey = function Hotkey(options) {
throw new TypeError(INVALID_HOTKEY);
}
- this.onPress = options.onPress;
+ this.onPress = options.onPress && options.onPress.bind(this);
this.toString = stringify.bind(null, hotkey);
// Registering listener on keyboard combination enclosed by this hotkey.
// Please note that `this.toString()` is a normalized version of
diff --git a/addon-sdk/source/lib/sdk/util/deprecate.js b/addon-sdk/source/lib/sdk/util/deprecate.js
index be3ca64508a..40f236de524 100644
--- a/addon-sdk/source/lib/sdk/util/deprecate.js
+++ b/addon-sdk/source/lib/sdk/util/deprecate.js
@@ -9,12 +9,16 @@ module.metadata = {
};
const { get, format } = require("../console/traceback");
+const { get: getPref } = require("../preferences/service");
+const PREFERENCE = "devtools.errorconsole.deprecation_warnings";
function deprecateUsage(msg) {
// Print caller stacktrace in order to help figuring out which code
// does use deprecated thing
let stack = get().slice(2);
- console.error("DEPRECATED: " + msg + "\n" + format(stack));
+
+ if (getPref(PREFERENCE))
+ console.error("DEPRECATED: " + msg + "\n" + format(stack));
}
exports.deprecateUsage = deprecateUsage;
diff --git a/addon-sdk/source/test/private-browsing/global.js b/addon-sdk/source/test/private-browsing/global.js
index 22ac59e67e9..199a853a2f3 100644
--- a/addon-sdk/source/test/private-browsing/global.js
+++ b/addon-sdk/source/test/private-browsing/global.js
@@ -7,6 +7,8 @@ const timer = require("sdk/timers");
const { LoaderWithHookedConsole, deactivate, pb, pbUtils } = require("./helper");
const tabs = require("sdk/tabs");
const { getMostRecentBrowserWindow, isWindowPrivate } = require('sdk/window/utils');
+const { set: setPref } = require("sdk/preferences/service");
+const DEPRECATE_PREF = "devtools.errorconsole.deprecation_warnings";
exports["test activate private mode via handler"] = function(test) {
test.waitUntilDone();
@@ -174,6 +176,7 @@ exports.testBothListeners = function(test) {
exports.testAutomaticUnload = function(test) {
test.waitUntilDone();
+ setPref(DEPRECATE_PREF, true);
// Create another private browsing instance and unload it
let { loader, errors } = LoaderWithHookedConsole(module);
diff --git a/addon-sdk/source/test/tabs/test-fennec-tabs.js b/addon-sdk/source/test/tabs/test-fennec-tabs.js
index b841589e89a..e579ebba93d 100644
--- a/addon-sdk/source/test/tabs/test-fennec-tabs.js
+++ b/addon-sdk/source/test/tabs/test-fennec-tabs.js
@@ -8,6 +8,8 @@ const { Loader, LoaderWithHookedConsole } = require('sdk/test/loader');
const timer = require('sdk/timers');
const tabs = require('sdk/tabs');
const windows = require('sdk/windows');
+const { set: setPref } = require("sdk/preferences/service");
+const DEPRECATE_PREF = "devtools.errorconsole.deprecation_warnings";
const tabsLen = tabs.length;
const URL = 'data:text/html;charset=utf-8,
#title#';
@@ -96,6 +98,7 @@ exports.testAutomaticDestroy = function(assert, done) {
// TEST: tab properties
exports.testTabProperties = function(assert, done) {
+ setPref(DEPRECATE_PREF, true);
let { loader, messages } = LoaderWithHookedConsole();
let tabs = loader.require('sdk/tabs');
diff --git a/addon-sdk/source/test/tabs/test-firefox-tabs.js b/addon-sdk/source/test/tabs/test-firefox-tabs.js
index 8777fd9e071..d3c5294ed2c 100644
--- a/addon-sdk/source/test/tabs/test-firefox-tabs.js
+++ b/addon-sdk/source/test/tabs/test-firefox-tabs.js
@@ -12,6 +12,8 @@ const { open, focus, close } = require('sdk/window/helpers');
const { StringBundle } = require('sdk/deprecated/app-strings');
const tabs = require('sdk/tabs');
const { browserWindows } = require('sdk/windows');
+const { set: setPref } = require("sdk/preferences/service");
+const DEPRECATE_PREF = "devtools.errorconsole.deprecation_warnings";
const base64png = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAYAAAAfFcSJAAAADUlEQVQImWNgYGBgAA";
@@ -904,6 +906,7 @@ exports.testOnLoadEventWithImage = function(assert, done) {
};
exports.testFaviconGetterDeprecation = function (assert, done) {
+ setPref(DEPRECATE_PREF, true);
const { LoaderWithHookedConsole } = require("sdk/test/loader");
let { loader, messages } = LoaderWithHookedConsole(module);
let tabs = loader.require('sdk/tabs');
diff --git a/addon-sdk/source/test/test-addon-installer.js b/addon-sdk/source/test/test-addon-installer.js
index a816799ac51..0938c23bba0 100644
--- a/addon-sdk/source/test/test-addon-installer.js
+++ b/addon-sdk/source/test/test-addon-installer.js
@@ -48,7 +48,7 @@ exports["test Install"] = function (assert, done) {
done();
}
);
-}
+};
exports["test Failing Install With Invalid Path"] = function (assert, done) {
AddonInstaller.install("invalid-path").then(
@@ -62,7 +62,7 @@ exports["test Failing Install With Invalid Path"] = function (assert, done) {
done();
}
);
-}
+};
exports["test Failing Install With Invalid File"] = function (assert, done) {
let directory = system.pathFor("ProfD");
@@ -131,6 +131,38 @@ exports["test Update"] = function (assert, done) {
}
next();
-}
+};
+
+exports['test Uninstall failure'] = function (assert, done) {
+ AddonInstaller.uninstall('invalid-addon-path').then(
+ () => assert.fail('Addon uninstall should not resolve successfully'),
+ () => assert.pass('Addon correctly rejected invalid uninstall')
+ ).then(done, assert.fail);
+};
+
+exports['test Addon Disable'] = function (assert, done) {
+ let ensureActive = (addonId) => AddonInstaller.isActive(addonId).then(state => {
+ assert.equal(state, true, 'Addon should be enabled by default');
+ return addonId;
+ });
+ let ensureInactive = (addonId) => AddonInstaller.isActive(addonId).then(state => {
+ assert.equal(state, false, 'Addon should be disabled after disabling');
+ return addonId;
+ });
+
+ AddonInstaller.install(ADDON_PATH)
+ .then(ensureActive)
+ .then(AddonInstaller.disable)
+ .then(ensureInactive)
+ .then(AddonInstaller.uninstall)
+ .then(done, assert.fail);
+};
+
+exports['test Disable failure'] = function (assert, done) {
+ AddonInstaller.disable('not-an-id').then(
+ () => assert.fail('Addon disable should not resolve successfully'),
+ () => assert.pass('Addon correctly rejected invalid disable')
+ ).then(done, assert.fail);
+};
require("test").run(exports);
diff --git a/addon-sdk/source/test/test-addon-page.js b/addon-sdk/source/test/test-addon-page.js
index 7cc6a4edaf0..fc885e377a0 100644
--- a/addon-sdk/source/test/test-addon-page.js
+++ b/addon-sdk/source/test/test-addon-page.js
@@ -18,6 +18,8 @@ const { setTimeout } = require('sdk/timers');
const { is } = require('sdk/system/xul-app');
const tabs = require('sdk/tabs');
const isAustralis = "gCustomizeMode" in windows.activeBrowserWindow;
+const { set: setPref } = require("sdk/preferences/service");
+const DEPRECATE_PREF = "devtools.errorconsole.deprecation_warnings";
let uri = require('sdk/self').data.url('index.html');
@@ -29,6 +31,7 @@ function isChromeVisible(window) {
exports['test add-on page deprecation message'] = function(assert) {
let { loader, messages } = LoaderWithHookedConsole(module);
loader.require('sdk/addon-page');
+ setPref(DEPRECATE_PREF, true);
assert.equal(messages.length, 1, "only one error is dispatched");
assert.equal(messages[0].type, "error", "the console message is an error");
diff --git a/addon-sdk/source/test/test-content-events.js b/addon-sdk/source/test/test-content-events.js
index f4a7b164479..9ec694f2530 100644
--- a/addon-sdk/source/test/test-content-events.js
+++ b/addon-sdk/source/test/test-content-events.js
@@ -41,7 +41,9 @@ exports["test multiple tabs"] = function(assert, done) {
let { events } = loader.require("sdk/content/events");
let { on, off } = loader.require("sdk/event/core");
let actual = [];
- on(events, "data", function({type, target, timeStamp}) {
+
+ on(events, "data", handler);
+ function handler ({type, target, timeStamp}) {
// ignore about:blank pages and *-document-global-created
// events that are not very consistent.
// ignore http:// requests, as Fennec's `about:home` page
@@ -52,7 +54,7 @@ exports["test multiple tabs"] = function(assert, done) {
type !== "chrome-document-global-created" &&
type !== "content-document-global-created")
actual.push(type + " -> " + target.URL)
- });
+ }
let window = getMostRecentBrowserWindow();
let firstTab = open("data:text/html,first-tab", window);
@@ -78,6 +80,7 @@ exports["test multiple tabs"] = function(assert, done) {
assert.fail(Error(reason));
}).then(function() {
loader.unload();
+ off(events, "data", handler);
done();
});
};
@@ -87,14 +90,15 @@ exports["test nested frames"] = function(assert, done) {
let { events } = loader.require("sdk/content/events");
let { on, off } = loader.require("sdk/event/core");
let actual = [];
- on(events, "data", function({type, target, timeStamp}) {
+ on(events, "data", handler);
+ function handler ({type, target, timeStamp}) {
// ignore about:blank pages and *-global-created
// events that are not very consistent.
if (target.URL !== "about:blank" &&
type !== "chrome-document-global-created" &&
type !== "content-document-global-created")
actual.push(type + " -> " + target.URL)
- });
+ }
let window = getMostRecentBrowserWindow();
let uri = encodeURI("data:text/html,