Bug 1496741 - Cleanup adb-addon.js module;r=ladybenko
authorJulian Descottes <jdescottes@mozilla.com>
Tue, 02 Oct 2018 11:25:03 +0200
changeset 496044 a7a2ce19cf57ed93bcf26d6fce128d6a2497ecc8
parent 496043 13430c50d08491283e924ac2598b95528aebe642
child 496045 ae15dbcedd8a73fc2a53b231354c49321da74ee1
push id9984
push userffxbld-merge
push dateMon, 15 Oct 2018 21:07:35 +0000
treeherdermozilla-beta@183d27ea8570 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersladybenko
bugs1496741
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 1496741 - Cleanup adb-addon.js module;r=ladybenko
devtools/client/aboutdebugging-new/src/modules/usb-runtimes.js
devtools/client/webide/content/addons.js
devtools/shared/adb/adb-addon.js
devtools/shared/apps/Devices.jsm
--- a/devtools/client/aboutdebugging-new/src/modules/usb-runtimes.js
+++ b/devtools/client/aboutdebugging-new/src/modules/usb-runtimes.js
@@ -1,33 +1,34 @@
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 "use strict";
 
 const { ADBScanner } = require("devtools/shared/adb/adb-scanner");
 loader.lazyRequireGetter(this, "adbAddon", "devtools/shared/adb/adb-addon", true);
