Bug 1326334 - Fix more errors in devtools/shared. r=jryans

MozReview-Commit-ID: 2MOe5hEyqYo
This commit is contained in:
Tim Nguyen 2017-01-03 23:47:28 +01:00
parent 56683af3e7
commit 1f91986edf
33 changed files with 550 additions and 559 deletions

View file

@ -116,16 +116,9 @@ devtools/server/tests/browser/**
!devtools/server/tests/browser/browser_webextension_inspected_window.js !devtools/server/tests/browser/browser_webextension_inspected_window.js
devtools/server/tests/mochitest/** devtools/server/tests/mochitest/**
devtools/server/tests/unit/** devtools/server/tests/unit/**
devtools/shared/apps/**
devtools/shared/gcli/**
!devtools/shared/gcli/templater.js
devtools/shared/heapsnapshot/** devtools/shared/heapsnapshot/**
devtools/shared/transport/** devtools/shared/transport/tests/unit/**
!devtools/shared/transport/transport.js
!devtools/shared/transport/websocket-transport.js
devtools/shared/webconsole/test/** devtools/shared/webconsole/test/**
devtools/shared/worker/**
!devtools/shared/worker/worker.js
# Ignore devtools pre-processed files # Ignore devtools pre-processed files
devtools/client/framework/toolbox-process-window.js devtools/client/framework/toolbox-process-window.js
@ -136,7 +129,7 @@ devtools/client/preferences/**
# Ignore devtools third-party libs # Ignore devtools third-party libs
devtools/shared/jsbeautify/* devtools/shared/jsbeautify/*
devtools/shared/acorn/* devtools/shared/acorn/*
devtools/client/sourceeditor/tern/* devtools/shared/gcli/source/*
devtools/shared/node-properties/* devtools/shared/node-properties/*
devtools/shared/pretty-fast/* devtools/shared/pretty-fast/*
devtools/shared/sourcemap/* devtools/shared/sourcemap/*
@ -147,6 +140,7 @@ devtools/client/shared/demangle.js
devtools/client/shared/vendor/* devtools/client/shared/vendor/*
devtools/client/sourceeditor/codemirror/*.js devtools/client/sourceeditor/codemirror/*.js
devtools/client/sourceeditor/codemirror/**/*.js devtools/client/sourceeditor/codemirror/**/*.js
devtools/client/sourceeditor/tern/*
devtools/client/sourceeditor/test/cm_mode_ruby.js devtools/client/sourceeditor/test/cm_mode_ruby.js
devtools/client/sourceeditor/test/codemirror/* devtools/client/sourceeditor/test/codemirror/*
devtools/client/inspector/markup/test/lib_* devtools/client/inspector/markup/test/lib_*

View file

@ -273,7 +273,7 @@ module.exports = {
// Disallow declaring the same variable more than once (we use let anyway). // Disallow declaring the same variable more than once (we use let anyway).
"no-redeclare": "error", "no-redeclare": "error",
// Disallow multiple spaces in a regular expression literal. // Disallow multiple spaces in a regular expression literal.
"no-regex-spaces": "error", "no-regex-spaces": "off",
// Allow reserved words being used as object literal keys. // Allow reserved words being used as object literal keys.
"no-reserved-keys": "off", "no-reserved-keys": "off",
// Don't restrict usage of specified node modules (not a node environment). // Don't restrict usage of specified node modules (not a node environment).

View file

@ -6,6 +6,8 @@
Components.utils.import("resource://devtools/shared/event-emitter.js"); Components.utils.import("resource://devtools/shared/event-emitter.js");
/* exported EXPORTED_SYMBOLS */
const EXPORTED_SYMBOLS = ["Devices"]; const EXPORTED_SYMBOLS = ["Devices"];
var addonInstalled = false; var addonInstalled = false;

View file

