Bug 1498410 - Part 4 - Export comma-dangle refactoring as a separate commit to ease reviews; r=ianbicking
☠☠ backed out by b2cd2ffe4ec8 ☠ ☠
authorJared Hirsch <ohai@6a68.net>
Mon, 15 Oct 2018 20:10:29 +0000
changeset 499775 01fa6937f05fc51562205eac8e895c62324452f8
parent 499774 426257ad4b83e3cffc628f76ae8bd55c2fa4fbaf
child 499776 0bf7bb3f9e581ee5da934136e404d794a130fddc
push id1864
push userffxbld-merge
push dateMon, 03 Dec 2018 15:51:40 +0000
treeherdermozilla-release@f040763d99ad [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersianbicking
bugs1498410
milestone64.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 1498410 - Part 4 - Export comma-dangle refactoring as a separate commit to ease reviews; r=ianbicking MozReview-Commit-ID: 455LZbfCGfy Differential Revision: https://phabricator.services.mozilla.com/D8506
browser/extensions/screenshots/background/analytics.js
browser/extensions/screenshots/background/auth.js
browser/extensions/screenshots/background/deviceInfo.js
browser/extensions/screenshots/background/main.js
browser/extensions/screenshots/background/selectorLoader.js
browser/extensions/screenshots/background/senderror.js
browser/extensions/screenshots/background/startBackground.js
browser/extensions/screenshots/background/takeshot.js
browser/extensions/screenshots/build/selection.js
browser/extensions/screenshots/build/thumbnailGenerator.js
browser/extensions/screenshots/catcher.js
browser/extensions/screenshots/onboarding/slides.js
browser/extensions/screenshots/selector/shooter.js
browser/extensions/screenshots/selector/ui.js
browser/extensions/screenshots/selector/uicontrol.js
browser/extensions/screenshots/selector/util.js
--- a/browser/extensions/screenshots/background/analytics.js
+++ b/browser/extensions/screenshots/background/analytics.js
@@ -11,17 +11,17 @@ this.analytics = (function() {
   const EVENT_BATCH_DURATION = 1000; // ms for setTimeout
   let pendingEvents = [];
   let pendingTimings = [];
   let eventsTimeoutHandle, timingsTimeoutHandle;
   const fetchOptions = {
     method: "POST",
     mode: "cors",
     headers: { "content-type": "application/json" },
-    credentials: "include"
+    credentials: "include",
   };
 
   function flushEvents() {
     if (pendingEvents.length === 0) {
       return;
     }
 
     const eventsUrl = `${main.getBackend()}/event`;
@@ -58,17 +58,17 @@ this.analytics = (function() {
   function sendTiming(timingLabel, timingVar, timingValue) {
     // sendTiming is only called in response to sendEvent, so no need to check
     // the telemetry pref again here.
     const timingCategory = "addon";
     pendingTimings.push({
       timingCategory,
       timingLabel,
       timingVar,
-      timingValue
+      timingValue,
     });
     if (!timingsTimeoutHandle) {
       timingsTimeoutHandle = setTimeout(() => {
         timingsTimeoutHandle = null;
         flushTimings();
       }, EVENT_BATCH_DURATION);
     }
   }
@@ -110,17 +110,17 @@ this.analytics = (function() {
     for (const [gaField, value] of Object.entries(abTests)) {
       options[gaField] = value;
     }
     pendingEvents.push({
       eventTime: Date.now(),
       event: eventCategory,
       action,
       label,
-      options
+      options,
     });
     if (!eventsTimeoutHandle) {
       eventsTimeoutHandle = setTimeout(() => {
         eventsTimeoutHandle = null;
         flushEvents();
       }, EVENT_BATCH_DURATION);
     }
     // This function used to return a Promise that was not used at any of the
@@ -168,121 +168,121 @@ this.analytics = (function() {
   // is deleted.
   const rules = [{
     name: "page-action",
     start: { action: "start-shot", label: "toolbar-button" },
     end: { action: "internal", label: "unhide-preselection-frame" },
     cancel: [
       { action: "cancel-shot" },
       { action: "internal", label: "document-hidden" },
-      { action: "internal", label: "unhide-onboarding-frame" }
-    ]
+      { action: "internal", label: "unhide-onboarding-frame" },
+    ],
   }, {
     name: "context-menu",
     start: { action: "start-shot", label: "context-menu" },
     end: { action: "internal", label: "unhide-preselection-frame" },
     cancel: [
       { action: "cancel-shot" },
       { action: "internal", label: "document-hidden" },
-      { action: "internal", label: "unhide-onboarding-frame" }
-    ]
+      { action: "internal", label: "unhide-onboarding-frame" },
+    ],
   }, {
     name: "page-action-onboarding",
     start: { action: "start-shot", label: "toolbar-button" },
     end: { action: "internal", label: "unhide-onboarding-frame" },
     cancel: [
       { action: "cancel-shot" },
       { action: "internal", label: "document-hidden" },
-      { action: "internal", label: "unhide-preselection-frame" }
-    ]
+      { action: "internal", label: "unhide-preselection-frame" },
+    ],
   }, {
     name: "context-menu-onboarding",
     start: { action: "start-shot", label: "context-menu" },
     end: { action: "internal", label: "unhide-onboarding-frame" },
     cancel: [
       { action: "cancel-shot" },
       { action: "internal", label: "document-hidden" },
-      { action: "internal", label: "unhide-preselection-frame" }
-    ]
+      { action: "internal", label: "unhide-preselection-frame" },
+    ],
   }, {
     name: "capture-full-page",
     start: { action: "capture-full-page" },
     end: { action: "internal", label: "unhide-preview-frame" },
     cancel: [
       { action: "cancel-shot" },
-      { action: "internal", label: "document-hidden" }
-    ]
+      { action: "internal", label: "document-hidden" },
+    ],
   }, {
     name: "capture-visible",
     start: { action: "capture-visible" },
     end: { action: "internal", label: "unhide-preview-frame" },
     cancel: [
       { action: "cancel-shot" },
-      { action: "internal", label: "document-hidden" }
-    ]
+      { action: "internal", label: "document-hidden" },
+    ],
   }, {
     name: "make-selection",
     start: { action: "make-selection" },
     end: { action: "internal", label: "unhide-selection-frame" },
     cancel: [
       { action: "cancel-shot" },
-      { action: "internal", label: "document-hidden" }
-    ]
+      { action: "internal", label: "document-hidden" },
+    ],
   }, {
     name: "save-shot",
     start: { action: "save-shot" },
     end: { action: "internal", label: "open-shot-tab" },
-    cancel: [{ action: "cancel-shot" }, { action: "upload-failed" }]
+    cancel: [{ action: "cancel-shot" }, { action: "upload-failed" }],
   }, {
     name: "save-visible",
     start: { action: "save-visible" },
     end: { action: "internal", label: "open-shot-tab" },
-    cancel: [{ action: "cancel-shot" }, { action: "upload-failed" }]
+    cancel: [{ action: "cancel-shot" }, { action: "upload-failed" }],
   }, {
     name: "save-full-page",
     start: { action: "save-full-page" },
     end: { action: "internal", label: "open-shot-tab" },
-    cancel: [{ action: "cancel-shot" }, { action: "upload-failed" }]
+    cancel: [{ action: "cancel-shot" }, { action: "upload-failed" }],
   }, {
     name: "save-full-page-truncated",
     start: { action: "save-full-page-truncated" },
     end: { action: "internal", label: "open-shot-tab" },
-    cancel: [{ action: "cancel-shot" }, { action: "upload-failed" }]
+    cancel: [{ action: "cancel-shot" }, { action: "upload-failed" }],
   }, {
     name: "download-shot",
     start: { action: "download-shot" },
     end: { action: "internal", label: "deactivate" },
     cancel: [
       { action: "cancel-shot" },
-      { action: "internal", label: "document-hidden" }
-    ]
+      { action: "internal", label: "document-hidden" },
+    ],
   }, {
     name: "download-full-page",
     start: { action: "download-full-page" },
     end: { action: "internal", label: "deactivate" },
     cancel: [
       { action: "cancel-shot" },
-      { action: "internal", label: "document-hidden" }
-    ]
+      { action: "internal", label: "document-hidden" },
+    ],
   }, {
     name: "download-full-page-truncated",
     start: { action: "download-full-page-truncated" },
     end: { action: "internal", label: "deactivate" },
     cancel: [
       { action: "cancel-shot" },
-      { action: "internal", label: "document-hidden" }
-    ]
+      { action: "internal", label: "document-hidden" },
+    ],
   }, {
     name: "download-visible",
     start: { action: "download-visible" },
     end: { action: "internal", label: "deactivate" },
     cancel: [
       { action: "cancel-shot" },
-      { action: "internal", label: "document-hidden" }
-    ]
+      { action: "internal", label: "document-hidden" },
+    ],
   }];
 
   // Match a filter (action and optional label) against an action and label.
   function match(filter, action, label) {
     return filter.label ?
       filter.action === action && filter.label === label :
       filter.action === action;
   }