+loader.lazyRequireGetter(this, "ADB_ADDON_STATES", "devtools/shared/adb/adb-addon", true);
 
 /**
  * This module provides a collection of helper methods to detect USB runtimes whom Firefox
  * is running on.
  */
 function addUSBRuntimesObserver(listener) {
   ADBScanner.on("runtime-list-updated", listener);
 }
 exports.addUSBRuntimesObserver = addUSBRuntimesObserver;
 
 function disableUSBRuntimes() {
   ADBScanner.disable();
 }
 exports.disableUSBRuntimes = disableUSBRuntimes;
 
 async function enableUSBRuntimes() {
-  if (adbAddon.status !== "installed") {
+  if (adbAddon.status !== ADB_ADDON_STATES.INSTALLED) {
     console.error("ADB extension is not installed");
     return;
   }
 
   ADBScanner.enable();
 }
 exports.enableUSBRuntimes = enableUSBRuntimes;
 
--- a/devtools/client/webide/content/addons.js
+++ b/devtools/client/webide/content/addons.js
@@ -7,16 +7,17 @@ const {loader, require} = ChromeUtils.im
 const Services = require("Services");
 const Strings = Services.strings.createBundle("chrome://devtools/locale/webide.properties");
 
 const {gDevTools} = require("devtools/client/framework/devtools");
 const {ADBScanner} = require("devtools/shared/adb/adb-scanner");
 const {RuntimeScanners} = require("devtools/client/webide/modules/runtimes");
 
 loader.lazyRequireGetter(this, "adbAddon", "devtools/shared/adb/adb-addon", true);
+loader.lazyRequireGetter(this, "ADB_ADDON_STATES", "devtools/shared/adb/adb-addon", true);
 
 window.addEventListener("load", function() {
   document.querySelector("#aboutaddons").onclick = function() {
     const browserWin = Services.wm.getMostRecentWindow(gDevTools.chromeWindowType);
     if (browserWin && browserWin.BrowserOpenAddonsMgr) {
       browserWin.BrowserOpenAddonsMgr("addons://list/extension");
     }
   };
@@ -28,19 +29,19 @@ function CloseUI() {
   window.parent.UI.openProject();
 }
 
 function BuildUI() {
   function onAddonUpdate(arg) {
     progress.removeAttribute("value");
     li.setAttribute("status", adbAddon.status);
     status.textContent = Strings.GetStringFromName("addons_status_" + adbAddon.status);
-    if (adbAddon.status == "installed") {
+    if (adbAddon.status == ADB_ADDON_STATES.INSTALLED) {
       RuntimeScanners.add(ADBScanner);
-    } else if (adbAddon.status == "uninstalled") {
+    } else if (adbAddon.status == ADB_ADDON_STATES.UNINSTALLED) {
       RuntimeScanners.remove(ADBScanner);
     }
   }
 
   function onAddonFailure(arg) {
     window.parent.UI.reportError("error_operationFail", arg);
   }
 
--- a/devtools/shared/adb/adb-addon.js
+++ b/devtools/shared/adb/adb-addon.js
@@ -9,145 +9,180 @@ const Services = require("Services");
 const EventEmitter = require("devtools/shared/event-emitter");
 
 const ADB_LINK = Services.prefs.getCharPref("devtools.remote.adb.extensionURL");
 const ADB_ADDON_ID = Services.prefs.getCharPref("devtools.remote.adb.extensionID");
 
 // Extension ID for adb helper extension that might be installed on Firefox 63 or older.
 const OLD_ADB_ADDON_ID = "adbhelper@mozilla.org";
 
-const platform = Services.appShell.hiddenDOMWindow.navigator.platform;
-let OS = "";
-if (platform.includes("Win")) {
-  OS = "win32";
-} else if (platform.includes("Mac")) {
-  OS = "mac64";
-} else if (platform.includes("Linux")) {
-  if (platform.includes("x86_64")) {
-    OS = "linux64";
-  } else {
-    OS = "linux32";
-  }
-}
-
-function ADBAddon() {
-  EventEmitter.decorate(this);
-
-  this._status = "unknown";
+// Possible values for ADBAddon::state. WebIDE relies on the exact values for localization
+// and styles, so they should not be updated until WebIDE is removed.
+const ADB_ADDON_STATES = {
+  DOWNLOADING: "downloading",
+  INSTALLED: "installed",
+  INSTALLING: "installing",
+  PREPARING: "preparing",
+  UNINSTALLED: "uninstalled",
+  UNKNOWN: "unknown",
+};
+exports.ADB_ADDON_STATES = ADB_ADDON_STATES;
 
-  // This addon uses the string "linux" for "linux32"
-  const fixedOS = OS == "linux32" ? "linux" : OS;
-  this.xpiLink = ADB_LINK.replace(/#OS#/g, fixedOS);
-
-  // Uninstall old version of the extension that might be installed on this profile.
-  this.uninstallOldExtension();
-
-  this.updateInstallStatus();
+/**
+ * Wrapper around the ADB Extension providing ADB binaries for devtools remote debugging.
+ * Fires the following events:
+ * - "update": the status of the addon was updated
+ * - "failure": addon installation failed
+ * - "progress": addon download in progress
+ *
+ * AdbAddon::state can take any of the values from ADB_ADDON_STATES.
+ */
+class ADBAddon extends EventEmitter {
+  constructor() {
+    super();
 
-  const addonsListener = {};
-  addonsListener.onEnabled =
-  addonsListener.onDisabled =
-  addonsListener.onInstalled =
-  addonsListener.onUninstalled = () => this.updateInstallStatus();
-  AddonManager.addAddonListener(addonsListener);
-}
+    this._status = ADB_ADDON_STATES.UNKNOWN;
+
+    // Uninstall old version of the extension that might be installed on this profile.
+    this.uninstallOldExtension();
 
-ADBAddon.prototype = {
+    const addonsListener = {};
+    addonsListener.onEnabled =
+    addonsListener.onDisabled =
+    addonsListener.onInstalled =
+    addonsListener.onUninstalled = () => this.updateInstallStatus();
+    AddonManager.addAddonListener(addonsListener);
+
+    this.updateInstallStatus();
+  }
+
   set status(value) {
     if (this._status != value) {
       this._status = value;
       this.emit("update");
     }
-  },
+  }
 
   get status() {
     return this._status;
-  },
+  }
 
-  updateInstallStatus: async function() {
+  async updateInstallStatus() {
     const addon = await AddonManager.getAddonByID(ADB_ADDON_ID);
     if (addon && !addon.userDisabled) {
-      this.status = "installed";
+      this.status = ADB_ADDON_STATES.INSTALLED;
     } else {
-      this.status = "uninstalled";
+      this.status = ADB_ADDON_STATES.UNINSTALLED;
     }
-  },
+  }
+
+  /**
+   * Returns the platform specific download link for the ADB extension.
+   */
+  _getXpiLink() {
+    const platform = Services.appShell.hiddenDOMWindow.navigator.platform;
+    let OS = "";
+    if (platform.includes("Win")) {
+      OS = "win32";
+    } else if (platform.includes("Mac")) {
+      OS = "mac64";
+    } else if (platform.includes("Linux")) {
+      if (platform.includes("x86_64")) {
+        OS = "linux64";
+      } else {
+        OS = "linux";
+      }
+    }
+
+    return ADB_LINK.replace(/#OS#/g, OS);
+  }
 
   /**
    * Install and enable the adb extension. Returns a promise that resolves when ADB is
    * enabled.
    *
    * @param {String} source
    *        String passed to the AddonManager for telemetry.
    */
-  install: async function(source) {
+  async install(source) {
     const addon = await AddonManager.getAddonByID(ADB_ADDON_ID);
     if (addon && !addon.userDisabled) {
-      this.status = "installed";
+      this.status = ADB_ADDON_STATES.INSTALLED;
       return;
     }
-    this.status = "preparing";
+    this.status = ADB_ADDON_STATES.PREPARING;
     if (addon && addon.userDisabled) {
       await addon.enable();
     } else {
       const install = await AddonManager.getInstallForURL(
-        this.xpiLink,
+        this._getXpiLink(),
         "application/x-xpinstall",
         null, null, null, null, null,
         { source }
       );
       install.addListener(this);
       install.install();
     }
-  },
+  }
 
-  uninstall: async function() {
+  async uninstall() {
     const addon = await AddonManager.getAddonByID(ADB_ADDON_ID);
     addon.uninstall();
-  },
+  }
 
-  uninstallOldExtension: async function() {
+  async uninstallOldExtension() {
     const oldAddon = await AddonManager.getAddonByID(OLD_ADB_ADDON_ID);
     if (oldAddon) {
       oldAddon.uninstall();
     }
-  },
+  }
 
-  installFailureHandler: function(install, message) {
-    this.status = "uninstalled";
+  installFailureHandler(install, message) {
+    this.status = ADB_ADDON_STATES.UNINSTALLED;
     this.emit("failure", message);
-  },
+  }
 
-  onDownloadStarted: function() {
-    this.status = "downloading";
-  },
+  // Expected AddonManager install listener.
+  onDownloadStarted() {
+    this.status = ADB_ADDON_STATES.DOWNLOADING;
+  }
 
-  onInstallStarted: function() {
-    this.status = "installing";
-  },
-
-  onDownloadProgress: function(install) {
+  // Expected AddonManager install listener.
+  onDownloadProgress(install) {
     if (install.maxProgress == -1) {
       this.emit("progress", -1);
     } else {
       this.emit("progress", install.progress / install.maxProgress);
     }
-  },
+  }
 
-  onInstallEnded: function({addon}) {
-    addon.enable();
-  },
-
-  onDownloadCancelled: function(install) {
+  // Expected AddonManager install listener.
+  onDownloadCancelled(install) {
     this.installFailureHandler(install, "Download cancelled");
-  },
-  onDownloadFailed: function(install) {
+  }
+
+  // Expected AddonManager install listener.
+  onDownloadFailed(install) {
     this.installFailureHandler(install, "Download failed");
-  },
-  onInstallCancelled: function(install) {
+  }
+
+  // Expected AddonManager install listener.
+  onInstallStarted() {
+    this.status = ADB_ADDON_STATES.INSTALLING;
+  }
+
+  // Expected AddonManager install listener.
+  onInstallCancelled(install) {
     this.installFailureHandler(install, "Install cancelled");
-  },
-  onInstallFailed: function(install) {
+  }
+
+  // Expected AddonManager install listener.
+  onInstallFailed(install) {
     this.installFailureHandler(install, "Install failed");
-  },
-};
+  }
+
+  // Expected AddonManager install listener.
+  onInstallEnded({addon}) {
+    addon.enable();
+  }
+}
 
 exports.adbAddon = new ADBAddon();
--- a/devtools/shared/apps/Devices.jsm
+++ b/devtools/shared/apps/Devices.jsm
@@ -1,23 +1,23 @@
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 "use strict";
 
 const { require } = ChromeUtils.import("resource://devtools/shared/Loader.jsm", {});
 const EventEmitter = require("devtools/shared/event-emitter");
-const { adbAddon } = require("devtools/shared/adb/adb-addon");
+const { adbAddon, ADB_ADDON_STATES } = require("devtools/shared/adb/adb-addon");
 
 /* exported EXPORTED_SYMBOLS */
 
 const EXPORTED_SYMBOLS = ["Devices"];
 
-var addonInstalled = adbAddon.status === "installed";
+var addonInstalled = adbAddon.status === ADB_ADDON_STATES.INSTALLED;
 
 const Devices = {
   _devices: {},
 
   get adbExtensionInstalled() {
     return addonInstalled;
   },
   set adbExtensionInstalled(v) {
@@ -44,17 +44,17 @@ const Devices = {
     return Object.keys(this._devices).sort();
   },
 
   getByName: function(name) {
     return this._devices[name];
   },
 
   updateAdbAddonStatus: function() {
-    this.adbExtensionInstalled = adbAddon.status === "installed";
+    this.adbExtensionInstalled = adbAddon.status === ADB_ADDON_STATES.INSTALLED;
   },
 };
 
 Object.defineProperty(this, "Devices", {
   value: Devices,
   enumerable: true,
   writable: false
 });