@ -37,8 +37,7 @@ function addDirToZip(writer, dir, basePath) {
if (file.isHidden() || if (file.isHidden() ||
file.isSpecial() || file.isSpecial() ||
file.equals(writer.file)) file.equals(writer.file)) {
{
continue; continue;
} }
@ -62,12 +61,15 @@ function addDirToZip(writer, dir, basePath) {
*/ */
function getResultText(code) { function getResultText(code) {
let regexp = let regexp =
/^\[Exception... "(.*)" nsresult: "0x[0-9a-fA-F]* \((.*)\)" location: ".*" data: .*\]$/; /^\[Exception... "(.*)" nsresult: "0x[0-9a-fA-F]* \((.*)\)" location: ".*" data: .*\]$/; // eslint-disable-line
let ex = Cc["@mozilla.org/js/xpc/Exception;1"]. let ex = Cc["@mozilla.org/js/xpc/Exception;1"]
createInstance(Ci.nsIXPCException); .createInstance(Ci.nsIXPCException);
ex.initialize(null, code, null, null, null, null); ex.initialize(null, code, null, null, null, null);
let [, message, name] = regexp.exec(ex.toString()); let [, message, name] = regexp.exec(ex.toString());
return { name: name, message: message }; return {
name,
message
};
} }
function zipDirectory(zipFile, dirToArchive) { function zipDirectory(zipFile, dirToArchive) {
@ -75,7 +77,7 @@ function zipDirectory(zipFile, dirToArchive) {
let writer = Cc["@mozilla.org/zipwriter;1"].createInstance(Ci.nsIZipWriter); let writer = Cc["@mozilla.org/zipwriter;1"].createInstance(Ci.nsIZipWriter);
writer.open(zipFile, PR_RDWR | PR_CREATE_FILE | PR_TRUNCATE); writer.open(zipFile, PR_RDWR | PR_CREATE_FILE | PR_TRUNCATE);
this.addDirToZip(writer, dirToArchive, ""); addDirToZip(writer, dirToArchive, "");
writer.processQueue({ writer.processQueue({
onStartRequest: function onStartRequest(request, context) {}, onStartRequest: function onStartRequest(request, context) {},
@ -83,8 +85,7 @@ function zipDirectory(zipFile, dirToArchive) {
if (status == Cr.NS_OK) { if (status == Cr.NS_OK) {
writer.close(); writer.close();
deferred.resolve(zipFile); deferred.resolve(zipFile);
} } else {
else {
let { name, message } = getResultText(status); let { name, message } = getResultText(status);
deferred.reject(name + ": " + message); deferred.reject(name + ": " + message);
} }
@ -97,9 +98,8 @@ function zipDirectory(zipFile, dirToArchive) {
function uploadPackage(client, webappsActor, packageFile, progressCallback) { function uploadPackage(client, webappsActor, packageFile, progressCallback) {
if (client.traits.bulk) { if (client.traits.bulk) {
return uploadPackageBulk(client, webappsActor, packageFile, progressCallback); return uploadPackageBulk(client, webappsActor, packageFile, progressCallback);
} else {
return uploadPackageJSON(client, webappsActor, packageFile, progressCallback);
} }
return uploadPackageJSON(client, webappsActor, packageFile, progressCallback);
} }
function uploadPackageJSON(client, webappsActor, packageFile, progressCallback) { function uploadPackageJSON(client, webappsActor, packageFile, progressCallback) {
@ -125,48 +125,45 @@ function uploadPackageJSON(client, webappsActor, packageFile, progressCallback)
function openFile(actor) { function openFile(actor) {
let openedFile; let openedFile;
OS.File.open(packageFile.path) OS.File.open(packageFile.path).then(file => {
.then(file => { openedFile = file;
openedFile = file; return openedFile.stat();
return openedFile.stat(); }).then(fileInfo => {
}) fileSize = fileInfo.size;
.then(fileInfo => { emitProgress();
fileSize = fileInfo.size; uploadChunk(actor, openedFile);
emitProgress(); });
uploadChunk(actor, openedFile);
});
} }
function uploadChunk(actor, file) { function uploadChunk(actor, file) {
file.read(CHUNK_SIZE) file.read(CHUNK_SIZE).then(function (bytes) {
.then(function (bytes) { bytesRead += bytes.length;
bytesRead += bytes.length; emitProgress();
emitProgress(); // To work around the fact that JSON.stringify translates the typed
// To work around the fact that JSON.stringify translates the typed // array to object, we are encoding the typed array here into a string
// array to object, we are encoding the typed array here into a string let chunk = String.fromCharCode.apply(null, bytes);
let chunk = String.fromCharCode.apply(null, bytes);
let request = { let chunkRequest = {
to: actor, to: actor,
type: "chunk", type: "chunk",
chunk: chunk chunk,
}; };
client.request(request, (res) => { client.request(chunkRequest, (res) => {
if (bytes.length == CHUNK_SIZE) { if (bytes.length == CHUNK_SIZE) {
uploadChunk(actor, file); uploadChunk(actor, file);
} else { } else {
file.close().then(function () { file.close().then(function () {
endsUpload(actor); endsUpload(actor);
});
}
}); });
}); }
});
});
} }
function endsUpload(actor) { function endsUpload(actor) {
let request = { let doneRequest = {
to: actor, to: actor,
type: "done" type: "done"
}; };
client.request(request, (res) => { client.request(doneRequest, (res) => {
deferred.resolve(actor); deferred.resolve(actor);
}); });
} }
@ -190,13 +187,13 @@ function uploadPackageBulk(client, webappsActor, packageFile, progressCallback)
let fileSize = packageFile.fileSize; let fileSize = packageFile.fileSize;
console.log("File size: " + fileSize); console.log("File size: " + fileSize);
let request = client.startBulkRequest({ let streamRequest = client.startBulkRequest({
actor: actor, actor: actor,
type: "stream", type: "stream",
length: fileSize length: fileSize
}); });
request.on("bulk-send-ready", ({copyFrom}) => { streamRequest.on("bulk-send-ready", ({copyFrom}) => {
NetUtil.asyncFetch({ NetUtil.asyncFetch({
uri: NetUtil.newURI(packageFile), uri: NetUtil.newURI(packageFile),
loadUsingSystemPrincipal: true loadUsingSystemPrincipal: true
@ -245,36 +242,37 @@ function installPackaged(client, webappsActor, packagePath, appId, progressCallb
packagePromise = promise.resolve(file); packagePromise = promise.resolve(file);
} }
packagePromise.then((zipFile) => { packagePromise.then((zipFile) => {
uploadPackage(client, webappsActor, zipFile, progressCallback) uploadPackage(client, webappsActor, zipFile, progressCallback).then((fileActor) => {
.then((fileActor) => { let request = {
let request = { to: webappsActor,
to: webappsActor, type: "install",
type: "install", appId: appId,
appId: appId, upload: fileActor
upload: fileActor };
}; client.request(request, (res) => {
client.request(request, (res) => { // If the install method immediatly fails,
// If the install method immediatly fails, // reject immediatly the installPackaged promise.
// reject immediatly the installPackaged promise. // Otherwise, wait for webappsEvent for completion
// Otherwise, wait for webappsEvent for completion if (res.error) {
if (res.error) { deferred.reject(res);
deferred.reject(res); }
} if ("error" in res) {
if ("error" in res) deferred.reject({error: res.error, message: res.message});
deferred.reject({error: res.error, message: res.message}); } else {
else deferred.resolve({appId: res.appId});
deferred.resolve({appId: res.appId}); }
}); });
// Ensure deleting the temporary package file, but only if that a temporary // Ensure deleting the temporary package file, but only if that a temporary
// package created when we pass a directory as `packagePath` // package created when we pass a directory as `packagePath`
if (zipFile != file) if (zipFile != file) {
zipFile.remove(false); zipFile.remove(false);
// In case of success or error, ensure deleting the temporary package file }
// also created on the device, but only once install request is done // In case of success or error, ensure deleting the temporary package file
deferred.promise.then( // also created on the device, but only once install request is done
() => removeServerTemporaryFile(client, fileActor), deferred.promise.then(
() => removeServerTemporaryFile(client, fileActor)); () => removeServerTemporaryFile(client, fileActor),
}); () => removeServerTemporaryFile(client, fileActor));
});
}); });
return deferred.promise; return deferred.promise;
} }
@ -293,10 +291,11 @@ function installHosted(client, webappsActor, appId, metadata, manifest) {
if (res.error) { if (res.error) {
deferred.reject(res); deferred.reject(res);
} }
if ("error" in res) if ("error" in res) {
deferred.reject({error: res.error, message: res.message}); deferred.reject({error: res.error, message: res.message});
else } else {
deferred.resolve({appId: res.appId}); deferred.resolve({appId: res.appId});
}
}); });
return deferred.promise; return deferred.promise;
} }
@ -307,8 +306,9 @@ function getTargetForApp(client, webappsActor, manifestURL) {
// of the same app in order to show only one toolbox per app and // of the same app in order to show only one toolbox per app and
// avoid re-creating lot of objects twice. // avoid re-creating lot of objects twice.
let existingTarget = appTargets.get(manifestURL); let existingTarget = appTargets.get(manifestURL);
if (existingTarget) if (existingTarget) {
return promise.resolve(existingTarget); return promise.resolve(existingTarget);
}
let deferred = defer(); let deferred = defer();
let request = { let request = {
@ -343,23 +343,22 @@ function getTargetForApp(client, webappsActor, manifestURL) {
exports.getTargetForApp = getTargetForApp; exports.getTargetForApp = getTargetForApp;
function reloadApp(client, webappsActor, manifestURL) { function reloadApp(client, webappsActor, manifestURL) {
return getTargetForApp(client, return getTargetForApp(
webappsActor, client, webappsActor, manifestURL
manifestURL). ).then((target) => {
then((target) => { // Request the ContentActor to reload the app
// Request the ContentActor to reload the app let request = {
let request = { to: target.form.actor,
to: target.form.actor, type: "reload",
type: "reload", options: {
options: { force: true
force: true },
}, manifestURL,
manifestURL: manifestURL };
}; return client.request(request);
return client.request(request); }, () => {
}, () => { throw new Error("Not running");
throw new Error("Not running"); });
});
} }
exports.reloadApp = reloadApp; exports.reloadApp = reloadApp;
@ -423,25 +422,26 @@ App.prototype = {
type: "getAppActor", type: "getAppActor",
manifestURL: this.manifest.manifestURL manifestURL: this.manifest.manifestURL
}; };
return this.client.request(request) return this.client.request(request).then(res => {
.then(res => { this._form = res.actor;
return this._form = res.actor; return this._form;
}); });
}, },
getTarget: function () { getTarget: function () {
if (this._target) { if (this._target) {
return promise.resolve(this._target); return promise.resolve(this._target);
} }
return this.getForm(). return this.getForm().then(
then((form) => getTarget(this.client, form)). (form) => getTarget(this.client, form)
then((target) => { ).then((target) => {
target.on("close", () => { target.on("close", () => {
delete this._form; delete this._form;
delete this._target; delete this._target;
});
return this._target = target;
}); });
this._target = target;
return this._target;
});
}, },
launch: function () { launch: function () {
@ -487,7 +487,6 @@ App.prototype = {
} }
}; };
/** /**
* `AppActorFront` is a client for the webapps actor. * `AppActorFront` is a client for the webapps actor.
*/ */
@ -537,23 +536,21 @@ AppActorFront.prototype = {
let app = this._apps ? this._apps.get(manifestURL) : null; let app = this._apps ? this._apps.get(manifestURL) : null;
if (app) { if (app) {
return promise.resolve(app); return promise.resolve(app);
} else {
let request = {
to: this.actor,
type: "getApp",
manifestURL: manifestURL
};
return this.client.request(request)
.then(res => {
let app = new App(this.client, this.actor, res.app);
if (this._apps) {
this._apps.set(manifestURL, app);
}
return app;
}, e => {
console.error("Unable to retrieve app", manifestURL, e);
});
} }
let request = {
to: this.actor,
type: "getApp",
manifestURL,
};
return this.client.request(request).then(res => {
app = new App(this.client, this.actor, res.app);
if (this._apps) {
this._apps.set(manifestURL, app);
}
return app;
}, e => {
console.error("Unable to retrieve app", manifestURL, e);
});
}, },
/** /**
@ -583,47 +580,42 @@ AppActorFront.prototype = {
to: this.actor, to: this.actor,
type: "getAll" type: "getAll"
}; };
return this._loadingPromise = this.client.request(request) this._loadingPromise = this.client.request(request).then(res => {
.then(res => { delete this._loadingPromise;
delete this._loadingPromise; this._apps = new Map();
this._apps = new Map(); for (let a of res.apps) {
for (let a of res.apps) { let app = new App(this.client, this.actor, a);
let app = new App(this.client, this.actor, a); this._apps.set(a.manifestURL, app);
this._apps.set(a.manifestURL, app); }
} }).then(() => {
}) // Then retrieve all running apps in order to flag them as running
.then(() => { let listRequest = {
// Then retrieve all running apps in order to flag them as running to: this.actor,
let request = { type: "listRunningApps"
to: this.actor, };
type: "listRunningApps" return this.client.request(listRequest).then(res => res.apps);
}; }).then(apps => {
return this.client.request(request) let promises = apps.map(manifestURL => {
.then(res => res.apps); // _getApp creates `App` instance and register it to AppActorFront
}) return this._getApp(manifestURL).then(app => {
.then(apps => { app.running = true;
let promises = apps.map(manifestURL => { // Fake appOpen event for all already opened
// _getApp creates `App` instance and register it to AppActorFront this._notifyListeners("appOpen", app);
return this._getApp(manifestURL)
.then(app => {
app.running = true;
// Fake appOpen event for all already opened
this._notifyListeners("appOpen", app);
});
}); });
return promise.all(promises);
})
.then(() => {
// Finally ask to receive all app events
return this._listenAppEvents(listener);
}); });
return promise.all(promises);
}).then(() => {
// Finally ask to receive all app events
return this._listenAppEvents(listener);
});
return this._loadingPromise;
}, },
fetchIcons: function () { fetchIcons: function () {
// On demand, retrieve apps icons in order to be able // On demand, retrieve apps icons in order to be able
// to synchronously retrieve it on `App` objects // to synchronously retrieve it on `App` objects
let promises = []; let promises = [];
for (let [manifestURL, app] of this._apps) { for (let [, app] of this._apps) {
promises.push(app.getIcon()); promises.push(app.getIcon());
} }
@ -708,16 +700,15 @@ AppActorFront.prototype = {
to: this.actor, to: this.actor,
type: "listRunningApps" type: "listRunningApps"
}; };
this.client.request(request) this.client.request(request).then(res => {
.then(res => { if (res.apps.indexOf(manifestURL) !== -1) {
if (res.apps.indexOf(manifestURL) !== -1) { app.running = true;
app.running = true; this._notifyListeners("appInstall", app);
this._notifyListeners("appInstall", app); this._notifyListeners("appOpen", app);
this._notifyListeners("appOpen", app); } else {
} else { this._notifyListeners("appInstall", app);
this._notifyListeners("appInstall", app); }
} });
});
break; break;
case "appUninstall": case "appUninstall":
// Fake a appClose event if we didn't got one before uninstall // Fake a appClose event if we didn't got one before uninstall
@ -796,22 +787,19 @@ AppActorFront.prototype = {
} }
} }
}; };
this._listenAppEvents(listener) // Execute the request
// Execute the request this._listenAppEvents(listener).then(request).then(response => {
.then(request) finalAppId = response.appId;
.then(response => { manifestURL = response.manifestURL;
finalAppId = response.appId;
manifestURL = response.manifestURL;
// Resolves immediately if the appInstall event // Resolves immediately if the appInstall event
// was dispatched during the request. // was dispatched during the request.
if (manifestURL in installs) { if (manifestURL in installs) {
resolve(installs[manifestURL]); resolve(installs[manifestURL]);
} }
}, deferred.reject); }, deferred.reject);
return deferred.promise; return deferred.promise;
}, },
/* /*
@ -826,12 +814,12 @@ AppActorFront.prototype = {
let manifestURL = metadata.manifestURL || let manifestURL = metadata.manifestURL ||
metadata.origin + "/manifest.webapp"; metadata.origin + "/manifest.webapp";
let request = () => { let request = () => {
return installHosted(this.client, this.actor, appId, metadata, return installHosted(
manifest) this.client, this.actor, appId, metadata, manifest
.then(response => ({ ).then(response => ({
appId: response.appId, appId: response.appId,
manifestURL: manifestURL manifestURL: manifestURL
})); }));
}; };
return this._install(request); return this._install(request);
} }

View file

@ -15,8 +15,7 @@ function getAddonManager() {
AddonManager: require("resource://gre/modules/AddonManager.jsm").AddonManager, AddonManager: require("resource://gre/modules/AddonManager.jsm").AddonManager,
addonManagerActive: true addonManagerActive: true
}; };
} } catch (ex) {
catch (ex) {
// Fake up an AddonManager just enough to let the file load // Fake up an AddonManager just enough to let the file load
return { return {
AddonManager: { AddonManager: {
@ -28,21 +27,15 @@ function getAddonManager() {
} }
} }
const { Cc, Ci, Cu } = require("chrome");
const { AddonManager, addonManagerActive } = getAddonManager(); const { AddonManager, addonManagerActive } = getAddonManager();
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
const BRAND_SHORT_NAME = Cc["@mozilla.org/intl/stringbundle;1"]
.getService(Ci.nsIStringBundleService)
.createBundle("chrome://branding/locale/brand.properties")
.GetStringFromName("brandShortName");
/** /**
* Takes a function that uses a callback as its last parameter, and returns a * Takes a function that uses a callback as its last parameter, and returns a
* new function that returns a promise instead. * new function that returns a promise instead.
* This should probably live in async-util * This should probably live in async-util
*/ */
const promiseify = function(scope, functionWithLastParamCallback) { const promiseify = function (scope, functionWithLastParamCallback) {
return (...args) => { return (...args) => {
return new Promise(resolve => { return new Promise(resolve => {
args.push((...results) => { args.push((...results) => {
@ -50,7 +43,7 @@ const promiseify = function(scope, functionWithLastParamCallback) {
}); });
functionWithLastParamCallback.apply(scope, args); functionWithLastParamCallback.apply(scope, args);
}); });
} };
}; };
// Convert callback based functions to promise based ones // Convert callback based functions to promise based ones
@ -65,7 +58,7 @@ function pendingOperations(addon) {
"PENDING_ENABLE", "PENDING_DISABLE", "PENDING_UNINSTALL", "PENDING_ENABLE", "PENDING_DISABLE", "PENDING_UNINSTALL",
"PENDING_INSTALL", "PENDING_UPGRADE" "PENDING_INSTALL", "PENDING_UPGRADE"
]; ];
return allOperations.reduce(function(operations, opName) { return allOperations.reduce(function (operations, opName) {
return addon.pendingOperations & AddonManager[opName] ? return addon.pendingOperations & AddonManager[opName] ?
operations.concat(opName) : operations.concat(opName) :
operations; operations;
@ -79,15 +72,19 @@ var items = [
parent: "selection", parent: "selection",
stringifyProperty: "name", stringifyProperty: "name",
cacheable: true, cacheable: true,
constructor: function() { constructor: function () {
// Tell GCLI to clear the cache of addons when one is added or removed // Tell GCLI to clear the cache of addons when one is added or removed
let listener = { let listener = {
onInstalled: addon => { this.clearCache(); }, onInstalled: addon => {
onUninstalled: addon => { this.clearCache(); }, this.clearCache();
},
onUninstalled: addon => {
this.clearCache();
},
}; };
AddonManager.addAddonListener(listener); AddonManager.addAddonListener(listener);
}, },
lookup: function() { lookup: function () {
return getAllAddons().then(addons => { return getAllAddons().then(addons => {
return addons.map(addon => { return addons.map(addon => {
let name = addon.name + " " + addon.version; let name = addon.name + " " + addon.version;
@ -114,10 +111,10 @@ var items = [
defaultValue: "all", defaultValue: "all",
description: l10n.lookup("addonListTypeDesc") description: l10n.lookup("addonListTypeDesc")
}], }],
exec: function(args, context) { exec: function (args, context) {
let types = (args.type === "all") ? null : [ args.type ]; let types = (args.type === "all") ? null : [ args.type ];
return getAddonsByTypes(types).then(addons => { return getAddonsByTypes(types).then(addons => {
addons = addons.map(function(addon) { addons = addons.map(function (addon) {
return { return {
name: addon.name, name: addon.name,
version: addon.version, version: addon.version,
@ -133,7 +130,7 @@ var items = [
item: "converter", item: "converter",
from: "addonsInfo", from: "addonsInfo",
to: "view", to: "view",
exec: function(addonsInfo, context) { exec: function (addonsInfo, context) {
if (!addonsInfo.addons.length) { if (!addonsInfo.addons.length) {
return context.createView({ return context.createView({
html: "<p>${message}</p>", html: "<p>${message}</p>",
@ -167,7 +164,7 @@ var items = [
function arrangeAddons(addons) { function arrangeAddons(addons) {
let enabledAddons = []; let enabledAddons = [];
let disabledAddons = []; let disabledAddons = [];
addons.forEach(function(addon) { addons.forEach(function (addon) {
if (addon.isActive) { if (addon.isActive) {
enabledAddons.push(addon); enabledAddons.push(addon);
} else { } else {
@ -208,7 +205,7 @@ var items = [
"</table>", "</table>",
data: { data: {
header: header, header: header,
addons: arrangeAddons(addonsInfo.addons).map(function(addon) { addons: arrangeAddons(addonsInfo.addons).map(function (addon) {
return { return {
name: addon.name, name: addon.name,
label: addon.name.replace(/\s/g, "_") + label: addon.name.replace(/\s/g, "_") +
@ -220,7 +217,7 @@ var items = [
+ addon.pendingOperations.map(lookupOperation).join(", ") + addon.pendingOperations.map(lookupOperation).join(", ")
+ ")") : + ")") :
"", "",
toggleActionName: isActiveForToggle(addon) ? "disable": "enable", toggleActionName: isActiveForToggle(addon) ? "disable" : "enable",
toggleActionMessage: isActiveForToggle(addon) ? toggleActionMessage: isActiveForToggle(addon) ?
l10n.lookup("addonListOutDisable") : l10n.lookup("addonListOutDisable") :
l10n.lookup("addonListOutEnable") l10n.lookup("addonListOutEnable")
@ -244,7 +241,7 @@ var items = [
description: l10n.lookup("addonNameDesc") description: l10n.lookup("addonNameDesc")
} }
], ],
exec: function(args, context) { exec: function (args, context) {
let name = (args.addon.name + " " + args.addon.version).trim(); let name = (args.addon.name + " " + args.addon.version).trim();
if (args.addon.userDisabled) { if (args.addon.userDisabled) {
args.addon.userDisabled = false; args.addon.userDisabled = false;
@ -266,7 +263,7 @@ var items = [
description: l10n.lookup("addonNameDesc") description: l10n.lookup("addonNameDesc")
} }
], ],
exec: function(args, context) { exec: function (args, context) {
// If the addon is not disabled or is set to "click to play" then // If the addon is not disabled or is set to "click to play" then
// disable it. Otherwise display the message "Add-on is already // disable it. Otherwise display the message "Add-on is already
// disabled." // disabled."
@ -292,7 +289,7 @@ var items = [
description: l10n.lookup("addonNameDesc") description: l10n.lookup("addonNameDesc")
} }
], ],
exec: function(args, context) { exec: function (args, context) {
let name = (args.addon.name + " " + args.addon.version).trim(); let name = (args.addon.name + " " + args.addon.version).trim();
if (args.addon.type !== "plugin") { if (args.addon.type !== "plugin") {
return l10n.lookupFormat("addonCantCtp", [ name ]); return l10n.lookupFormat("addonCantCtp", [ name ]);

View file

@ -32,7 +32,7 @@ exports.items = [
} }
] ]
}], }],
exec: function(args, context) { exec: function (args, context) {
let utils; let utils;
let deferred = context.defer(); let deferred = context.defer();
@ -42,7 +42,7 @@ exports.items = [
utils = new AppCacheUtils(context.environment.document); utils = new AppCacheUtils(context.environment.document);
} }
utils.validateManifest().then(function(errors) { utils.validateManifest().then(function (errors) {
deferred.resolve([errors, utils.manifestURI || "-"]); deferred.resolve([errors, utils.manifestURI || "-"]);
}); });
@ -53,7 +53,7 @@ exports.items = [
item: "converter", item: "converter",
from: "appcacheerrors", from: "appcacheerrors",
to: "view", to: "view",
exec: function([errors, manifestURI], context) { exec: function ([errors, manifestURI], context) {
if (errors.length == 0) { if (errors.length == 0) {
return context.createView({ return context.createView({
html: "<span>" + l10n.lookup("appCacheValidatedSuccessfully") + "</span>" html: "<span>" + l10n.lookup("appCacheValidatedSuccessfully") + "</span>"
@ -81,7 +81,7 @@ exports.items = [
name: "appcache clear", name: "appcache clear",
description: l10n.lookup("appCacheClearDesc"), description: l10n.lookup("appCacheClearDesc"),
manual: l10n.lookup("appCacheClearManual"), manual: l10n.lookup("appCacheClearManual"),
exec: function(args, context) { exec: function (args, context) {
let utils = new AppCacheUtils(args.uri); let utils = new AppCacheUtils(args.uri);
utils.clearAll(); utils.clearAll();
@ -106,7 +106,7 @@ exports.items = [
}, },
] ]
}], }],
exec: function(args, context) { exec: function (args, context) {
let utils = new AppCacheUtils(); let utils = new AppCacheUtils();
return utils.listEntries(args.search); return utils.listEntries(args.search);
} }
@ -115,7 +115,7 @@ exports.items = [
item: "converter", item: "converter",
from: "appcacheentries", from: "appcacheentries",
to: "view", to: "view",
exec: function(entries, context) { exec: function (entries, context) {
return context.createView({ return context.createView({
html: "" + html: "" +
"<ul class='gcli-appcache-list'>" + "<ul class='gcli-appcache-list'>" +
@ -178,7 +178,7 @@ exports.items = [
defaultValue: null, defaultValue: null,
} }
], ],
exec: function(args, context) { exec: function (args, context) {
let utils = new AppCacheUtils(); let utils = new AppCacheUtils();
return utils.viewEntry(args.key); return utils.viewEntry(args.key);
} }

View file

@ -27,11 +27,11 @@ exports.items = [
name: "calllog start", name: "calllog start",
description: l10n.lookup("calllogStartDesc"), description: l10n.lookup("calllogStartDesc"),
exec: function(args, context) { exec: function (args, context) {
let contentWindow = context.environment.window; let contentWindow = context.environment.window;
let dbg = new Debugger(contentWindow); let dbg = new Debugger(contentWindow);
dbg.onEnterFrame = function(frame) { dbg.onEnterFrame = function (frame) {
// BUG 773652 - Make the output from the GCLI calllog command nicer // BUG 773652 - Make the output from the GCLI calllog command nicer
contentWindow.console.log("Method call: " + this.callDescription(frame)); contentWindow.console.log("Method call: " + this.callDescription(frame));
}.bind(this); }.bind(this);
@ -45,12 +45,11 @@ exports.items = [
return l10n.lookup("calllogStartReply"); return l10n.lookup("calllogStartReply");
}, },
callDescription: function(frame) { callDescription: function (frame) {
let name = "<anonymous>"; let name = "<anonymous>";
if (frame.callee.name) { if (frame.callee.name) {
name = frame.callee.name; name = frame.callee.name;
} } else {
else {
let desc = frame.callee.getOwnPropertyDescriptor("displayName"); let desc = frame.callee.getOwnPropertyDescriptor("displayName");
if (desc && desc.value && typeof desc.value == "string") { if (desc && desc.value && typeof desc.value == "string") {
name = desc.value; name = desc.value;
@ -61,7 +60,7 @@ exports.items = [
return name + "(" + args + ")"; return name + "(" + args + ")";
}, },
valueToString: function(value) { valueToString: function (value) {
if (typeof value !== "object" || value === null) { if (typeof value !== "object" || value === null) {
return uneval(value); return uneval(value);
} }
@ -74,7 +73,7 @@ exports.items = [
name: "calllog stop", name: "calllog stop",
description: l10n.lookup("calllogStopDesc"), description: l10n.lookup("calllogStopDesc"),
exec: function(args, context) { exec: function (args, context) {
let numDebuggers = debuggers.length; let numDebuggers = debuggers.length;
if (numDebuggers == 0) { if (numDebuggers == 0) {
return l10n.lookup("calllogStopNoLogging"); return l10n.lookup("calllogStopNoLogging");
@ -111,7 +110,7 @@ exports.items = [
manual: l10n.lookup("calllogChromeSourceTypeManual"), manual: l10n.lookup("calllogChromeSourceTypeManual"),
} }
], ],
exec: function(args, context) { exec: function (args, context) {
let globalObj; let globalObj;
let contentWindow = context.environment.window; let contentWindow = context.environment.window;
@ -136,17 +135,16 @@ exports.items = [
} }
} else { } else {
let chromeWin = context.environment.chromeDocument.defaultView; let chromeWin = context.environment.chromeDocument.defaultView;
let sandbox = new Cu.Sandbox(chromeWin, let sandbox = new Cu.Sandbox(chromeWin, {
{ sandboxPrototype: chromeWin,
sandboxPrototype: chromeWin, wantXrays: false,
wantXrays: false, sandboxName: "gcli-cmd-calllog-chrome"
sandboxName: "gcli-cmd-calllog-chrome" });
});
let returnVal; let returnVal;
try { try {
returnVal = Cu.evalInSandbox(args.source, sandbox, "ECMAv5"); returnVal = Cu.evalInSandbox(args.source, sandbox, "ECMAv5");
sandboxes.push(sandbox); sandboxes.push(sandbox);
} catch(e) { } catch (e) {
// We need to save the message before cleaning up else e contains a dead // We need to save the message before cleaning up else e contains a dead
// object. // object.
let msg = l10n.lookup("callLogChromeEvalException") + ": " + e; let msg = l10n.lookup("callLogChromeEvalException") + ": " + e;
@ -164,7 +162,7 @@ exports.items = [
let dbg = new Debugger(globalObj); let dbg = new Debugger(globalObj);
chromeDebuggers.push(dbg); chromeDebuggers.push(dbg);
dbg.onEnterFrame = function(frame) { dbg.onEnterFrame = function (frame) {
// BUG 773652 - Make the output from the GCLI calllog command nicer // BUG 773652 - Make the output from the GCLI calllog command nicer
contentWindow.console.log(l10n.lookup("callLogChromeMethodCall") + contentWindow.console.log(l10n.lookup("callLogChromeMethodCall") +
": " + this.callDescription(frame)); ": " + this.callDescription(frame));
@ -177,13 +175,14 @@ exports.items = [
return l10n.lookup("calllogChromeStartReply"); return l10n.lookup("calllogChromeStartReply");
}, },
valueToString: function(value) { valueToString: function (value) {
if (typeof value !== "object" || value === null) if (typeof value !== "object" || value === null) {
return uneval(value); return uneval(value);
}
return "[object " + value.class + "]"; return "[object " + value.class + "]";
}, },
callDescription: function(frame) { callDescription: function (frame) {
let name = frame.callee.name || l10n.lookup("callLogChromeAnonFunction"); let name = frame.callee.name || l10n.lookup("callLogChromeAnonFunction");
let args = frame.arguments.map(this.valueToString).join(", "); let args = frame.arguments.map(this.valueToString).join(", ");
return name + "(" + args + ")"; return name + "(" + args + ")";
@ -197,7 +196,7 @@ exports.items = [
get hidden() { get hidden() {
return gcli.hiddenByChromePref(); return gcli.hiddenByChromePref();
}, },
exec: function(args, context) { exec: function (args, context) {
let numDebuggers = chromeDebuggers.length; let numDebuggers = chromeDebuggers.length;
if (numDebuggers == 0) { if (numDebuggers == 0) {
return l10n.lookup("calllogChromeStopNoLogging"); return l10n.lookup("calllogChromeStopNoLogging");

View file

@ -5,18 +5,19 @@
"use strict"; "use strict";
const { Cc, Ci, Cu } = require("chrome"); const { Cc, Ci, Cu } = require("chrome");
const { OS, TextDecoder } = Cu.import("resource://gre/modules/osfile.jsm", {});
const { Task } = require("devtools/shared/task");
const { OS } = Cu.import("resource://gre/modules/osfile.jsm", {});
const { TextEncoder, TextDecoder } = Cu.import('resource://gre/modules/commonjs/toolkit/loader.js', {});
const gcli = require("gcli/index"); const gcli = require("gcli/index");
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
loader.lazyGetter(this, "prefBranch", function() { loader.lazyGetter(this, "prefBranch", function () {
let prefService = Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefService); let prefService = Cc["@mozilla.org/preferences-service;1"]
.getService(Ci.nsIPrefService);
return prefService.getBranch(null).QueryInterface(Ci.nsIPrefBranch2); return prefService.getBranch(null).QueryInterface(Ci.nsIPrefBranch2);
}); });
loader.lazyGetter(this, "supportsString", function() { loader.lazyGetter(this, "supportsString", function () {
return Cc["@mozilla.org/supports-string;1"].createInstance(Ci.nsISupportsString); return Cc["@mozilla.org/supports-string;1"].createInstance(Ci.nsISupportsString);
}); });
@ -66,30 +67,32 @@ function loadItemsFromMozDir() {
// We need to return (a promise of) an array of items from the *.mozcmd // We need to return (a promise of) an array of items from the *.mozcmd
// files in dirName (which we can assume to be a valid directory now) // files in dirName (which we can assume to be a valid directory now)
return statPromise.then(() => { return Task.async(function* () {
yield statPromise;
let itemPromises = []; let itemPromises = [];
let iterator = new OS.File.DirectoryIterator(dirName); let iterator = new OS.File.DirectoryIterator(dirName);
let iterPromise = iterator.forEach(entry => { try {
if (entry.name.match(/.*\.mozcmd$/) && !entry.isDir) { yield iterator.forEach(entry => {
itemPromises.push(loadCommandFile(entry)); if (entry.name.match(/.*\.mozcmd$/) && !entry.isDir) {
} itemPromises.push(loadCommandFile(entry));
}); }
return iterPromise.then(() => {
iterator.close();
return Promise.all(itemPromises).then((itemsArray) => {
return itemsArray.reduce((prev, curr) => {
return prev.concat(curr);
}, []);
}); });
}, reason => { iterator.close(); throw reason; }); iterator.close();
let itemsArray = yield Promise.all(itemPromises);
return itemsArray.reduce((prev, curr) => {
return prev.concat(curr);
}, []);
} catch (e) {
iterator.close();
throw e;
}
}); });
} }
exports.mozDirLoader = function(name) { exports.mozDirLoader = function (name) {
return loadItemsFromMozDir().then(items => { return loadItemsFromMozDir().then(items => {
return { items: items }; return { items };
}); });
}; };
@ -100,10 +103,10 @@ exports.mozDirLoader = function(name) {
*/ */
function loadCommandFile(entry) { function loadCommandFile(entry) {
let readPromise = OS.File.read(entry.path); let readPromise = OS.File.read(entry.path);
return readPromise = readPromise.then(array => { readPromise = readPromise.then(array => {
let decoder = new TextDecoder(); let decoder = new TextDecoder();
let source = decoder.decode(array); let source = decoder.decode(array);
var principal = Cc["@mozilla.org/systemprincipal;1"] let principal = Cc["@mozilla.org/systemprincipal;1"]
.createInstance(Ci.nsIPrincipal); .createInstance(Ci.nsIPrincipal);
let sandbox = new Cu.Sandbox(principal, { let sandbox = new Cu.Sandbox(principal, {
@ -113,11 +116,12 @@ function loadCommandFile(entry) {
if (!Array.isArray(data)) { if (!Array.isArray(data)) {
console.error("Command file '" + entry.name + "' does not have top level array."); console.error("Command file '" + entry.name + "' does not have top level array.");
return; return null;
} }
return data; return data;
}); });
return readPromise;
} }
exports.items = [ exports.items = [
@ -136,7 +140,7 @@ exports.items = [
get hidden() { get hidden() {
return !prefBranch.prefHasUserValue(PREF_DIR); return !prefBranch.prefHasUserValue(PREF_DIR);
}, },
exec: function(args, context) { exec: function (args, context) {
gcli.load(); gcli.load();
let dirName = prefBranch.getComplexValue(PREF_DIR, let dirName = prefBranch.getComplexValue(PREF_DIR,
@ -164,9 +168,10 @@ exports.items = [
], ],
returnType: "string", returnType: "string",
get hidden() { get hidden() {
return true; // !prefBranch.prefHasUserValue(PREF_DIR); // !prefBranch.prefHasUserValue(PREF_DIR);
return true;
}, },
exec: function(args, context) { exec: function (args, context) {
supportsString.data = args.directory; supportsString.data = args.directory;
prefBranch.setComplexValue(PREF_DIR, Ci.nsISupportsString, supportsString); prefBranch.setComplexValue(PREF_DIR, Ci.nsISupportsString, supportsString);

View file

@ -24,7 +24,7 @@ const { Ci, Cc } = require("chrome");
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
const { XPCOMUtils } = require("resource://gre/modules/XPCOMUtils.jsm"); const { XPCOMUtils } = require("resource://gre/modules/XPCOMUtils.jsm");
XPCOMUtils.defineLazyGetter(this, "cookieMgr", function() { XPCOMUtils.defineLazyGetter(this, "cookieMgr", function () {
return Cc["@mozilla.org/cookiemanager;1"].getService(Ci.nsICookieManager2); return Cc["@mozilla.org/cookiemanager;1"].getService(Ci.nsICookieManager2);
}); });
@ -52,9 +52,9 @@ function translateExpires(expires) {
return l10n.lookup("cookieListOutSession"); return l10n.lookup("cookieListOutSession");
} }
let expires_msec = expires * 1000; let expiresMsec = expires * 1000;
return (new Date(expires_msec)).toLocaleString(); return (new Date(expiresMsec)).toLocaleString();
} }
/** /**
@ -86,17 +86,16 @@ exports.items = [
description: l10n.lookup("cookieListDesc"), description: l10n.lookup("cookieListDesc"),
manual: l10n.lookup("cookieListManual"), manual: l10n.lookup("cookieListManual"),
returnType: "cookies", returnType: "cookies",
exec: function(args, context) { exec: function (args, context) {
if (context.environment.target.isRemote) { if (context.environment.target.isRemote) {
throw new Error("The cookie gcli commands only work in a local tab, " + throw new Error("The cookie gcli commands only work in a local tab, " +
"see bug 1221488"); "see bug 1221488");
} }
let host = new URL(context.environment.target.url).host; let host = new URL(context.environment.target.url).host;
let contentWindow = context.environment.window; let contentWindow = context.environment.window;
host = sanitizeHost(host); host = sanitizeHost(host);
let enm = cookieMgr.getCookiesFromHost(host, contentWindow.document. let { originAttributes } = contentWindow.document.nodePrincipal;
nodePrincipal. let enm = cookieMgr.getCookiesFromHost(host, originAttributes);
originAttributes);
let cookies = []; let cookies = [];
while (enm.hasMoreElements()) { while (enm.hasMoreElements()) {
@ -131,17 +130,16 @@ exports.items = [
description: l10n.lookup("cookieRemoveKeyDesc"), description: l10n.lookup("cookieRemoveKeyDesc"),
} }
], ],
exec: function(args, context) { exec: function (args, context) {
if (context.environment.target.isRemote) { if (context.environment.target.isRemote) {
throw new Error("The cookie gcli commands only work in a local tab, " + throw new Error("The cookie gcli commands only work in a local tab, " +
"see bug 1221488"); "see bug 1221488");
} }
let host = new URL(context.environment.target.url).host; let host = new URL(context.environment.target.url).host;
let contentWindow = context.environment.window; let contentWindow = context.environment.window;
host = sanitizeHost(host); host = sanitizeHost(host);
let enm = cookieMgr.getCookiesFromHost(host, contentWindow.document. let { originAttributes } = contentWindow.document.nodePrincipal;
nodePrincipal. let enm = cookieMgr.getCookiesFromHost(host, originAttributes);
originAttributes);
while (enm.hasMoreElements()) { while (enm.hasMoreElements()) {
let cookie = enm.getNext().QueryInterface(Ci.nsICookie); let cookie = enm.getNext().QueryInterface(Ci.nsICookie);
@ -158,7 +156,7 @@ exports.items = [
item: "converter", item: "converter",
from: "cookies", from: "cookies",
to: "view", to: "view",
exec: function(cookies, context) { exec: function (cookies, context) {
if (cookies.length == 0) { if (cookies.length == 0) {
let host = new URL(context.environment.target.url).host; let host = new URL(context.environment.target.url).host;
host = sanitizeHost(host); host = sanitizeHost(host);
@ -275,7 +273,7 @@ exports.items = [
] ]
} }
], ],
exec: function(args, context) { exec: function (args, context) {
if (context.environment.target.isRemote) { if (context.environment.target.isRemote) {
throw new Error("The cookie gcli commands only work in a local tab, " + throw new Error("The cookie gcli commands only work in a local tab, " +
"see bug 1221488"); "see bug 1221488");
@ -283,7 +281,7 @@ exports.items = [
let host = new URL(context.environment.target.url).host; let host = new URL(context.environment.target.url).host;
host = sanitizeHost(host); host = sanitizeHost(host);
let time = Date.parse(args.expires) / 1000; let time = Date.parse(args.expires) / 1000;
let contentWindow = context.environment.window; let contentWindow = context.environment.window;
cookieMgr.add(args.domain ? "." + args.domain : host, cookieMgr.add(args.domain ? "." + args.domain : host,
args.path ? args.path : "/", args.path ? args.path : "/",
args.name, args.name,
@ -292,9 +290,7 @@ exports.items = [
args.httpOnly, args.httpOnly,
args.session, args.session,
time, time,
contentWindow.document. contentWindow.document.nodePrincipal.originAttributes);
nodePrincipal.
originAttributes);
} }
} }
]; ];

View file

@ -4,8 +4,6 @@
"use strict"; "use strict";
const { Cc, Ci } = require("chrome");
const domtemplate = require("gcli/util/domtemplate"); const domtemplate = require("gcli/util/domtemplate");
const csscoverage = require("devtools/shared/fronts/csscoverage"); const csscoverage = require("devtools/shared/fronts/csscoverage");
const l10n = csscoverage.l10n; const l10n = csscoverage.l10n;
@ -37,7 +35,7 @@ exports.items = [
manual: l10n.lookup("csscoverageStartNoReloadManual") manual: l10n.lookup("csscoverageStartNoReloadManual")
} }
], ],
exec: function*(args, context) { exec: function* (args, context) {
let usage = yield csscoverage.getUsage(context.environment.target); let usage = yield csscoverage.getUsage(context.environment.target);
if (usage == null) { if (usage == null) {
throw new Error(l10n.lookup("csscoverageNoRemoteError")); throw new Error(l10n.lookup("csscoverageNoRemoteError"));
@ -52,7 +50,7 @@ exports.items = [
name: "csscoverage stop", name: "csscoverage stop",
hidden: true, hidden: true,
description: l10n.lookup("csscoverageStopDesc2"), description: l10n.lookup("csscoverageStopDesc2"),
exec: function*(args, context) { exec: function* (args, context) {
let target = context.environment.target; let target = context.environment.target;
let usage = yield csscoverage.getUsage(target); let usage = yield csscoverage.getUsage(target);
if (usage == null) { if (usage == null) {
@ -68,7 +66,7 @@ exports.items = [
name: "csscoverage oneshot", name: "csscoverage oneshot",
hidden: true, hidden: true,
description: l10n.lookup("csscoverageOneShotDesc2"), description: l10n.lookup("csscoverageOneShotDesc2"),
exec: function*(args, context) { exec: function* (args, context) {
let target = context.environment.target; let target = context.environment.target;
let usage = yield csscoverage.getUsage(target); let usage = yield csscoverage.getUsage(target);
if (usage == null) { if (usage == null) {
@ -85,25 +83,27 @@ exports.items = [
hidden: true, hidden: true,
description: l10n.lookup("csscoverageToggleDesc2"), description: l10n.lookup("csscoverageToggleDesc2"),
state: { state: {
isChecked: function(target) { isChecked: function (target) {
return csscoverage.getUsage(target).then(usage => { return csscoverage.getUsage(target).then(usage => {
return usage.isRunning(); return usage.isRunning();
}); });
}, },
onChange: function(target, handler) { onChange: function (target, handler) {
csscoverage.getUsage(target).then(usage => { csscoverage.getUsage(target).then(usage => {
this.handler = ev => { handler("state-change", ev); }; this.handler = ev => {
handler("state-change", ev);
};
usage.on("state-change", this.handler); usage.on("state-change", this.handler);
}); });
}, },
offChange: function(target, handler) { offChange: function (target, handler) {
csscoverage.getUsage(target).then(usage => { csscoverage.getUsage(target).then(usage => {
usage.off("state-change", this.handler); usage.off("state-change", this.handler);
this.handler = undefined; this.handler = undefined;
}); });
}, },
}, },
exec: function*(args, context) { exec: function* (args, context) {
let target = context.environment.target; let target = context.environment.target;
let usage = yield csscoverage.getUsage(target); let usage = yield csscoverage.getUsage(target);
if (usage == null) { if (usage == null) {
@ -120,7 +120,7 @@ exports.items = [
name: "csscoverage report", name: "csscoverage report",
hidden: true, hidden: true,
description: l10n.lookup("csscoverageReportDesc2"), description: l10n.lookup("csscoverageReportDesc2"),
exec: function*(args, context) { exec: function* (args, context) {
let usage = yield csscoverage.getUsage(context.environment.target); let usage = yield csscoverage.getUsage(context.environment.target);
if (usage == null) { if (usage == null) {
throw new Error(l10n.lookup("csscoverageNoRemoteError")); throw new Error(l10n.lookup("csscoverageNoRemoteError"));
@ -137,7 +137,7 @@ exports.items = [
item: "converter", item: "converter",
from: "csscoveragePageReport", from: "csscoveragePageReport",
to: "dom", to: "dom",
exec: function*(csscoveragePageReport, context) { exec: function* (csscoveragePageReport, context) {
let target = context.environment.target; let target = context.environment.target;
let toolbox = yield gDevTools.showToolbox(target, "styleeditor"); let toolbox = yield gDevTools.showToolbox(target, "styleeditor");
@ -185,7 +185,8 @@ exports.items = [
// Create a new chart. // Create a new chart.
let container = host.querySelector(".csscoverage-report-chart"); let container = host.querySelector(".csscoverage-report-chart");
let chart = Chart.PieTable(panel._panelDoc, { let chart = Chart.PieTable(panel._panelDoc, {
diameter: 200, // px // px
diameter: 200,
title: "CSS Usage", title: "CSS Usage",
data: [ data: [
{ size: data.summary.preload, label: "Used Preload" }, { size: data.summary.preload, label: "Used Preload" },

View file

@ -4,25 +4,24 @@
"use strict"; "use strict";
const { Cc, Ci, Cu, CC } = require("chrome"); const { Cc, Ci, CC } = require("chrome");
const Services = require("Services"); const Services = require("Services");
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
const dirService = Cc["@mozilla.org/file/directory_service;1"] const dirService = Cc["@mozilla.org/file/directory_service;1"]
.getService(Ci.nsIProperties); .getService(Ci.nsIProperties);
function showFolder(aPath) { function showFolder(path) {
let nsLocalFile = CC("@mozilla.org/file/local;1", "nsILocalFile", let NSLocalFile = CC("@mozilla.org/file/local;1", "nsILocalFile",
"initWithPath"); "initWithPath");
try { try {
let file = new nsLocalFile(aPath); let file = new NSLocalFile(path);
if (file.exists()) { if (file.exists()) {
file.reveal(); file.reveal();
return l10n.lookupFormat("folderOpenDirResult", [aPath]); return l10n.lookupFormat("folderOpenDirResult", [path]);
} else {
return l10n.lookup("folderInvalidPath");
} }
return l10n.lookup("folderInvalidPath");
} catch (e) { } catch (e) {
return l10n.lookup("folderInvalidPath"); return l10n.lookup("folderInvalidPath");
} }
@ -47,7 +46,7 @@ exports.items = [
} }
], ],
returnType: "string", returnType: "string",
exec: function(args, context) { exec: function (args, context) {
let dirName = args.path; let dirName = args.path;
// replaces ~ with the home directory path in unix and windows // replaces ~ with the home directory path in unix and windows
@ -67,7 +66,7 @@ exports.items = [
name: "folder openprofile", name: "folder openprofile",
description: l10n.lookup("folderOpenProfileDesc"), description: l10n.lookup("folderOpenProfileDesc"),
returnType: "string", returnType: "string",
exec: function(args, context) { exec: function (args, context) {
// Get the profile directory. // Get the profile directory.
let currProfD = Services.dirsvc.get("ProfD", Ci.nsIFile); let currProfD = Services.dirsvc.get("ProfD", Ci.nsIFile);
let profileDir = currProfD.path; let profileDir = currProfD.path;

View file

@ -103,7 +103,7 @@ exports.items = [
] ]
} }
], ],
exec: function(args, context) { exec: function (args, context) {
// Remove all existing highlighters unless told otherwise // Remove all existing highlighters unless told otherwise
if (!args.keep) { if (!args.keep) {
unhighlightAll(); unhighlightAll();

View file

@ -107,7 +107,7 @@ try {
/** /**
* Add modules to a system for use in a content process (but don't call load) * Add modules to a system for use in a content process (but don't call load)
*/ */
exports.addAllItemsByModule = function(system) { exports.addAllItemsByModule = function (system) {
system.addItemsByModule(exports.baseModules, { delayedLoad: true }); system.addItemsByModule(exports.baseModules, { delayedLoad: true });
system.addItemsByModule(exports.devtoolsModules, { delayedLoad: true }); system.addItemsByModule(exports.devtoolsModules, { delayedLoad: true });
system.addItemsByModule(exports.devtoolsToolModules, { delayedLoad: true }); system.addItemsByModule(exports.devtoolsToolModules, { delayedLoad: true });
@ -133,7 +133,7 @@ var customProperties = [ "buttonId", "buttonClass", "tooltipText" ];
* Create a system which connects to a GCLI in a remote target * Create a system which connects to a GCLI in a remote target
* @return Promise<System> for the given target * @return Promise<System> for the given target
*/ */
exports.getSystem = function(target) { exports.getSystem = function (target) {
const existingLinks = linksForTarget.get(target); const existingLinks = linksForTarget.get(target);
if (existingLinks != null) { if (existingLinks != null) {
existingLinks.refs++; existingLinks.refs++;
@ -164,7 +164,7 @@ exports.getSystem = function(target) {
* Someone that called getSystem doesn't need it any more, so decrement the * Someone that called getSystem doesn't need it any more, so decrement the
* count of users of the system for that target, and destroy if needed * count of users of the system for that target, and destroy if needed
*/ */
exports.releaseSystem = function(target) { exports.releaseSystem = function (target) {
const links = linksForTarget.get(target); const links = linksForTarget.get(target);
if (links == null) { if (links == null) {
throw new Error("releaseSystem called for unknown target"); throw new Error("releaseSystem called for unknown target");

View file

@ -53,7 +53,7 @@ exports.items = [
}, },
description: l10n.lookup("injectLibraryDesc") description: l10n.lookup("injectLibraryDesc")
}], }],
exec: function*(args, context) { exec: function* (args, context) {
let document = context.environment.document; let document = context.environment.document;
let library = args.library; let library = args.library;
let name = (library.type === "selection") ? let name = (library.type === "selection") ?
@ -68,7 +68,7 @@ exports.items = [
try { try {
// Check if URI is valid // Check if URI is valid
Services.io.newURI(src, null, null); Services.io.newURI(src, null, null);
} catch(e) { } catch (e) {
return l10n.lookupFormat("injectFailed", [name]); return l10n.lookupFormat("injectFailed", [name]);
} }

View file

@ -4,7 +4,7 @@
"use strict"; "use strict";
const { Cc, Ci, Cu } = require("chrome"); const { Cc } = require("chrome");
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
const XMLHttpRequest = Cc["@mozilla.org/xmlextras/xmlhttprequest;1"]; const XMLHttpRequest = Cc["@mozilla.org/xmlextras/xmlhttprequest;1"];
@ -19,7 +19,7 @@ exports.items = [
runAt: "client", runAt: "client",
name: "jsb", name: "jsb",
description: l10n.lookup("jsbDesc"), description: l10n.lookup("jsbDesc"),
returnValue:"string", returnValue: "string",
params: [ params: [
{ {
name: "url", name: "url",
@ -91,7 +91,8 @@ exports.items = [
] ]
} }
], ],
exec: function(args, context) { exec: function (args, context) {
/* eslint-disable camelcase */
let opts = { let opts = {
indent_size: args.indentSize, indent_size: args.indentSize,
indent_char: args.indentChar, indent_char: args.indentChar,
@ -103,12 +104,12 @@ exports.items = [
space_before_conditional: !args.noSpaceBeforeConditional, space_before_conditional: !args.noSpaceBeforeConditional,
unescape_strings: args.unescapeStrings unescape_strings: args.unescapeStrings
}; };
/* eslint-enable camelcase */
let xhr = new XMLHttpRequest(); let xhr = new XMLHttpRequest();
let deferred = context.defer(); let deferred = context.defer();
xhr.onreadystatechange = function() { xhr.onreadystatechange = function () {
if (xhr.readyState == 4) { if (xhr.readyState == 4) {
if (xhr.status == 200 || xhr.status == 0) { if (xhr.status == 200 || xhr.status == 0) {
let result = beautify.js(xhr.responseText, opts); let result = beautify.js(xhr.responseText, opts);
@ -120,12 +121,12 @@ exports.items = [
deferred.reject("Unable to load page to beautify: " + args.url + " " + deferred.reject("Unable to load page to beautify: " + args.url + " " +
xhr.status + " " + xhr.statusText); xhr.status + " " + xhr.statusText);
} }
}; }
} };
try { try {
xhr.open("GET", args.url, true); xhr.open("GET", args.url, true);
xhr.send(null); xhr.send(null);
} catch(e) { } catch (e) {
return l10n.lookup("jsbInvalidURL"); return l10n.lookup("jsbInvalidURL");
} }
return deferred.promise; return deferred.promise;

View file

@ -69,7 +69,7 @@ exports.items = [
}, },
], ],
exec: function (args, context) { exec: function (args, context) {
var listener = debuggerServer.createListener(); let listener = debuggerServer.createListener();
if (!listener) { if (!listener) {
throw new Error(l10n.lookup("listenDisabledOutput")); throw new Error(l10n.lookup("listenDisabledOutput"));
} }

View file

@ -28,7 +28,7 @@ exports.items = [{
defaultValue: null, defaultValue: null,
description: l10n.lookup("mdnCssProp") description: l10n.lookup("mdnCssProp")
}], }],
exec: function(args) { exec: function (args) {
if (!MdnDocsWidget) { if (!MdnDocsWidget) {
return null; return null;
} }
@ -47,7 +47,7 @@ exports.items = [{
item: "converter", item: "converter",
from: "cssPropertyOutput", from: "cssPropertyOutput",
to: "dom", to: "dom",
exec: function(result, context) { exec: function (result, context) {
let propertyName = result.property; let propertyName = result.property;
let document = context.document; let document = context.document;

View file

@ -40,7 +40,7 @@ exports.items = [
onChange: (target, handler) => eventEmitter.on("changed", handler), onChange: (target, handler) => eventEmitter.on("changed", handler),
offChange: (target, handler) => eventEmitter.off("changed", handler) offChange: (target, handler) => eventEmitter.off("changed", handler)
}, },
exec: function*(args, context) { exec: function* (args, context) {
let { target } = context.environment; let { target } = context.environment;
// Pipe the call to the server command. // Pipe the call to the server command.
@ -73,7 +73,7 @@ exports.items = [
runAt: "server", runAt: "server",
hidden: true, hidden: true,
returnType: "highlighterVisibility", returnType: "highlighterVisibility",
exec: function(args, context) { exec: function (args, context) {
let env = context.environment; let env = context.environment;
let { document } = env; let { document } = env;
let id = getOuterId(env.window); let id = getOuterId(env.window);
@ -99,8 +99,8 @@ exports.items = [
// window is refreshed or closed with the measuring tool shown. // window is refreshed or closed with the measuring tool shown.
events.once(highlighter, "destroy", () => { events.once(highlighter, "destroy", () => {
if (highlighters.has(document)) { if (highlighters.has(document)) {
let { environment } = highlighters.get(document); let { environment: toDestroy } = highlighters.get(document);
environment.destroy(); toDestroy.destroy();
highlighters.delete(document); highlighters.delete(document);
} }
}); });

View file

@ -38,7 +38,7 @@ exports.items = [
} }
} }
], ],
exec: function(args, context) { exec: function (args, context) {
let contentViewer = getContentViewer(context); let contentViewer = getContentViewer(context);
contentViewer.emulateMedium(args.type); contentViewer.emulateMedium(args.type);
} }
@ -48,7 +48,7 @@ exports.items = [
runAt: "server", runAt: "server",
name: "media reset", name: "media reset",
description: l10n.lookup("mediaResetDesc"), description: l10n.lookup("mediaResetDesc"),
exec: function(args, context) { exec: function (args, context) {
let contentViewer = getContentViewer(context); let contentViewer = getContentViewer(context);
contentViewer.stopEmulatingMedium(); contentViewer.stopEmulatingMedium();
} }

View file

@ -4,7 +4,7 @@
"use strict"; "use strict";
const { Cc, Ci, Cu } = require("chrome"); const { Cc, Ci } = require("chrome");
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
exports.items = [ exports.items = [
@ -37,7 +37,7 @@ exports.items = [
name: "selector", name: "selector",
type: "string", type: "string",
description: l10n.lookup("pagemodReplaceSelectorDesc"), description: l10n.lookup("pagemodReplaceSelectorDesc"),
defaultValue: "*:not(script):not(style):not(embed):not(object):not(frame):not(iframe):not(frameset)", defaultValue: "*:not(script):not(style):not(embed):not(object):not(frame):not(iframe):not(frameset)", // eslint-disable-line
}, },
{ {
name: "root", name: "root",
@ -63,10 +63,10 @@ exports.items = [
}, },
], ],
// Make a given string safe to use in a regular expression. // Make a given string safe to use in a regular expression.
escapeRegex: function(aString) { escapeRegex: function (string) {
return aString.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&"); return string.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&");
}, },
exec: function(args, context) { exec: function (args, context) {
let searchTextNodes = !args.attrOnly; let searchTextNodes = !args.attrOnly;
let searchAttributes = !args.contentOnly; let searchAttributes = !args.contentOnly;
let regexOptions = args.ignoreCase ? "ig" : "g"; let regexOptions = args.ignoreCase ? "ig" : "g";
@ -153,7 +153,7 @@ exports.items = [
description: l10n.lookup("pagemodRemoveElementIfEmptyOnlyDesc"), description: l10n.lookup("pagemodRemoveElementIfEmptyOnlyDesc"),
}, },
], ],
exec: function(args, context) { exec: function (args, context) {
let root = args.root || context.environment.document; let root = args.root || context.environment.document;
let elements = Array.prototype.slice.call(root.querySelectorAll(args.search)); let elements = Array.prototype.slice.call(root.querySelectorAll(args.search));
@ -207,7 +207,7 @@ exports.items = [
description: l10n.lookup("pagemodRemoveAttributeIgnoreCaseDesc"), description: l10n.lookup("pagemodRemoveAttributeIgnoreCaseDesc"),
}, },
], ],
exec: function(args, context) { exec: function (args, context) {
let root = args.root || context.environment.document; let root = args.root || context.environment.document;
let regexOptions = args.ignoreCase ? "ig" : "g"; let regexOptions = args.ignoreCase ? "ig" : "g";
let attributeRegex = new RegExp(args.searchAttributes, regexOptions); let attributeRegex = new RegExp(args.searchAttributes, regexOptions);
@ -221,7 +221,7 @@ exports.items = [
continue; continue;
} }
var attrs = Array.prototype.slice.call(element.attributes); let attrs = Array.prototype.slice.call(element.attributes);
for (let y = 0; y < attrs.length; y++) { for (let y = 0; y < attrs.length; y++) {
let attr = attrs[y]; let attr = attrs[y];
if (attributeRegex.test(attr.name)) { if (attributeRegex.test(attr.name)) {
@ -255,7 +255,7 @@ exports.items = [
defaultValue: "window" defaultValue: "window"
} }
], ],
exec: function(args, context) { exec: function (args, context) {
let html = context.environment.document.documentElement.outerHTML; let html = context.environment.document.documentElement.outerHTML;
if (args.destination === "stdout") { if (args.destination === "stdout") {
return html; return html;
@ -265,12 +265,12 @@ exports.items = [
let clipboard = Cc["@mozilla.org/widget/clipboardhelper;1"] let clipboard = Cc["@mozilla.org/widget/clipboardhelper;1"]
.getService(Ci.nsIClipboardHelper); .getService(Ci.nsIClipboardHelper);
clipboard.copyString(url); clipboard.copyString(url);
return ''; return "";
} }
let url = "data:text/plain;charset=utf8," + encodeURIComponent(html); let url = "data:text/plain;charset=utf8," + encodeURIComponent(html);
context.environment.window.open(url); context.environment.window.open(url);
return ''; return "";
} }
} }
]; ];

View file

@ -12,7 +12,7 @@ var telemetry;
try { try {
const Telemetry = require("devtools/client/shared/telemetry"); const Telemetry = require("devtools/client/shared/telemetry");
telemetry = new Telemetry(); telemetry = new Telemetry();
} catch(e) { } catch (e) {
// DevTools Telemetry module only available in Firefox // DevTools Telemetry module only available in Firefox
} }
@ -115,7 +115,7 @@ exports.items = [
} }
] ]
}], }],
exec: function*(args, context) { exec: function* (args, context) {
if (!args.chrome) { if (!args.chrome) {
const output = yield context.updateExec("paintflashing_server --state on"); const output = yield context.updateExec("paintflashing_server --state on");
@ -144,7 +144,7 @@ exports.items = [
} }
] ]
}], }],
exec: function*(args, context) { exec: function* (args, context) {
if (!args.chrome) { if (!args.chrome) {
const output = yield context.updateExec("paintflashing_server --state off"); const output = yield context.updateExec("paintflashing_server --state off");
@ -169,7 +169,7 @@ exports.items = [
tooltipText: l10n.lookup("paintflashingTooltip"), tooltipText: l10n.lookup("paintflashingTooltip"),
description: l10n.lookup("paintflashingToggleDesc"), description: l10n.lookup("paintflashingToggleDesc"),
manual: l10n.lookup("paintflashingManual"), manual: l10n.lookup("paintflashingManual"),
exec: function*(args, context) { exec: function* (args, context) {
const output = yield context.updateExec("paintflashing_server --state toggle"); const output = yield context.updateExec("paintflashing_server --state toggle");
onPaintFlashingChanged(context.environment.target, output.data); onPaintFlashingChanged(context.environment.target, output.data);
@ -190,7 +190,7 @@ exports.items = [
}, },
], ],
returnType: "paintFlashingState", returnType: "paintFlashingState",
exec: function(args, context) { exec: function (args, context) {
let { window } = context.environment; let { window } = context.environment;
let id = getOuterId(window); let id = getOuterId(window);
let flashing = setPaintFlashing(window, args.state); let flashing = setPaintFlashing(window, args.state);

View file

@ -1,24 +1,24 @@
/* This Source Code Form is subject to the terms of the Mozilla Public /* 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 * 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/. */ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
"use strict"; "use strict";
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
exports.items = [ exports.items = [
{ {
item: "command", item: "command",
runAt: "server", runAt: "server",
name: "qsa", name: "qsa",
description: l10n.lookup("qsaDesc"), description: l10n.lookup("qsaDesc"),
params: [{ params: [{
name: "query", name: "query",
type: "nodelist", type: "nodelist",
description: l10n.lookup("qsaQueryDesc") description: l10n.lookup("qsaQueryDesc")
}], }],
exec: function(args, context) { exec: function (args, context) {
return args.query.length; return args.query.length;
} }
} }
]; ];

View file

@ -4,7 +4,7 @@
"use strict"; "use strict";
const { Cc, Ci, Cu } = require("chrome"); const { Cc, Ci } = require("chrome");
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
const Services = require("Services"); const Services = require("Services");

View file

@ -39,7 +39,7 @@ exports.items = [
onChange: (target, handler) => eventEmitter.on("changed", handler), onChange: (target, handler) => eventEmitter.on("changed", handler),
offChange: (target, handler) => eventEmitter.off("changed", handler) offChange: (target, handler) => eventEmitter.off("changed", handler)
}, },
exec: function*(args, context) { exec: function* (args, context) {
let { target } = context.environment; let { target } = context.environment;
// Pipe the call to the server command. // Pipe the call to the server command.
@ -71,7 +71,7 @@ exports.items = [
runAt: "server", runAt: "server",
hidden: true, hidden: true,
returnType: "highlighterVisibility", returnType: "highlighterVisibility",
exec: function(args, context) { exec: function (args, context) {
let env = context.environment; let env = context.environment;
let { document } = env; let { document } = env;
let id = getOuterId(env.window); let id = getOuterId(env.window);
@ -97,8 +97,8 @@ exports.items = [
// window is refreshed or closed with the rulers shown. // window is refreshed or closed with the rulers shown.
events.once(highlighter, "destroy", () => { events.once(highlighter, "destroy", () => {
if (highlighters.has(document)) { if (highlighters.has(document)) {
let { environment } = highlighters.get(document); let { environment: toDestroy } = highlighters.get(document);
environment.destroy(); toDestroy.destroy();
highlighters.delete(document); highlighters.delete(document);
} }
}); });

View file

@ -9,7 +9,6 @@ const l10n = require("gcli/l10n");
const Services = require("Services"); const Services = require("Services");
const { NetUtil } = require("resource://gre/modules/NetUtil.jsm"); const { NetUtil } = require("resource://gre/modules/NetUtil.jsm");
const { getRect } = require("devtools/shared/layout/utils"); const { getRect } = require("devtools/shared/layout/utils");
const promise = require("promise");
const defer = require("devtools/shared/defer"); const defer = require("devtools/shared/defer");
const { Task } = require("devtools/shared/task"); const { Task } = require("devtools/shared/task");
@ -19,11 +18,6 @@ loader.lazyImporter(this, "FileUtils", "resource://gre/modules/FileUtils.jsm");
loader.lazyImporter(this, "PrivateBrowsingUtils", loader.lazyImporter(this, "PrivateBrowsingUtils",
"resource://gre/modules/PrivateBrowsingUtils.jsm"); "resource://gre/modules/PrivateBrowsingUtils.jsm");
const BRAND_SHORT_NAME = Cc["@mozilla.org/intl/stringbundle;1"]
.getService(Ci.nsIStringBundleService)
.createBundle("chrome://branding/locale/brand.properties")
.GetStringFromName("brandShortName");
// String used as an indication to generate default file name in the following // String used as an indication to generate default file name in the following
// format: "Screen Shot yyyy-mm-dd at HH.MM.SS.png" // format: "Screen Shot yyyy-mm-dd at HH.MM.SS.png"
const FILENAME_DEFAULT_VALUE = " "; const FILENAME_DEFAULT_VALUE = " ";
@ -128,7 +122,7 @@ exports.items = [
item: "converter", item: "converter",
from: "imageSummary", from: "imageSummary",
to: "dom", to: "dom",
exec: function(imageSummary, context) { exec: function (imageSummary, context) {
const document = context.document; const document = context.document;
const root = document.createElement("div"); const root = document.createElement("div");
@ -142,7 +136,8 @@ exports.items = [
// Add the thumbnail image // Add the thumbnail image
if (imageSummary.data != null) { if (imageSummary.data != null) {
const image = context.document.createElement("div"); const image = context.document.createElement("div");
const previewHeight = parseInt(256 * imageSummary.height / imageSummary.width); const previewHeight = parseInt(256 * imageSummary.height / imageSummary.width,
10);
const style = "" + const style = "" +
"width: 256px;" + "width: 256px;" +
"height: " + previewHeight + "px;" + "height: " + previewHeight + "px;" +
@ -240,9 +235,7 @@ function captureScreenshot(args, document) {
}, args.delay * 1000); }, args.delay * 1000);
}); });
} }
else { return createScreenshotData(document, args);
return createScreenshotData(document, args);
}
} }
/** /**
@ -260,8 +253,8 @@ function saveScreenshot(args, context, reply) {
return Promise.all([ return Promise.all([
args.clipboard ? saveToClipboard(context, reply) : SKIP, args.clipboard ? saveToClipboard(context, reply) : SKIP,
args.imgur ? uploadToImgur(reply) : SKIP, args.imgur ? uploadToImgur(reply) : SKIP,
fileNeeded ? saveToFile(context, reply) : SKIP, fileNeeded ? saveToFile(context, reply) : SKIP,
]).then(() => reply); ]).then(() => reply);
} }
@ -283,15 +276,13 @@ function createScreenshotData(document, args) {
if (args.fullpage) { if (args.fullpage) {
// Bug 961832: GCLI screenshot shows fixed position element in wrong // Bug 961832: GCLI screenshot shows fixed position element in wrong
// position if we don't scroll to top // position if we don't scroll to top
window.scrollTo(0,0); window.scrollTo(0, 0);
width = window.innerWidth + window.scrollMaxX - window.scrollMinX; width = window.innerWidth + window.scrollMaxX - window.scrollMinX;
height = window.innerHeight + window.scrollMaxY - window.scrollMinY; height = window.innerHeight + window.scrollMaxY - window.scrollMinY;
filename = filename.replace(".png", "-fullpage.png"); filename = filename.replace(".png", "-fullpage.png");
} } else if (args.selector) {
else if (args.selector) {
({ top, left, width, height } = getRect(window, args.selector, window)); ({ top, left, width, height } = getRect(window, args.selector, window));
} } else {
else {
left = window.scrollX; left = window.scrollX;
top = window.scrollY; top = window.scrollY;
width = window.innerWidth; width = window.innerWidth;
@ -347,7 +338,7 @@ function getFilename(defaultName) {
const date = new Date(); const date = new Date();
let dateString = date.getFullYear() + "-" + (date.getMonth() + 1) + let dateString = date.getFullYear() + "-" + (date.getMonth() + 1) +
"-" + date.getDate(); "-" + date.getDate();
dateString = dateString.split("-").map(function(part) { dateString = dateString.split("-").map(function (part) {
if (part.length == 1) { if (part.length == 1) {
part = "0" + part; part = "0" + part;
} }
@ -399,8 +390,7 @@ function saveToClipboard(context, reply) {
clip.setData(trans, null, Ci.nsIClipboard.kGlobalClipboard); clip.setData(trans, null, Ci.nsIClipboard.kGlobalClipboard);
reply.destinations.push(l10n.lookup("screenshotCopied")); reply.destinations.push(l10n.lookup("screenshotCopied"));
} } catch (ex) {
catch (ex) {
console.error(ex); console.error(ex);
reply.destinations.push(l10n.lookup("screenshotErrorCopying")); reply.destinations.push(l10n.lookup("screenshotErrorCopying"));
} }
@ -422,14 +412,15 @@ function uploadToImgur(reply) {
fd.append("title", reply.filename); fd.append("title", reply.filename);
const postURL = Services.prefs.getCharPref("devtools.gcli.imgurUploadURL"); const postURL = Services.prefs.getCharPref("devtools.gcli.imgurUploadURL");
const clientID = "Client-ID " + Services.prefs.getCharPref("devtools.gcli.imgurClientID"); const clientID = "Client-ID " +
Services.prefs.getCharPref("devtools.gcli.imgurClientID");
xhr.open("POST", postURL); xhr.open("POST", postURL);
xhr.setRequestHeader("Authorization", clientID); xhr.setRequestHeader("Authorization", clientID);
xhr.send(fd); xhr.send(fd);
xhr.responseType = "json"; xhr.responseType = "json";
xhr.onreadystatechange = function() { xhr.onreadystatechange = function () {
if (xhr.readyState == 4) { if (xhr.readyState == 4) {
if (xhr.status == 200) { if (xhr.status == 200) {
reply.href = xhr.response.data.link; reply.href = xhr.response.data.link;
@ -477,7 +468,7 @@ function DownloadListener(win, transfer) {
} }
DownloadListener.prototype = { DownloadListener.prototype = {
QueryInterface: function(iid) { QueryInterface: function (iid) {
if (iid.equals(Ci.nsIInterfaceRequestor) || if (iid.equals(Ci.nsIInterfaceRequestor) ||
iid.equals(Ci.nsIWebProgressListener) || iid.equals(Ci.nsIWebProgressListener) ||
iid.equals(Ci.nsIWebProgressListener2) || iid.equals(Ci.nsIWebProgressListener2) ||
@ -487,7 +478,7 @@ DownloadListener.prototype = {
throw Cr.NS_ERROR_NO_INTERFACE; throw Cr.NS_ERROR_NO_INTERFACE;
}, },
getInterface: function(iid) { getInterface: function (iid) {
if (iid.equals(Ci.nsIAuthPrompt) || if (iid.equals(Ci.nsIAuthPrompt) ||
iid.equals(Ci.nsIAuthPrompt2)) { iid.equals(Ci.nsIAuthPrompt2)) {
let ww = Cc["@mozilla.org/embedcomp/window-watcher;1"] let ww = Cc["@mozilla.org/embedcomp/window-watcher;1"]
@ -498,7 +489,7 @@ DownloadListener.prototype = {
throw Cr.NS_ERROR_NO_INTERFACE; throw Cr.NS_ERROR_NO_INTERFACE;
}, },
onStateChange: function(webProgress, request, state, status) { onStateChange: function (webProgress, request, state, status) {
// Check if the download has completed // Check if the download has completed
if ((state & Ci.nsIWebProgressListener.STATE_STOP) && if ((state & Ci.nsIWebProgressListener.STATE_STOP) &&
(state & Ci.nsIWebProgressListener.STATE_IS_NETWORK)) { (state & Ci.nsIWebProgressListener.STATE_IS_NETWORK)) {
@ -517,7 +508,7 @@ DownloadListener.prototype = {
* Save the screenshot data to disk, returning a promise which is resolved on * Save the screenshot data to disk, returning a promise which is resolved on
* completion. * completion.
*/ */
var saveToFile = Task.async(function*(context, reply) { var saveToFile = Task.async(function* (context, reply) {
let document = context.environment.chromeDocument; let document = context.environment.chromeDocument;
let window = context.environment.chromeWindow; let window = context.environment.chromeWindow;

View file

@ -13,17 +13,15 @@
"use strict"; "use strict";
const { Cc, Ci, Cu, CC } = require("chrome"); const { Ci } = require("chrome");
const l10n = require("gcli/l10n"); const l10n = require("gcli/l10n");
const CSP = Cc["@mozilla.org/cspcontext;1"].getService(Ci.nsIContentSecurityPolicy);
const GOOD_IMG_SRC = "chrome://browser/content/gcli_sec_good.svg"; const GOOD_IMG_SRC = "chrome://browser/content/gcli_sec_good.svg";
const MOD_IMG_SRC = "chrome://browser/content/gcli_sec_moderate.svg"; const MOD_IMG_SRC = "chrome://browser/content/gcli_sec_moderate.svg";
const BAD_IMG_SRC = "chrome://browser/content/gcli_sec_bad.svg"; const BAD_IMG_SRC = "chrome://browser/content/gcli_sec_bad.svg";
// special handling within policy // special handling within policy
const POLICY_REPORT_ONLY = "report-only" const POLICY_REPORT_ONLY = "report-only";
// special handling of directives // special handling of directives
const DIR_UPGRADE_INSECURE = "upgrade-insecure-requests"; const DIR_UPGRADE_INSECURE = "upgrade-insecure-requests";
@ -42,7 +40,11 @@ const CONTENT_SECURITY_POLICY_REPORT_ONLY_MSG = l10n.lookup("securityCSPROHeader
const NEXT_URI_HEADER = l10n.lookup("securityReferrerNextURI"); const NEXT_URI_HEADER = l10n.lookup("securityReferrerNextURI");
const CALCULATED_REFERRER_HEADER = l10n.lookup("securityReferrerCalculatedReferrer"); const CALCULATED_REFERRER_HEADER = l10n.lookup("securityReferrerCalculatedReferrer");
/* The official names from the W3C Referrer Policy Draft http://www.w3.org/TR/referrer-policy/ */ /* The official names from the W3C Referrer Policy Draft http://www.w3.org/TR/referrer-policy/ */
const REFERRER_POLICY_NAMES = [ "None When Downgrade (default)", "None", "Origin Only", "Origin When Cross-Origin", "Unsafe URL" ]; const REFERRER_POLICY_NAMES = [
"None When Downgrade (default)",
"None", "Origin Only",
"Origin When Cross-Origin", "Unsafe URL"
];
exports.items = [ exports.items = [
{ {
@ -59,24 +61,23 @@ exports.items = [
description: l10n.lookup("securityCSPDesc"), description: l10n.lookup("securityCSPDesc"),
manual: l10n.lookup("securityCSPManual"), manual: l10n.lookup("securityCSPManual"),
returnType: "securityCSPInfo", returnType: "securityCSPInfo",
exec: function(args, context) { exec: function (args, context) {
let cspJSON = context.environment.document.nodePrincipal.cspJSON;
let cspOBJ = JSON.parse(cspJSON);
var cspJSON = context.environment.document.nodePrincipal.cspJSON; let outPolicies = [];
var cspOBJ = JSON.parse(cspJSON);
var outPolicies = []; let policies = cspOBJ["csp-policies"];
var policies = cspOBJ["csp-policies"];
// loop over all the different policies // loop over all the different policies
for (var csp in policies) { for (let csp in policies) {
var curPolicy = policies[csp]; let curPolicy = policies[csp];
// loop over all the directive-values within that policy // loop over all the directive-values within that policy
var outDirectives = []; let outDirectives = [];
var outHeader = CONTENT_SECURITY_POLICY_MSG; let outHeader = CONTENT_SECURITY_POLICY_MSG;
for (var dir in curPolicy) { for (let dir in curPolicy) {
var curDir = curPolicy[dir]; let curDir = curPolicy[dir];
// when iterating properties within the obj we might also // when iterating properties within the obj we might also
// encounter the 'report-only' flag, which is not a csp directive. // encounter the 'report-only' flag, which is not a csp directive.
@ -88,7 +89,7 @@ exports.items = [
} }
// loop over all the directive-sources within that directive // loop over all the directive-sources within that directive
var outSrcs = []; let outSrcs = [];
// special case handling for the directives // special case handling for the directives
// upgrade-insecure-requests and block-all-mixed-content // upgrade-insecure-requests and block-all-mixed-content
@ -97,17 +98,19 @@ exports.items = [
dir === DIR_BLOCK_ALL_MIXED_CONTENT) { dir === DIR_BLOCK_ALL_MIXED_CONTENT) {
outSrcs.push({ outSrcs.push({
icon: GOOD_IMG_SRC, icon: GOOD_IMG_SRC,
src: "", // no src // no src
desc: "" // no description src: "",
// no description
desc: ""
}); });
} }
for (var src in curDir) { for (let src in curDir) {
var curSrc = curDir[src]; let curSrc = curDir[src];
// the default icon and descritpion of the directive-src // the default icon and descritpion of the directive-src
var outIcon = GOOD_IMG_SRC; let outIcon = GOOD_IMG_SRC;
var outDesc = ""; let outDesc = "";
if (curSrc.indexOf("*") > -1) { if (curSrc.indexOf("*") > -1) {
outIcon = MOD_IMG_SRC; outIcon = MOD_IMG_SRC;
@ -142,8 +145,8 @@ exports.items = [
item: "converter", item: "converter",
from: "securityCSPInfo", from: "securityCSPInfo",
to: "view", to: "view",
exec: function(cspInfo, context) { exec: function (cspInfo, context) {
var url = context.environment.target.url; const url = context.environment.target.url;
if (cspInfo.length == 0) { if (cspInfo.length == 0) {
return context.createView({ return context.createView({
@ -156,6 +159,7 @@ exports.items = [
"</table>"}); "</table>"});
} }
/* eslint-disable max-len */
return context.createView({ return context.createView({
html: html:
"<table class='gcli-csp-detail' cellspacing='10' valign='top'>" + "<table class='gcli-csp-detail' cellspacing='10' valign='top'>" +
@ -181,10 +185,11 @@ exports.items = [
" </td>" + " </td>" +
" </tr>" + " </tr>" +
"</table>", "</table>",
data: { data: {
cspinfo: cspInfo, cspinfo: cspInfo,
} }
}); });
/* eslint-enable max-len */
} }
}, },
{ {
@ -195,17 +200,17 @@ exports.items = [
description: l10n.lookup("securityReferrerPolicyDesc"), description: l10n.lookup("securityReferrerPolicyDesc"),
manual: l10n.lookup("securityReferrerPolicyManual"), manual: l10n.lookup("securityReferrerPolicyManual"),
returnType: "securityReferrerPolicyInfo", returnType: "securityReferrerPolicyInfo",
exec: function(args, context) { exec: function (args, context) {
var doc = context.environment.document; let doc = context.environment.document;
var referrerPolicy = doc.referrerPolicy; let { referrerPolicy } = doc;
var pageURI = doc.documentURIObject; let pageURI = doc.documentURIObject;
var sameDomainReferrer = ""; let sameDomainReferrer = "";
var otherDomainReferrer = ""; let otherDomainReferrer = "";
var downgradeReferrer = ""; let downgradeReferrer = "";
var otherDowngradeReferrer = ""; let otherDowngradeReferrer = "";
var origin = pageURI.prePath; let origin = pageURI.prePath;
switch (referrerPolicy) { switch (referrerPolicy) {
case Ci.nsIHttpChannel.REFERRER_POLICY_NO_REFERRER: case Ci.nsIHttpChannel.REFERRER_POLICY_NO_REFERRER:
@ -255,28 +260,28 @@ exports.items = [
break; break;
} }
var sameDomainUri = origin + "/*"; let sameDomainUri = origin + "/*";
var referrerUrls = [ let referrerUrls = [
// add the referrer uri 'referrer' we would send when visiting 'uri' // add the referrer uri 'referrer' we would send when visiting 'uri'
{ {
uri: pageURI.scheme+'://example.com/', uri: pageURI.scheme + "://example.com/",
referrer: otherDomainReferrer, referrer: otherDomainReferrer,
description: l10n.lookup('securityReferrerPolicyOtherDomain')}, description: l10n.lookup("securityReferrerPolicyOtherDomain")},
{ {
uri: sameDomainUri, uri: sameDomainUri,
referrer: sameDomainReferrer, referrer: sameDomainReferrer,
description: l10n.lookup('securityReferrerPolicySameDomain')} description: l10n.lookup("securityReferrerPolicySameDomain")}
]; ];
if (pageURI.schemeIs('https')) { if (pageURI.schemeIs("https")) {
// add the referrer we would send on downgrading http->https // add the referrer we would send on downgrading http->https
if (sameDomainReferrer != downgradeReferrer) { if (sameDomainReferrer != downgradeReferrer) {
referrerUrls.push({ referrerUrls.push({
uri: "http://"+pageURI.hostPort+"/*", uri: "http://" + pageURI.hostPort + "/*",
referrer: downgradeReferrer, referrer: downgradeReferrer,
description: description:
l10n.lookup('securityReferrerPolicySameDomainDowngrade') l10n.lookup("securityReferrerPolicySameDomainDowngrade")
}); });
} }
if (otherDomainReferrer != otherDowngradeReferrer) { if (otherDomainReferrer != otherDowngradeReferrer) {
@ -284,7 +289,7 @@ exports.items = [
uri: "http://example.com/", uri: "http://example.com/",
referrer: otherDowngradeReferrer, referrer: otherDowngradeReferrer,
description: description:
l10n.lookup('securityReferrerPolicyOtherDomainDowngrade') l10n.lookup("securityReferrerPolicyOtherDomainDowngrade")
}); });
} }
} }
@ -294,16 +299,16 @@ exports.items = [
[pageURI.spec]), [pageURI.spec]),
policyName: REFERRER_POLICY_NAMES[referrerPolicy], policyName: REFERRER_POLICY_NAMES[referrerPolicy],
urls: referrerUrls urls: referrerUrls
} };
} }
}, },
{ {
item: "converter", item: "converter",
from: "securityReferrerPolicyInfo", from: "securityReferrerPolicyInfo",
to: "view", to: "view",
exec: function(referrerPolicyInfo, context) { exec: function (referrerPolicyInfo, context) {
return context.createView({ return context.createView({
html: html:
"<div class='gcli-referrer-policy'>" + "<div class='gcli-referrer-policy'>" +
" <strong> ${rpi.header} </strong> <br />" + " <strong> ${rpi.header} </strong> <br />" +
" ${rpi.policyName} <br />" + " ${rpi.policyName} <br />" +
@ -319,10 +324,10 @@ exports.items = [
" </tr>" + " </tr>" +
" </table>" + " </table>" +
"</div>", "</div>",
data: { data: {
rpi: referrerPolicyInfo, rpi: referrerPolicyInfo,
} }
}); });
} }
} }
]; ];

View file

@ -24,12 +24,11 @@
* Called to clean up at the end of use * Called to clean up at the end of use
*/ */
const { Cc, Ci, Cu } = require("chrome"); const { Cc, Ci } = require("chrome");
const DevToolsUtils = require("devtools/shared/DevToolsUtils"); const DevToolsUtils = require("devtools/shared/DevToolsUtils");
const { dumpn, dumpv } = DevToolsUtils; const { dumpn, dumpv } = DevToolsUtils;
const flags = require("devtools/shared/flags"); const flags = require("devtools/shared/flags");
const StreamUtils = require("devtools/shared/transport/stream-utils"); const StreamUtils = require("devtools/shared/transport/stream-utils");
const promise = require("promise");
const defer = require("devtools/shared/defer"); const defer = require("devtools/shared/defer");
DevToolsUtils.defineLazyGetter(this, "unicodeConverter", () => { DevToolsUtils.defineLazyGetter(this, "unicodeConverter", () => {
@ -136,7 +135,9 @@ Object.defineProperty(JSONPacket.prototype, "object", {
/** /**
* Gets the object (not the serialized string) being read or written. * Gets the object (not the serialized string) being read or written.
*/ */
get: function () { return this._object; }, get: function () {
return this._object;
},
/** /**
* Sets the object to be sent when write() is called. * Sets the object to be sent when write() is called.
@ -200,7 +201,9 @@ JSONPacket.prototype.write = function (stream) {
}; };
Object.defineProperty(JSONPacket.prototype, "done", { Object.defineProperty(JSONPacket.prototype, "done", {
get: function () { return this._done; } get: function () {
return this._done;
}
}); });
JSONPacket.prototype.toString = function () { JSONPacket.prototype.toString = function () {
@ -369,10 +372,11 @@ Object.defineProperty(BulkPacket.prototype, "header", {
}); });
Object.defineProperty(BulkPacket.prototype, "done", { Object.defineProperty(BulkPacket.prototype, "done", {
get: function () { return this._done; }, get: function () {
return this._done;
},
}); });
BulkPacket.prototype.toString = function () { BulkPacket.prototype.toString = function () {
return "Bulk: " + JSON.stringify(this.header, null, 2); return "Bulk: " + JSON.stringify(this.header, null, 2);
}; };
@ -408,7 +412,9 @@ RawPacket.prototype.write = function (stream) {
}; };
Object.defineProperty(RawPacket.prototype, "done", { Object.defineProperty(RawPacket.prototype, "done", {
get: function () { return this._done; } get: function () {
return this._done;
}
}); });
exports.RawPacket = RawPacket; exports.RawPacket = RawPacket;

View file

@ -4,12 +4,11 @@
"use strict"; "use strict";
const { Ci, Cc, Cu, Cr, CC } = require("chrome"); const { Ci, Cc, Cr, CC } = require("chrome");
const Services = require("Services"); const Services = require("Services");
const DevToolsUtils = require("devtools/shared/DevToolsUtils"); const DevToolsUtils = require("devtools/shared/DevToolsUtils");
const { dumpv } = DevToolsUtils; const { dumpv } = DevToolsUtils;
const EventEmitter = require("devtools/shared/event-emitter"); const EventEmitter = require("devtools/shared/event-emitter");
const promise = require("promise");
const defer = require("devtools/shared/defer"); const defer = require("devtools/shared/defer");
DevToolsUtils.defineLazyGetter(this, "IOUtil", () => { DevToolsUtils.defineLazyGetter(this, "IOUtil", () => {
@ -70,8 +69,8 @@ function StreamCopier(input, output, length) {
if (IOUtil.outputStreamIsBuffered(output)) { if (IOUtil.outputStreamIsBuffered(output)) {
this.output = output; this.output = output;
} else { } else {
this.output = Cc["@mozilla.org/network/buffered-output-stream;1"]. this.output = Cc["@mozilla.org/network/buffered-output-stream;1"]
createInstance(Ci.nsIBufferedOutputStream); .createInstance(Ci.nsIBufferedOutputStream);
this.output.init(output, BUFFER_SIZE); this.output.init(output, BUFFER_SIZE);
} }
this._length = length; this._length = length;
@ -124,9 +123,8 @@ StreamCopier.prototype = {
this._debug("Waiting for output stream"); this._debug("Waiting for output stream");
this.baseAsyncOutput.asyncWait(this, 0, 0, Services.tm.currentThread); this.baseAsyncOutput.asyncWait(this, 0, 0, Services.tm.currentThread);
return; return;
} else {
throw e;
} }
throw e;
} }
this._amountLeft -= bytesCopied; this._amountLeft -= bytesCopied;
@ -162,9 +160,8 @@ StreamCopier.prototype = {
this._debug("Waiting for output stream"); this._debug("Waiting for output stream");
this.baseAsyncOutput.asyncWait(this, 0, 0, Services.tm.currentThread); this.baseAsyncOutput.asyncWait(this, 0, 0, Services.tm.currentThread);
return; return;
} else {
throw e;
} }
throw e;
} }
this._deferred.resolve(); this._deferred.resolve();
}, },

View file

@ -1,9 +1,12 @@
/* This Source Code Form is subject to the terms of the Mozilla Public /* 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 * 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/. */ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
(function (root, factory) {
"use strict";
/* eslint-env amd */
"use strict";
(function (root, factory) {
if (typeof define === "function" && define.amd) { if (typeof define === "function" && define.amd) {
define(factory); define(factory);
} else if (typeof exports === "object") { } else if (typeof exports === "object") {
@ -12,8 +15,6 @@
root.workerHelper = factory(); root.workerHelper = factory();
} }
}(this, function () { }(this, function () {
"use strict";
/** /**
* This file is to only be included by ChromeWorkers. This exposes * This file is to only be included by ChromeWorkers. This exposes
* a `createTask` function to workers to register tasks for communication * a `createTask` function to workers to register tasks for communication
@ -81,23 +82,20 @@
} }
try { try {
let results;
handleResponse(taskFn(data)); handleResponse(taskFn(data));
} catch (e) { } catch (ex) {
handleError(e); handleError(ex);
} }
function handleResponse(response) { function handleResponse(response) {
// If a promise // If a promise
if (response && typeof response.then === "function") { if (response && typeof response.then === "function") {
response.then(val => self.postMessage({ id, response: val }), handleError); response.then(val => self.postMessage({ id, response: val }), handleError);
} } else if (response instanceof Error) {
// If an error object // If an error object
else if (response instanceof Error) {
handleError(response); handleError(response);
} } else {
// If anything else // If anything else
else {
self.postMessage({ id, response }); self.postMessage({ id, response });
} }
} }
@ -106,21 +104,23 @@
try { try {
// First, try and structured clone the error across directly. // First, try and structured clone the error across directly.
self.postMessage({ id, error }); self.postMessage({ id, error });
} catch (_) { } catch (x) {
// We could not clone whatever error value was given. Do our best to // We could not clone whatever error value was given. Do our best to
// stringify it. // stringify it.
let errorString = `Error while performing task "${task}": `; let errorString = `Error while performing task "${task}": `;
try { try {
errorString += error.toString(); errorString += error.toString();
} catch (_) { } catch (ex) {
errorString += "<could not stringify error>"; errorString += "<could not stringify error>";
} }
if ("stack" in error) { if ("stack" in error) {
try { try {
errorString += "\n" + error.stack; errorString += "\n" + error.stack;
} catch (_) { } } catch (err) {
// Do nothing
}
} }
self.postMessage({ id, error: errorString }); self.postMessage({ id, error: errorString });
@ -130,4 +130,4 @@
} }
return { createTask: createTask }; return { createTask: createTask };
}.bind(this))); }));

View file

@ -4,6 +4,8 @@
"use strict"; "use strict";
/* global worker */
// A CommonJS module loader that is designed to run inside a worker debugger. // A CommonJS module loader that is designed to run inside a worker debugger.
// We can't simply use the SDK module loader, because it relies heavily on // We can't simply use the SDK module loader, because it relies heavily on
// Components, which isn't available in workers. // Components, which isn't available in workers.
@ -60,7 +62,7 @@ function normalizeId(id) {
// An id consists of an optional root and a path. A root consists of either // An id consists of an optional root and a path. A root consists of either
// a scheme name followed by 2 or 3 slashes, or a single slash. Slashes in the // a scheme name followed by 2 or 3 slashes, or a single slash. Slashes in the
// root are not used as separators, so only normalize the path. // root are not used as separators, so only normalize the path.
let [_, root, path] = id.match(/^(\w+:\/\/\/?|\/)?(.*)/); let [, root, path] = id.match(/^(\w+:\/\/\/?|\/)?(.*)/);
let stack = []; let stack = [];
path.split("/").forEach(function (component) { path.split("/").forEach(function (component) {
@ -75,12 +77,10 @@ function normalizeId(id) {
} else { } else {
stack.push(".."); stack.push("..");
} }
} else if (stack[stack.length - 1] == "..") {
stack.push("..");
} else { } else {
if (stack[stack.length - 1] == "..") { stack.pop();
stack.push("..");
} else {
stack.pop();
}
} }
break; break;
default: default:
@ -336,7 +336,8 @@ var loader = {
Object.defineProperty(object, name, { Object.defineProperty(object, name, {
get: function () { get: function () {
delete object[name]; delete object[name];
return object[name] = lambda.apply(object); object[name] = lambda.apply(object);
return object[name];
}, },
configurable: true, configurable: true,
enumerable: true enumerable: true
@ -361,6 +362,7 @@ var loader = {
// object to implement them. On worker threads, we use the APIs provided by // object to implement them. On worker threads, we use the APIs provided by
// the worker debugger. // the worker debugger.
/* eslint-disable no-shadow */
var { var {
Debugger, Debugger,
URL, URL,
@ -372,13 +374,12 @@ var {
setImmediate, setImmediate,
xpcInspector, xpcInspector,
} = (function () { } = (function () {
if (typeof Components === "object") { // Main thread // Main thread
if (typeof Components === "object") {
let { let {
Constructor: CC, Constructor: CC,
classes: Cc, classes: Cc,
manager: Cm,
interfaces: Ci, interfaces: Ci,
results: Cr,
utils: Cu utils: Cu
} = Components; } = Components;
@ -406,8 +407,8 @@ var {
let rpc = undefined; let rpc = undefined;
let subScriptLoader = Cc["@mozilla.org/moz/jssubscript-loader;1"]. let subScriptLoader = Cc["@mozilla.org/moz/jssubscript-loader;1"]
getService(Ci.mozIJSSubScriptLoader); .getService(Ci.mozIJSSubScriptLoader);
let loadSubScript = function (url, sandbox) { let loadSubScript = function (url, sandbox) {
subScriptLoader.loadSubScript(url, sandbox, "UTF-8"); subScriptLoader.loadSubScript(url, sandbox, "UTF-8");
@ -421,8 +422,8 @@ var {
Timer.setTimeout(callback, 0); Timer.setTimeout(callback, 0);
}; };
let xpcInspector = Cc["@mozilla.org/jsinspector;1"]. let xpcInspector = Cc["@mozilla.org/jsinspector;1"]
getService(Ci.nsIJSInspector); .getService(Ci.nsIJSInspector);
return { return {
Debugger, Debugger,
@ -435,46 +436,47 @@ var {
setImmediate, setImmediate,
xpcInspector xpcInspector
}; };
} else { // Worker thread
let requestors = [];
let scope = this;
let xpcInspector = {
get eventLoopNestLevel() {
return requestors.length;
},
get lastNestRequestor() {
return requestors.length === 0 ? null : requestors[requestors.length - 1];
},
enterNestedEventLoop: function (requestor) {
requestors.push(requestor);
scope.enterEventLoop();
return requestors.length;
},
exitNestedEventLoop: function () {
requestors.pop();
scope.leaveEventLoop();
return requestors.length;
}
};
return {
Debugger: this.Debugger,
URL: this.URL,
createSandbox: this.createSandbox,
dump: this.dump,
rpc: this.rpc,
loadSubScript: this.loadSubScript,
reportError: this.reportError,
setImmediate: this.setImmediate,
xpcInspector: xpcInspector
};
} }
// Worker thread
let requestors = [];
let scope = this;
let xpcInspector = {
get eventLoopNestLevel() {
return requestors.length;
},
get lastNestRequestor() {
return requestors.length === 0 ? null : requestors[requestors.length - 1];
},
enterNestedEventLoop: function (requestor) {
requestors.push(requestor);
scope.enterEventLoop();
return requestors.length;
},
exitNestedEventLoop: function () {
requestors.pop();
scope.leaveEventLoop();
return requestors.length;
}
};
return {
Debugger: this.Debugger,
URL: this.URL,
createSandbox: this.createSandbox,
dump: this.dump,
rpc: this.rpc,
loadSubScript: this.loadSubScript,
reportError: this.reportError,
setImmediate: this.setImmediate,
xpcInspector: xpcInspector
};
}).call(this); }).call(this);
/* eslint-enable no-shadow */
// Create the default instance of the worker loader, using the APIs we defined // Create the default instance of the worker loader, using the APIs we defined
// above. // above.

View file

@ -1,6 +1,8 @@
/* Any copyright is dedicated to the Public Domain. /* Any copyright is dedicated to the Public Domain.
http://creativecommons.org/publicdomain/zero/1.0/ */ http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
// Tests that the devtools/shared/worker communicates properly // Tests that the devtools/shared/worker communicates properly
// as both CommonJS module and as a JSM. // as both CommonJS module and as a JSM.
@ -37,7 +39,7 @@ function* testWorker(context, workerFactory) {
ok(results.plottedData.length, ok(results.plottedData.length,
`worker should have returned an object with array properties in ${context}`); `worker should have returned an object with array properties in ${context}`);
let fn = workerify(function (x) { return x * x; }); let fn = workerify(x => x * x);
is((yield fn(5)), 25, `workerify works in ${context}`); is((yield fn(5)), 25, `workerify works in ${context}`);
fn.destroy(); fn.destroy();

View file

@ -1,6 +1,8 @@
/* Any copyright is dedicated to the Public Domain. /* Any copyright is dedicated to the Public Domain.
http://creativecommons.org/publicdomain/zero/1.0/ */ http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
// Tests errors are handled properly by the DevToolsWorker. // Tests errors are handled properly by the DevToolsWorker.
const { DevToolsWorker } = require("devtools/shared/worker/worker"); const { DevToolsWorker } = require("devtools/shared/worker/worker");
@ -9,7 +11,7 @@ const WORKER_URL =
add_task(function* () { add_task(function* () {
try { try {
let workerNotFound = new DevToolsWorker("resource://i/dont/exist.js"); new DevToolsWorker("resource://i/dont/exist.js");
ok(false, "Creating a DevToolsWorker with an invalid URL throws"); ok(false, "Creating a DevToolsWorker with an invalid URL throws");
} catch (e) { } catch (e) {
ok(true, "Creating a DevToolsWorker with an invalid URL throws"); ok(true, "Creating a DevToolsWorker with an invalid URL throws");
@ -19,14 +21,16 @@ add_task(function* () {
try { try {
// plotTimestampsGraph requires timestamp, interval an duration props on the object // plotTimestampsGraph requires timestamp, interval an duration props on the object
// passed in so there should be an error thrown in the worker // passed in so there should be an error thrown in the worker
let results = yield worker.performTask("plotTimestampsGraph", {}); yield worker.performTask("plotTimestampsGraph", {});
ok(false, "DevToolsWorker returns a rejected promise when an error occurs in the worker"); ok(false,
"DevToolsWorker returns a rejected promise when an error occurs in the worker");
} catch (e) { } catch (e) {
ok(true, "DevToolsWorker returns a rejected promise when an error occurs in the worker"); ok(true,
"DevToolsWorker returns a rejected promise when an error occurs in the worker");
} }
try { try {
let results = yield worker.performTask("not a real task"); yield worker.performTask("not a real task");
ok(false, "DevToolsWorker returns a rejected promise when task does not exist"); ok(false, "DevToolsWorker returns a rejected promise when task does not exist");
} catch (e) { } catch (e) {
ok(true, "DevToolsWorker returns a rejected promise when task does not exist"); ok(true, "DevToolsWorker returns a rejected promise when task does not exist");
@ -34,7 +38,7 @@ add_task(function* () {
worker.destroy(); worker.destroy();
try { try {
let results = yield worker.performTask("plotTimestampsGraph", { yield worker.performTask("plotTimestampsGraph", {
timestamps: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9], timestamps: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9],
interval: 1, interval: 1,
duration: 1 duration: 1

View file

@ -1,12 +1,14 @@
/* Any copyright is dedicated to the Public Domain. /* Any copyright is dedicated to the Public Domain.
http://creativecommons.org/publicdomain/zero/1.0/ */ http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
// Tests that the devtools/shared/worker can handle: // Tests that the devtools/shared/worker can handle:
// returned primitives (or promise or Error) // returned primitives (or promise or Error)
// //
// And tests `workerify` by doing so. // And tests `workerify` by doing so.
const { DevToolsWorker, workerify } = require("devtools/shared/worker/worker"); const { workerify } = require("devtools/shared/worker/worker");
function square(x) { function square(x) {
return x * x; return x * x;
} }