--- a/browser/extensions/screenshots/background/auth.js
+++ b/browser/extensions/screenshots/background/auth.js
@@ -35,17 +35,17 @@ this.auth = (function() {
   exports.getDeviceId = function() {
     return registrationInfo && registrationInfo.deviceId;
   };
 
   function generateRegistrationInfo() {
     const info = {
       deviceId: `anon${makeUuid()}`,
       secret: makeUuid(),
-      registered: false
+      registered: false,
     };
     return info;
   }
 
   function register() {
     return new Promise((resolve, reject) => {
       const registerUrl = main.getBackend() + "/api/register";
       // TODO: replace xhr with Fetch #2261
@@ -71,17 +71,17 @@ this.auth = (function() {
         analytics.sendEvent("register-failed", "connection-error");
         const exc = new Error("Error contacting server");
         exc.popupMessage = "LOGIN_CONNECTION_ERROR";
         reject(exc);
       });
       req.send(JSON.stringify({
         deviceId: registrationInfo.deviceId,
         secret: registrationInfo.secret,
-        deviceInfo: JSON.stringify(deviceInfo())
+        deviceInfo: JSON.stringify(deviceInfo()),
       }));
     });
   }
 
   function login(options) {
     const { ownershipCheck, noRegister } = options || {};
     return new Promise((resolve, reject) => {
       return fetchStoredInfo.then(() => {
--- a/browser/extensions/screenshots/background/deviceInfo.js
+++ b/browser/extensions/screenshots/background/deviceInfo.js
@@ -22,13 +22,13 @@ this.deviceInfo = (function() {
       platform: platformInfo.os,
       architecture: platformInfo.arch,
       version: firefoxVersion || chromeVersion,
       // These don't seem to apply to Chrome:
       // build: system.build,
       // platformVersion: system.platformVersion,
       userAgent: navigator.userAgent,
       appVendor: appName,
-      appName
+      appName,
     };
   };
 
 })();
--- a/browser/extensions/screenshots/background/main.js
+++ b/browser/extensions/screenshots/background/main.js
@@ -127,17 +127,17 @@ this.main = (function() {
       }
       if (!urlEnabled(tab.url)) {
         if (!onboarded) {
           sendEvent("goto-onboarding", "selection-button", {incognito: tab.incognito});
           forceOnboarding();
           return;
         }
         senderror.showError({
-          popupMessage: "UNSHOOTABLE_PAGE"
+          popupMessage: "UNSHOOTABLE_PAGE",
         });
         return;
       }
       // No need to catch() here because of watchPromise().
       // eslint-disable-next-line promise/catch-or-return
       toggleSelector(tab)
         .then(() => sendEvent("start-shot", "context-menu", {incognito: tab.incognito}));
     }));
@@ -195,17 +195,17 @@ this.main = (function() {
 
   communication.register("openShot", (sender, {url, copied}) => {
     if (copied) {
       const id = makeUuid();
       return browser.notifications.create(id, {
         type: "basic",
         iconUrl: "../icons/copied-notification.svg",
         title: browser.i18n.getMessage("notificationLinkCopiedTitle"),
-        message: browser.i18n.getMessage("notificationLinkCopiedDetails", pasteSymbol)
+        message: browser.i18n.getMessage("notificationLinkCopiedDetails", pasteSymbol),
       });
     }
     return null;
   });
 
   // This is used for truncated full page downloads and copy to clipboards.
   // Those longer operations need to display an animated spinner/loader, so
   // it's preferable to perform toDataURL() in the background.
@@ -229,17 +229,17 @@ this.main = (function() {
     return blobConverters.blobToArray(blob).then(buffer => {
       return browser.clipboard.setImageData(
         buffer, blob.type.split("/", 2)[1]).then(() => {
           catcher.watchPromise(incrementCount("copy"));
           return browser.notifications.create({
             type: "basic",
             iconUrl: "../icons/copied-notification.svg",
             title: browser.i18n.getMessage("notificationImageCopiedTitle"),
-            message: browser.i18n.getMessage("notificationImageCopiedDetails", pasteSymbol)
+            message: browser.i18n.getMessage("notificationImageCopiedDetails", pasteSymbol),
           });
         });
     });
   });
 
   communication.register("downloadShot", (sender, info) => {
     // 'data:' urls don't work directly, let's use a Blob
     // see http://stackoverflow.com/questions/40269862/save-data-uri-as-file-using-downloads-download-api
@@ -256,17 +256,17 @@ this.main = (function() {
       }
     });
     browser.downloads.onChanged.addListener(onChangedCallback);
     catcher.watchPromise(incrementCount("download"));
     return browser.windows.getLastFocused().then(windowInfo => {
       return browser.downloads.download({
         url,
         incognito: windowInfo.incognito,
-        filename: info.filename
+        filename: info.filename,
       }).catch((error) => {
         // We are not logging error message when user cancels download
         if (error && error.message && !error.message.includes("canceled")) {
           log.error(error.message);
         }
       }).then((id) => {
         downloadId = id;
       });
@@ -281,17 +281,17 @@ this.main = (function() {
     hasSeenOnboarding = Promise.resolve(true);
     catcher.watchPromise(browser.storage.local.set({hasSeenOnboarding: true}));
   });
 
   communication.register("abortStartShot", () => {
     // Note, we only show the error but don't report it, as we know that we can't
     // take shots of these pages:
     senderror.showError({
-      popupMessage: "UNSHOOTABLE_PAGE"
+      popupMessage: "UNSHOOTABLE_PAGE",
     });
   });
 
   // A Screenshots page wants us to start/force onboarding
   communication.register("requestOnboarding", (sender) => {
     return startSelectionWithOnboarding(sender.tab);
   });
 
--- a/browser/extensions/screenshots/background/selectorLoader.js
+++ b/browser/extensions/screenshots/background/selectorLoader.js
@@ -14,56 +14,56 @@ this.selectorLoader = (function() {
     "build/buildSettings.js",
     "log.js",
     "catcher.js",
     "assertIsTrusted.js",
     "assertIsBlankDocument.js",
     "blobConverters.js",
     "background/selectorLoader.js",
     "selector/callBackground.js",
-    "selector/util.js"
+    "selector/util.js",
   ];
 
   const selectorScripts = [
     "clipboard.js",
     "makeUuid.js",
     "build/selection.js",
     "build/shot.js",
     "randomString.js",
     "domainFromUrl.js",
     "build/inlineSelectionCss.js",
     "selector/documentMetadata.js",
     "selector/ui.js",
     "selector/shooter.js",
-    "selector/uicontrol.js"
+    "selector/uicontrol.js",
   ];
 
   // These are loaded on request (by the selector worker) to activate the onboarding:
   const onboardingScripts = [
     "build/onboardingCss.js",
     "build/onboardingHtml.js",
-    "onboarding/slides.js"
+    "onboarding/slides.js",
   ];
 
   exports.unloadIfLoaded = function(tabId) {
     return browser.tabs.executeScript(tabId, {
       code: "this.selectorLoader && this.selectorLoader.unloadModules()",
-      runAt: "document_start"
+      runAt: "document_start",
     }).then(result => {
       return result && result[0];
     });
   };
 
   exports.testIfLoaded = function(tabId) {
     if (loadingTabs.has(tabId)) {
       return true;
     }
     return browser.tabs.executeScript(tabId, {
       code: "!!this.selectorLoader",
-      runAt: "document_start"
+      runAt: "document_start",
     }).then(result => {
       return result && result[0];
     });
   };
 
   const loadingTabs = new Set();
 
   exports.loadModules = function(tabId, hasSeenOnboarding) {
@@ -95,31 +95,31 @@ this.selectorLoader = (function() {
         return browser.experiments.screenshots.getUpdateChannel().then((channel) => {
           return browser.tabs.get(tabId).then(tab => {
             const downloadOnly = !historyEnabled || uploadDisabled || channel === "esr" || tab.incognito;
             return browser.tabs.executeScript(tabId, {
               // Note: `window` here refers to a global accessible to content
               // scripts, but not the scripts in the underlying page. For more
               // details, see https://mdn.io/WebExtensions/Content_scripts#Content_script_environment
               code: `window.downloadOnly = ${downloadOnly}`,
-              runAt: "document_start"
+              runAt: "document_start",
             });
           });
         });
       });
     });
   }
 
   function executeModules(tabId, scripts) {
     let lastPromise = Promise.resolve(null);
     scripts.forEach((file) => {
       lastPromise = lastPromise.then(() => {
         return browser.tabs.executeScript(tabId, {
           file,
-          runAt: "document_start"
+          runAt: "document_start",
         }).catch((error) => {
           log.error("error in script:", file, error);
           error.scriptName = file;
           throw error;
         });
       });
     });
     return lastPromise.then(() => {
--- a/browser/extensions/screenshots/background/senderror.js
+++ b/browser/extensions/screenshots/background/senderror.js
@@ -8,52 +8,52 @@ this.senderror = (function() {
   const manifest = browser.runtime.getManifest();
 
   // Do not show an error more than every ERROR_TIME_LIMIT milliseconds:
   const ERROR_TIME_LIMIT = 3000;
 
   const messages = {
     REQUEST_ERROR: {
       title: browser.i18n.getMessage("requestErrorTitle"),
-      info: browser.i18n.getMessage("requestErrorDetails")
+      info: browser.i18n.getMessage("requestErrorDetails"),
     },
     CONNECTION_ERROR: {
       title: browser.i18n.getMessage("connectionErrorTitle"),
-      info: browser.i18n.getMessage("connectionErrorDetails")
+      info: browser.i18n.getMessage("connectionErrorDetails"),
     },
     LOGIN_ERROR: {
       title: browser.i18n.getMessage("requestErrorTitle"),
-      info: browser.i18n.getMessage("loginErrorDetails")
+      info: browser.i18n.getMessage("loginErrorDetails"),
     },
     LOGIN_CONNECTION_ERROR: {
       title: browser.i18n.getMessage("connectionErrorTitle"),
-      info: browser.i18n.getMessage("connectionErrorDetails")
+      info: browser.i18n.getMessage("connectionErrorDetails"),
     },
     UNSHOOTABLE_PAGE: {
       title: browser.i18n.getMessage("unshootablePageErrorTitle"),
-      info: browser.i18n.getMessage("unshootablePageErrorDetails")
+      info: browser.i18n.getMessage("unshootablePageErrorDetails"),
     },
     SHOT_PAGE: {
-      title: browser.i18n.getMessage("selfScreenshotErrorTitle")
+      title: browser.i18n.getMessage("selfScreenshotErrorTitle"),
     },
     MY_SHOTS: {
-      title: browser.i18n.getMessage("selfScreenshotErrorTitle")
+      title: browser.i18n.getMessage("selfScreenshotErrorTitle"),
     },
     EMPTY_SELECTION: {
-      title: browser.i18n.getMessage("emptySelectionErrorTitle")
+      title: browser.i18n.getMessage("emptySelectionErrorTitle"),
     },
     PRIVATE_WINDOW: {
       title: browser.i18n.getMessage("privateWindowErrorTitle"),
-      info: browser.i18n.getMessage("privateWindowErrorDetails")
+      info: browser.i18n.getMessage("privateWindowErrorDetails"),
     },
     generic: {
       title: browser.i18n.getMessage("genericErrorTitle"),
       info: browser.i18n.getMessage("genericErrorDetails"),
-      showMessage: true
-    }
+      showMessage: true,
+    },
   };
 
   communication.register("reportError", (sender, error) => {
     catcher.unhandled(error);
   });
 
   let lastErrorTime;
 
@@ -77,17 +77,17 @@ this.senderror = (function() {
         message = error.message;
       }
     }
     if (Date.now() - startBackground.startTime > 5 * 1000) {
       browser.notifications.create(id, {
         type: "basic",
         // FIXME: need iconUrl for an image, see #2239
         title,
-        message
+        message,
       });
     }
   };
 
   exports.reportError = function(e) {
     if (!analytics.isTelemetryEnabled()) {
       log.error("Telemetry disabled. Not sending critical error:", e);
       return;
@@ -118,17 +118,17 @@ this.senderror = (function() {
       }
     }
     rest.stack = exception.stack;
     Raven.captureException(exception, {
       logger: "addon",
       tags: {category: e.popupMessage},
       release: manifest.version,
       message: exception.message,
-      extra: rest
+      extra: rest,
     });
   };
 
   catcher.registerHandler((errorObj) => {
     if (!errorObj.noPopup) {
       exports.showError(errorObj);
     }
     if (!errorObj.noReport) {
--- a/browser/extensions/screenshots/background/startBackground.js
+++ b/browser/extensions/screenshots/background/startBackground.js
@@ -21,32 +21,32 @@ this.startBackground = (function() {
     "background/auth.js",
     "background/senderror.js",
     "build/raven.js",
     "build/shot.js",
     "build/thumbnailGenerator.js",
     "background/analytics.js",
     "background/deviceInfo.js",
     "background/takeshot.js",
-    "background/main.js"
+    "background/main.js",
   ];
 
   browser.pageAction.onClicked.addListener(tab => {
     loadIfNecessary().then(() => {
       main.onClicked(tab);
     }).catch(error => {
       console.error("Error loading Screenshots:", error);
     });
   });
 
   browser.contextMenus.create({
     id: "create-screenshot",
     title: browser.i18n.getMessage("contextMenuLabel"),
     contexts: ["page"],
-    documentUrlPatterns: ["<all_urls>"]
+    documentUrlPatterns: ["<all_urls>"],
   });
 
   browser.contextMenus.onClicked.addListener((info, tab) => {
     loadIfNecessary().then(() => {
       main.onClickedContextMenu(info, tab);
     }).catch((error) => {
       console.error("Error loading Screenshots:", error);
     });
--- a/browser/extensions/screenshots/background/takeshot.js
+++ b/browser/extensions/screenshots/background/takeshot.js
@@ -22,19 +22,19 @@ this.takeshot = (function() {
           createdDate: Date.now(),
           image: {
             url: buildSettings.uploadBinary ? "" : dataUrl,
             captureType,
             text: captureText,
             location: selectedPos,
             dimensions: {
               x: selectedPos.right - selectedPos.left,
-              y: selectedPos.bottom - selectedPos.top
-            }
-          }
+              y: selectedPos.bottom - selectedPos.top,
+            },
+          },
         });
       });
     }
     const shotAbTests = {};
     const abTests = auth.getAbTests();
     for (const testName of Object.keys(abTests)) {
       if (abTests[testName].shotField) {
         shotAbTests[testName] = abTests[testName].value;
@@ -89,17 +89,17 @@ this.takeshot = (function() {
     return screenshotPage(selectedPos, scroll);
   });
 
   function screenshotPage(pos, scroll) {
     pos = {
       top: pos.top - scroll.scrollY,
       left: pos.left - scroll.scrollX,
       bottom: pos.bottom - scroll.scrollY,
-      right: pos.right - scroll.scrollX
+      right: pos.right - scroll.scrollX,
     };
     pos.width = pos.right - pos.left;
     pos.height = pos.bottom - pos.top;
     return catcher.watchPromise(browser.tabs.captureVisibleTab(
       null,
       {format: "png"}
     ).then((dataUrl) => {
       const image = new Image();
@@ -172,17 +172,17 @@ this.takeshot = (function() {
         body = concatBuffers(body, enc.encode("\r\n").buffer);
       }
 
       let tail = `\r\n--${boundary}--`;
       tail = enc.encode(tail);
       body = concatBuffers(body, tail.buffer);
       return {
         "content-type": `multipart/form-data; boundary=${boundary}`,
-        body
+        body,
       };
     });
   }
 
   function uploadShot(shot, blob, thumbnail) {
     let headers;
     return auth.authHeaders().then((_headers) => {
       headers = _headers;
@@ -194,27 +194,27 @@ this.takeshot = (function() {
         return createMultipart(
           {shot: JSON.stringify(shot)},
 
           files
         );
       }
       return {
         "content-type": "application/json",
-        body: JSON.stringify(shot)
+        body: JSON.stringify(shot),
       };
 
     }).then((submission) => {
       headers["content-type"] = submission["content-type"];
       sendEvent("upload", "started", {eventValue: Math.floor(submission.body.length / 1000)});
       return fetch(shot.jsonUrl, {
         method: "PUT",
         mode: "cors",
         headers,
-        body: submission.body
+        body: submission.body,
       });
     }).then((resp) => {
       if (!resp.ok) {
         sendEvent("upload-failed", `status-${resp.status}`);
         const exc = new Error(`Response failed with status ${resp.status}`);
         exc.popupMessage = "REQUEST_ERROR";
         throw exc;
       } else {
--- a/browser/extensions/screenshots/build/selection.js
+++ b/browser/extensions/screenshots/build/selection.js
@@ -57,17 +57,17 @@ this.selection = (function () {let expor
     return Math.abs(this.y2 - this.y1);
   }
 
   rect() {
     return {
       top: Math.floor(this.top),
       left: Math.floor(this.left),
       bottom: Math.floor(this.bottom),
-      right: Math.floor(this.right)
+      right: Math.floor(this.right),
     };
   }
 
   union(other) {
     return new Selection(
       Math.min(this.left, other.left),
       Math.min(this.top, other.top),
       Math.max(this.right, other.right),
@@ -89,17 +89,17 @@ this.selection = (function () {let expor
     return new Selection(this.x1, this.y1, this.x2, this.y2);
   }
 
   toJSON() {
     return {
       left: this.left,
       right: this.right,
       top: this.top,
-      bottom: this.bottom
+      bottom: this.bottom,
     };
   }
 
   static getBoundingClientRect(el) {
     if (!el.getBoundingClientRect) {
       // Typically the <html> element or somesuch
       return null;
     }
--- a/browser/extensions/screenshots/build/thumbnailGenerator.js
+++ b/browser/extensions/screenshots/build/thumbnailGenerator.js
@@ -43,17 +43,17 @@ function getThumbnailDimensions(imageWid
     thumbnailImageHeight = Math.min(scaledY, maxThumbnailHeight,
                                     maxThumbnailHeight / (maxThumbnailWidth / imageWidth));
   }
 
   return {
     width: thumbnailImageWidth,
     height: thumbnailImageHeight,
     scaledX,
-    scaledY
+    scaledY,
   };
 }
 
 /**
  * @param {dataUrl} String Data URL of the original image.
  * @param {int} imageHeight Height in pixels of the original image.
  * @param {int} imageWidth Width in pixels of the original image.
  * @param {String} urlOrBlob 'blob' for a blob, otherwise data url.
--- a/browser/extensions/screenshots/catcher.js
+++ b/browser/extensions/screenshots/catcher.js
@@ -29,17 +29,17 @@ this.catcher = (function() {
     let result;
     if (exc.fromMakeError) {
       result = exc;
     } else {
       result = {
         fromMakeError: true,
         name: exc.name || "ERROR",
         message: String(exc),
-        stack: exc.stack
+        stack: exc.stack,
       };
       for (const attr in exc) {
         result[attr] = exc[attr];
       }
     }
     if (info) {
       for (const attr of Object.keys(info)) {
         result[attr] = info[attr];
--- a/browser/extensions/screenshots/onboarding/slides.js
+++ b/browser/extensions/screenshots/onboarding/slides.js
@@ -89,21 +89,21 @@ this.slides = (function() {
     // termsAndPrivacyNoticeCloudServices is a more complicated substitution:
     const termsContainer = doc.querySelector(".onboarding-legal-notice");
     termsContainer.innerHTML = "";
     const termsSentinel = "__TERMS__";
     const privacySentinel = "__PRIVACY__";
     const sentinelSplitter = "!!!";
     const linkTexts = {
       [termsSentinel]: browser.i18n.getMessage("termsAndPrivacyNoticeTermsLink"),
-      [privacySentinel]: browser.i18n.getMessage("termsAndPrivacyNoticyPrivacyLink")
+      [privacySentinel]: browser.i18n.getMessage("termsAndPrivacyNoticyPrivacyLink"),
     };
     const linkUrls = {
       [termsSentinel]: "https://www.mozilla.org/about/legal/terms/services/",
-      [privacySentinel]: "https://www.mozilla.org/privacy/firefox/"
+      [privacySentinel]: "https://www.mozilla.org/privacy/firefox/",
     };
     const text = browser.i18n.getMessage(
       "termsAndPrivacyNotice2",
       [sentinelSplitter + termsSentinel + sentinelSplitter,
        sentinelSplitter + privacySentinel + sentinelSplitter]);
     const parts = text.split(sentinelSplitter);
     for (const part of parts) {
       let el;
--- a/browser/extensions/screenshots/selector/shooter.js
+++ b/browser/extensions/screenshots/selector/shooter.js
@@ -147,34 +147,34 @@ this.shooter = (function() { // eslint-d
         image: {
           url: buildSettings.uploadBinary ? "" : dataUrl,
           type,
           captureType,
           text: captureText,
           location: selectedPos,
           dimensions: {
             x: selectedPos.right - selectedPos.left,
-            y: selectedPos.bottom - selectedPos.top
-          }
-        }
+            y: selectedPos.bottom - selectedPos.top,
+          },
+        },
       });
     }
     catcher.watchPromise(callBackground("takeShot", {
       captureType,
       captureText,
       scroll: {
         scrollX: window.scrollX,
         scrollY: window.scrollY,
         innerHeight: window.innerHeight,
-        innerWidth: window.innerWidth
+        innerWidth: window.innerWidth,
       },
       selectedPos,
       shotId: shotObject.id,
       shot: shotObject.toJSON(),
-      imageBlob
+      imageBlob,
     }).then((url) => {
       return clipboard.copy(url).then((copied) => {
         return callBackground("openShot", { url, copied });
       });
     }, (error) => {
       if ("popupMessage" in error && (error.popupMessage === "REQUEST_ERROR" || error.popupMessage === "CONNECTION_ERROR")) {
         // The error has been signaled to the user, but unlike other errors (or
         // success) we should not abort the selection
@@ -201,30 +201,30 @@ this.shooter = (function() { // eslint-d
       if (!dataUrl) {
         promise = callBackground(
           "screenshotPage",
           selectedPos.toJSON(),
           {
             scrollX: window.scrollX,
             scrollY: window.scrollY,
             innerHeight: window.innerHeight,
-            innerWidth: window.innerWidth
+            innerWidth: window.innerWidth,
           });
       }
       catcher.watchPromise(promise.then((dataUrl) => {
         let type = blobConverters.getTypeFromDataUrl(dataUrl);
         type = type ? type.split("/", 2)[1] : null;
         shotObject.delAllClips();
         shotObject.addClip({
           createdDate: Date.now(),
           image: {
             url: dataUrl,
             type,
-            location: selectedPos
-          }
+            location: selectedPos,
+          },
         });
         ui.triggerDownload(dataUrl, shotObject.filename);
         uicontrol.deactivate();
       }));
     }));
   };
 
   let copyInProgress = null;
@@ -267,17 +267,17 @@ this.shooter = (function() { // eslint-d
     callBackground("sendEvent", ...args);
   };
 
   catcher.watchFunction(() => {
     shotObject = new AbstractShot(
       backend,
       randomString(RANDOM_STRING_LENGTH) + "/" + domainFromUrl(location),
       {
-        origin: shot.originFromUrl(location.href)
+        origin: shot.originFromUrl(location.href),
       }
     );
     shotObject.update(documentMetadata());
   })();
 
   return exports;
 })();
 null;
--- a/browser/extensions/screenshots/selector/ui.js
+++ b/browser/extensions/screenshots/selector/ui.js
@@ -125,17 +125,17 @@ this.ui = (function() { // eslint-disabl
 
   const iframeSelection = exports.iframeSelection = {
     element: null,
     addClassName: "",
     sizeTracking: {
       timer: null,
       windowDelayer: null,
       lastHeight: null,
-      lastWidth: null
+      lastWidth: null,
     },
     document: null,
     display(installHandlerOnDocument) {
       return new Promise((resolve, reject) => {
         if (!this.element) {
           this.element = initializeIframe();
           this.element.id = "firefox-screenshots-selection-iframe";
           this.element.style.display = "none";
@@ -257,17 +257,17 @@ this.ui = (function() { // eslint-disabl
       }
       return el;
     },
 
     remove() {
       this.stopSizeWatch();
       util.removeNode(this.element);
       this.element = this.document = null;
-    }
+    },
   };
 
   iframeSelection.onResize = watchFunction(assertIsTrusted(onResize.bind(iframeSelection)), true);
 
   const iframePreSelection = exports.iframePreSelection = {
     element: null,
     document: null,
     display(installHandlerOnDocument, standardOverlayCallbacks) {
@@ -371,17 +371,17 @@ this.ui = (function() { // eslint-disabl
       return el;
     },
 
     remove() {
       this.hide();
       util.removeNode(this.element);
       this.element = null;
       this.document = null;
-    }
+    },
   };
 
   const iframePreview = exports.iframePreview = {
     element: null,
     document: null,
     display(installHandlerOnDocument, standardOverlayCallbacks) {
       return new Promise((resolve, reject) => {
         if (!this.element) {
@@ -475,17 +475,17 @@ this.ui = (function() { // eslint-disabl
       this.document.body.querySelector(".loader").style.display = "";
     },
 
     remove() {
       this.hide();
       util.removeNode(this.element);
       this.element = null;
       this.document = null;
-    }
+    },
   };
 
   iframePreSelection.onResize = watchFunction(onResize.bind(iframePreSelection), true);
 
   const iframe = exports.iframe = {
     currentIframe: iframePreSelection,
     display(installHandlerOnDocument, standardOverlayCallbacks) {
       return iframeSelection.display(installHandlerOnDocument)
@@ -539,17 +539,17 @@ this.ui = (function() { // eslint-disabl
     },
 
     usePreview() {
       if (this.currentIframe === iframeSelection || this.currentIframe === iframePreSelection) {
         this.hide();
       }
       this.currentIframe = iframePreview;
       this.unhide();
-    }
+    },
   };
 
   const movements = ["topLeft", "top", "topRight", "left", "right", "bottomLeft", "bottom", "bottomRight"];
 
   /** Creates the selection box */
   exports.Box = {
 
     display(pos, callbacks) {
@@ -810,17 +810,17 @@ this.ui = (function() { // eslint-disabl
       }
       this.save.removeAttribute("disabled");
     },
 
     el: null,
     boxTopEl: null,
     boxLeftEl: null,
     boxRightEl: null,
-    boxBottomEl: null
+    boxBottomEl: null,
   };
 
   exports.HoverBox = {
 
     el: null,
 
     display(rect) {
       if (!this.el) {
@@ -841,17 +841,17 @@ this.ui = (function() { // eslint-disabl
       if (this.downloadNotice) {
         this.downloadNotice.display = "none";
       }
     },
 
     remove() {
       util.removeNode(this.el);
       this.el = null;
-    }
+    },
   };
 
   exports.PixelDimensions = {
     el: null,
     xEl: null,
     yEl: null,
     display(xPos, yPos, x, y) {
       if (!this.el) {
@@ -865,17 +865,17 @@ this.ui = (function() { // eslint-disabl
       this.xEl.textContent = Math.round(x);
       this.yEl.textContent = Math.round(y);
       this.el.style.top = (yPos + 12) + "px";
       this.el.style.left = (xPos + 12) + "px";
     },
     remove() {
       util.removeNode(this.el);
       this.el = this.xEl = this.yEl = null;
-    }
+    },
   };
 
   exports.Preview = {
     display(dataUrl, showCropWarning) {
       const img = makeEl("IMG");
       const imgBlob = blobConverters.dataUrlToBlob(dataUrl);
       img.src = URL.createObjectURL(imgBlob);
       iframe.document().querySelector(".preview-image").appendChild(img);
@@ -885,17 +885,17 @@ this.ui = (function() { // eslint-disabl
           <tr class="notice-wrapper">
             <td class="notice-content"></td>
           </tr>
         </tbody>`;
         const contentCell = imageCroppedEl.getElementsByTagName("td");
         contentCell[0].textContent = browser.i18n.getMessage("imageCropPopupWarning", buildSettings.maxImageHeight);
         iframe.document().querySelector(".preview-buttons").appendChild(imageCroppedEl);
       }
-    }
+    },
   };
 
   /** Removes every UI this module creates */
   exports.remove = function() {
     for (const name in exports) {
       if (name.startsWith("iframe")) {
         continue;
       }
--- a/browser/extensions/screenshots/selector/uicontrol.js
+++ b/browser/extensions/screenshots/selector/uicontrol.js
@@ -69,35 +69,35 @@ this.uicontrol = (function() {
 
   function round10(n) {
     return Math.floor(n / 10) * 10;
   }
 
   function eventOptionsForBox(box) {
     return {
       cd1: round10(Math.abs(box.bottom - box.top)),
-      cd2: round10(Math.abs(box.right - box.left))
+      cd2: round10(Math.abs(box.right - box.left)),
     };
   }
 
   function eventOptionsForResize(boxStart, boxEnd) {
     return {
       cd1: round10(
         (boxEnd.bottom - boxEnd.top)
         - (boxStart.bottom - boxStart.top)),
       cd2: round10(
         (boxEnd.right - boxEnd.left)
-        - (boxStart.right - boxStart.left))
+        - (boxStart.right - boxStart.left)),
     };
   }
 
   function eventOptionsForMove(posStart, posEnd) {
     return {
       cd1: round10(posEnd.y - posStart.y),
-      cd2: round10(posEnd.x - posStart.x)
+      cd2: round10(posEnd.x - posStart.x),
     };
   }
 
   function downloadShot() {
     const previewDataUrl = (captureType === "fullPageTruncated") ? null : dataUrl;
     // Downloaded shots don't have dimension limits
     removeDimensionLimitsOnFullPageShot();
     shooter.downloadShot(selectedPos, previewDataUrl, captureType);
@@ -120,26 +120,26 @@ this.uicontrol = (function() {
     topLeft: ["x1", "y1"],
     top: [null, "y1"],
     topRight: ["x2", "y1"],
     left: ["x1", null],
     right: ["x2", null],
     bottomLeft: ["x1", "y2"],
     bottom: [null, "y2"],
     bottomRight: ["x2", "y2"],
-    move: ["*", "*"]
+    move: ["*", "*"],
   };
 
   const doNotAutoselectTags = {
     H1: true,
     H2: true,
     H3: true,
     H4: true,
     H5: true,
-    H6: true
+    H6: true,
   };
 
   let captureType;
 
   function removeDimensionLimitsOnFullPageShot() {
     if (captureType === "fullPageTruncated") {
       captureType = "fullPage";
       selectedPos = new Selection(
@@ -156,17 +156,17 @@ this.uicontrol = (function() {
       sendEvent("save-shot", "overlay-save-button");
       shooter.takeShot("selection", selectedPos);
     }, download: () => {
       sendEvent("download-shot", "overlay-download-button");
       downloadShot();
     }, copy: () => {
       sendEvent("copy-shot", "overlay-copy-button");
       copyShot();
-    }
+    },
   };
 
   const standardOverlayCallbacks = {
     cancel: () => {
       sendEvent("cancel-shot", "cancel-preview-button");
       exports.deactivate();
     },
     onClickCancel: e => {
@@ -220,17 +220,17 @@ this.uicontrol = (function() {
     },
     onDownloadPreview: () => {
       sendEvent(`download-${captureType.replace(/([a-z])([A-Z])/g, "$1-$2").toLowerCase()}`, "download-preview-button");
       downloadShot();
     },
     onCopyPreview: () => {
       sendEvent(`copy-${captureType.replace(/([a-z])([A-Z])/g, "$1-$2").toLowerCase()}`, "copy-preview-button");
       copyShot();
-    }
+    },
   };
 
   /** Holds all the objects that handle events for each state: */
   const stateHandlers = {};
 
   function getState() {
     return getState.state;
   }
@@ -286,38 +286,38 @@ this.uicontrol = (function() {
 
   let dataUrl;
 
   stateHandlers.previewing = {
     start() {
       dataUrl = shooter.screenshotPage(selectedPos, captureType);
       ui.iframe.usePreview();
       ui.Preview.display(dataUrl, captureType === "fullPageTruncated");
-    }
+    },
   };
 
   stateHandlers.onboarding = {
     start() {
       if (typeof slides === "undefined") {
         throw new Error("Attempted to set state to onboarding without loading slides");
       }
       sendEvent("internal", "unhide-onboarding-frame");
       catcher.watchPromise(slides.display({
-        onEnd: this.slidesOnEnd.bind(this)
+        onEnd: this.slidesOnEnd.bind(this),
       }));
     },
 
     slidesOnEnd() {
       callBackground("hasSeenOnboarding");
       setState("crosshairs");
     },
 
     end() {
       slides.remove();
-    }
+    },
   };
 
   stateHandlers.crosshairs = {
 
     cachedEl: null,
 
     start() {
       selectedPos = mousedownPos = null;
@@ -494,17 +494,17 @@ this.uicontrol = (function() {
       event.stopPropagation();
       event.preventDefault();
       return false;
     },
 
     end() {
       ui.HoverBox.remove();
       ui.PixelDimensions.remove();
-    }
+    },
   };
 
   stateHandlers.draggingReady = {
     minMove: 40, // px
     minAutoImageWidth: 40,
     minAutoImageHeight: 40,
     maxAutoElementWidth: 800,
     maxAutoElementHeight: 600,
@@ -585,17 +585,17 @@ this.uicontrol = (function() {
         }
         el = el.parentNode;
       }
       return null;
     },
 
     end() {
       mouseupNoAutoselect = false;
-    }
+    },
 
   };
 
   stateHandlers.dragging = {
 
     start() {
       ui.iframe.useSelection();
       ui.Box.display(selectedPos);
@@ -614,24 +614,24 @@ this.uicontrol = (function() {
       selectedPos.y2 = util.truncateY(event.pageY);
       ui.Box.display(selectedPos, standardDisplayCallbacks);
       sendEvent(
         "make-selection", "selection-drag",
         eventOptionsForBox({
           top: selectedPos.y1,
           bottom: selectedPos.y2,
           left: selectedPos.x1,
-          right: selectedPos.x2
+          right: selectedPos.x2,
         }));
       setState("selected");
     },
 
     end() {
       ui.PixelDimensions.remove();
-    }
+    },
   };
 
   stateHandlers.selected = {
     start() {
       ui.iframe.useSelection();
     },
 
     mousedown(event) {
@@ -648,17 +648,17 @@ this.uicontrol = (function() {
         sendEvent("start-move-selection", "selection");
         stateHandlers.resizing.startResize(event, "move");
       } else if (!ui.Box.isControl(target)) {
         mousedownPos = new Pos(event.pageX, event.pageY);
         setState("crosshairs");
       }
       event.preventDefault();
       return false;
-    }
+    },
   };
 
   stateHandlers.resizing = {
     start() {
       ui.iframe.useSelection();
       selectedPos.sortCoords();
     },
 
@@ -727,24 +727,24 @@ this.uicontrol = (function() {
       scrollIfByEdge(event.pageX, event.pageY);
       ui.Box.display(selectedPos);
     },
 
     end() {
       resizeDirection = resizeStartPos = resizeStartSelected = null;
       selectedPos.sortCoords();
       ui.PixelDimensions.remove();
-    }
+    },
   };
 
   stateHandlers.cancel = {
     start() {
       ui.iframe.hide();
       ui.Box.remove();
-    }
+    },
   };
 
   function getDocumentWidth() {
     return Math.max(
       document.body && document.body.clientWidth,
       document.documentElement.clientWidth,
       document.body && document.body.scrollWidth,
       document.documentElement.scrollWidth);
--- a/browser/extensions/screenshots/selector/util.js
+++ b/browser/extensions/screenshots/selector/util.js
@@ -41,17 +41,17 @@ this.util = (function() { // eslint-disa
     const scrollY = window.scrollY;
     const text = [];
     function traverse(el) {
       let elBox = el.getBoundingClientRect();
       elBox = {
         top: elBox.top + scrollY,
         bottom: elBox.bottom + scrollY,
         left: elBox.left + scrollX,
-        right: elBox.right + scrollX
+        right: elBox.right + scrollX,
       };
       if (elBox.bottom < box.top ||
           elBox.top > box.bottom ||
           elBox.right < box.left ||
           elBox.left > box.right) {
         // Totally outside of the box
         return;
       }