Bug 1329014 - Enable the no-extra-bind rule and use eslint --fix to autofix the errors. r=standard8
authorJared Wein <jwein@mozilla.com>
Thu, 05 Jan 2017 16:43:29 -0500
changeset 328397 a889d9cb7e9c7a8e07cfb50a1eaed9787d63f6f8
parent 328396 c5007935cdddad95804a80063d69c84d04adacc6
child 328398 5ee72effcfb4beabfb88c1a75b22a9e874f1c3a3
push id85438
push userryanvm@gmail.com
push dateSat, 07 Jan 2017 16:23:13 +0000
treeherdermozilla-inbound@e9d16569a7b4 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersstandard8
bugs1329014
milestone53.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 1329014 - Enable the no-extra-bind rule and use eslint --fix to autofix the errors. r=standard8 MozReview-Commit-ID: BwK94W2mHXS
browser/base/content/aboutNetError.xhtml
browser/components/migration/ChromeProfileMigrator.js
browser/components/migration/SafariProfileMigrator.js
browser/components/newtab/tests/browser/browser_newtab_overrides.js
browser/components/newtab/tests/browser/browser_newtabwebchannel.js
browser/components/newtab/tests/browser/browser_remotenewtab_pageloads.js
browser/components/nsBrowserGlue.js
browser/components/uitour/UITour.jsm
browser/modules/SocialService.jsm
toolkit/.eslintrc.js
toolkit/components/crashes/CrashManager.jsm
toolkit/components/jsdownloads/src/DownloadCore.jsm
toolkit/components/jsdownloads/test/unit/head.js
toolkit/components/places/Bookmarks.jsm
toolkit/components/places/PlacesTransactions.jsm
toolkit/components/places/PlacesUtils.jsm
toolkit/components/places/UnifiedComplete.js
toolkit/components/reader/AboutReader.jsm
toolkit/components/telemetry/TelemetrySession.jsm
toolkit/identity/IdentityProvider.jsm
toolkit/modules/ProfileAge.jsm
toolkit/modules/secondscreen/RokuApp.jsm
toolkit/modules/secondscreen/SimpleServiceDiscovery.jsm
toolkit/mozapps/extensions/content/extensions.js
--- a/browser/base/content/aboutNetError.xhtml
+++ b/browser/base/content/aboutNetError.xhtml
@@ -303,17 +303,17 @@
             // If it looks like an error that is user config based
             if (getErrorCode() == "nssFailure2" && hasPrefStyleError && options && options.changedCertPrefs) {
               showPrefChangeContainer();
             }
           }
           if (getErrorCode() == "weakCryptoUsed" || getErrorCode() == "sslv3Used") {
             setupAdvancedButton(getErrorCode() == "weakCryptoUsed");
           }
-        }.bind(this), true, true);
+        }, true, true);
 
         var event = new CustomEvent("AboutNetErrorLoad", {bubbles:true});
         document.dispatchEvent(event);
 
         if (err == "inadequateSecurityError") {
           // Remove the "Try again" button for HTTP/2 inadequate security as it
           // is useless.
           document.getElementById("errorTryAgain").style.display = "none";
--- a/browser/components/migration/ChromeProfileMigrator.js
+++ b/browser/components/migration/ChromeProfileMigrator.js
@@ -288,18 +288,18 @@ function GetBookmarksResource(aProfileFo
             parentGuid =
               yield MigrationUtils.createImportedBookmarksFolder("Chrome", parentGuid);
           }
           yield insertBookmarkItems(parentGuid, roots.other.children, errorGatherer);
         }
         if (gotErrors) {
           throw new Error("The migration included errors.");
         }
-      }.bind(this)).then(() => aCallback(true),
-                         () => aCallback(false));
+      }).then(() => aCallback(true),
+              () => aCallback(false));
     }
   };
 }
 
 function GetHistoryResource(aProfileFolder) {
   let historyFile = aProfileFolder.clone();
   historyFile.append("History");
   if (!historyFile.exists())
--- a/browser/components/migration/SafariProfileMigrator.js
+++ b/browser/components/migration/SafariProfileMigrator.js
@@ -323,17 +323,17 @@ SearchStrings.prototype = {
           if (recentSearchStrings && recentSearchStrings.length > 0) {
             let changes = recentSearchStrings.map((searchString) => (
               {op: "add",
                fieldname: "searchbar-history",
                value: searchString}));
             FormHistory.update(changes);
           }
         }
-      }.bind(this), aCallback));
+      }, aCallback));
   }
 };
 
 function SafariProfileMigrator() {
 }
 
 SafariProfileMigrator.prototype = Object.create(MigratorPrototype);
 
--- a/browser/components/newtab/tests/browser/browser_newtab_overrides.js
+++ b/browser/components/newtab/tests/browser/browser_newtab_overrides.js
@@ -130,10 +130,10 @@ add_task(function* override_blank_loads_
     yield BrowserTestUtils.removeTab(gBrowser.selectedTab);
   }
 });
 
 function nextChangeNotificationPromise(aNewURL, testMessage) {
   return TestUtils.topicObserved("newtab-url-changed", function observer(aSubject, aData) {  // jshint unused:false
       Assert.equal(aData, aNewURL, testMessage);
       return true;
-  }.bind(this));
+  });
 }
--- a/browser/components/newtab/tests/browser/browser_newtabwebchannel.js
+++ b/browser/components/newtab/tests/browser/browser_newtabwebchannel.js
@@ -86,28 +86,28 @@ add_task(function* webchannel_broadcast(
   let countingMessagePromise = new Promise(resolve => {
     let count = 0;
     NewTabWebChannel.on("foo", function test_message(name, msg) {
       count += 1;
       if (count === 2) {
         NewTabWebChannel.off("foo", test_message);
         resolve(msg.target);
       }
-    }.bind(this));
+    });
   });
 
   let countingReplyPromise = new Promise(resolve => {
     let count = 0;
     NewTabWebChannel.on("reply", function test_message(name, msg) {
       count += 1;
       if (count === 2) {
         NewTabWebChannel.off("reply", test_message);
         resolve(msg.target);
       }
-    }.bind(this));
+    });
   });
 
   let countingUnloadPromise = new Promise(resolve => {
     let count = 0;
     NewTabWebChannel.on("targetUnload", function test_message() {
       count += 1;
       if (count === 2) {
         NewTabWebChannel.off("targetUnload", test_message);
@@ -142,17 +142,17 @@ add_task(function* webchannel_broadcast(
  */
 add_task(function* webchannel_switch() {
   setup();
 
   function newMessagePromise() {
     return new Promise(resolve => {
       NewTabWebChannel.once("foo", function(name, msg) {
         resolve(msg.target);
-      }.bind(this));
+      });
     });
   }
 
   let replyCount = 0;
   function newReplyPromise() {
     return new Promise(resolve => {
       NewTabWebChannel.on("reply", function() {
         replyCount += 1;
--- a/browser/components/newtab/tests/browser/browser_remotenewtab_pageloads.js
+++ b/browser/components/newtab/tests/browser/browser_remotenewtab_pageloads.js
@@ -43,10 +43,10 @@ add_task(function* open_newtab() {
   });
   yield BrowserTestUtils.removeTab(gBrowser.selectedTab);
 });
 
 function nextChangeNotificationPromise(aNewURL, testMessage) {
   return TestUtils.topicObserved("newtab-url-changed", function observer(aSubject, aData) {  // jshint unused:false
       Assert.equal(aData, aNewURL, testMessage);
       return true;
-  }.bind(this));
+  });
 }
--- a/browser/components/nsBrowserGlue.js
+++ b/browser/components/nsBrowserGlue.js
@@ -1156,17 +1156,17 @@ BrowserGlue.prototype = {
                           .add(shouldCheck);
         Services.telemetry.getHistogramById("BROWSER_SET_DEFAULT_DIALOG_PROMPT_RAWCOUNT")
                           .add(promptCount);
       } catch (ex) { /* Don't break the default prompt if telemetry is broken. */ }
 
       if (willPrompt) {
         Services.tm.mainThread.dispatch(function() {
           DefaultBrowserCheck.prompt(RecentWindow.getMostRecentBrowserWindow());
-        }.bind(this), Ci.nsIThread.DISPATCH_NORMAL);
+        }, Ci.nsIThread.DISPATCH_NORMAL);
       }
     }
 
     E10SAccessibilityCheck.onWindowsRestored();
   },
 
   _createExtraDefaultProfile() {
     if (!AppConstants.MOZ_DEV_EDITION) {
--- a/browser/components/uitour/UITour.jsm
+++ b/browser/components/uitour/UITour.jsm
@@ -1313,17 +1313,17 @@ this.UITour = {
         maybeNotifyHeartbeat("Heartbeat:Voted", { score: rating });
 
         // Append the score data to the engagement URL.
         userEngaged(new Map([
           ["type", "stars"],
           ["score", rating],
           ["flowid", aOptions.flowId]
         ]));
-      }.bind(this));
+      });
 
       // Add it to the container.
       ratingContainer.appendChild(ratingElement);
     }
 
     frag.appendChild(ratingContainer);
 
     // Make sure the stars are not pushed to the right by the spacer.
--- a/browser/modules/SocialService.jsm
+++ b/browser/modules/SocialService.jsm
@@ -445,17 +445,17 @@ this.SocialService = {
     }.bind(this));
   },
 
   // Returns a single provider object with the specified origin.  The provider
   // must be "installed" (ie, in ActiveProviders)
   getProvider: function getProvider(origin, onDone) {
     schedule((function() {
       onDone(SocialServiceInternal.providers[origin] || null);
-    }).bind(this));
+    }));
   },
 
   // Returns an unordered array of installed providers
   getProviderList(onDone) {
     schedule(function() {
       onDone(SocialServiceInternal.providerArray);
     });
   },
--- a/toolkit/.eslintrc.js
+++ b/toolkit/.eslintrc.js
@@ -73,16 +73,19 @@ module.exports = {
     "no-dupe-args": "error",
 
     // No duplicate keys in object declarations
     "no-dupe-keys": "error",
 
     // No duplicate cases in switch statements
     "no-duplicate-case": "error",
 
+    // Disallow unnecessary calls to .bind()
+    "no-extra-bind": "error",
+
     // No labels
     "no-labels": "error",
 
     // If an if block ends with a return no need for an else block
     "no-else-return": "error",
 
     // No empty statements
     "no-empty": ["error", {"allowEmptyCatch": true}],
--- a/toolkit/components/crashes/CrashManager.jsm
+++ b/toolkit/components/crashes/CrashManager.jsm
@@ -755,17 +755,17 @@ this.CrashManager.prototype = Object.fre
         });
       } finally {
         it.close();
       }
 
       entries.sort((a, b) => { return a.date - b.date; });
 
       return entries;
-    }.bind(this));
+    });
   },
 
   _getStore() {
     if (this._getStoreTask) {
       return this._getStoreTask;
     }
 
     return this._getStoreTask = Task.spawn(function* () {
--- a/toolkit/components/jsdownloads/src/DownloadCore.jsm
+++ b/toolkit/components/jsdownloads/src/DownloadCore.jsm
@@ -2092,36 +2092,36 @@ this.DownloadCopySaver.prototype = {
                                               keepPartialData);
               } else {
                 // Set the final target file, and delete it on failure.
                 backgroundFileSaver.setTarget(new FileUtils.File(targetPath),
                                               false);
               }
             }.bind(copySaver),
 
-            onStopRequest: function(aRequest, aContext, aStatusCode) {
+            onStopRequest(aRequest, aContext, aStatusCode) {
               try {
                 backgroundFileSaver.onStopRequest(aRequest, aContext,
                                                   aStatusCode);
               } finally {
                 // If the data transfer completed successfully, indicate to the
                 // background file saver that the operation can finish.  If the
                 // data transfer failed, the saver has been already stopped.
                 if (Components.isSuccessCode(aStatusCode)) {
                   backgroundFileSaver.finish(Cr.NS_OK);
                 }
               }
-            }.bind(copySaver),
+            },
 
-            onDataAvailable: function(aRequest, aContext, aInputStream,
+            onDataAvailable(aRequest, aContext, aInputStream,
                                       aOffset, aCount) {
               backgroundFileSaver.onDataAvailable(aRequest, aContext,
                                                   aInputStream, aOffset,
                                                   aCount);
-            }.bind(copySaver),
+            },
           });
 
           // We should check if we have been canceled in the meantime, after
           // all the previous asynchronous operations have been executed and
           // just before we set the _backgroundFileSaver property.
           if (this._canceled) {
             throw new DownloadError({ message: "Saver canceled." });
           }
--- a/toolkit/components/jsdownloads/test/unit/head.js
+++ b/toolkit/components/jsdownloads/test/unit/head.js
@@ -356,17 +356,17 @@ function promiseStartLegacyDownload(aSou
     // the Download object to be created and added to the public downloads.
     transfer.init(sourceURI, NetUtil.newURI(targetFile), null, mimeInfo, null,
                   null, persist, isPrivate);
     persist.progressListener = transfer;
 
     // Start the actual download process.
     persist.savePrivacyAwareURI(sourceURI, null, null, 0, null, null, targetFile,
                                 isPrivate);
-  }.bind(this)).then(null, do_report_unexpected_exception);
+  }).then(null, do_report_unexpected_exception);
 
   return deferred.promise;
 }
 
 /**
  * Starts a new download using the nsIHelperAppService interface, and controls
  * it using the legacy nsITransfer interface.  The source of the download will
  * be "interruptible_resumable.txt" and partially downloaded data will be kept.
@@ -424,17 +424,17 @@ function promiseStartExternalHelperAppSe
       },
 
       onDataAvailable(aRequest, aContext, aInputStream, aOffset,
                                 aCount) {
         this.contentListener.onDataAvailable(aRequest, aContext, aInputStream,
                                              aOffset, aCount);
       },
     });
-  }.bind(this)).then(null, do_report_unexpected_exception);
+  }).then(null, do_report_unexpected_exception);
 
   return deferred.promise;
 }
 
 /**
  * Waits for a download to reach half of its progress, in case it has not
  * reached the expected progress already.
  *
--- a/toolkit/components/places/Bookmarks.jsm
+++ b/toolkit/components/places/Bookmarks.jsm
@@ -1375,17 +1375,17 @@ function reorderChildren(parent, ordered
       yield db.executeCached(
         `DELETE FROM moz_items_annos
          WHERE anno_attribute_id = (SELECT id FROM moz_anno_attributes
                                     WHERE name = :orphanAnno) AND
                item_id IN (${possibleOrphanIds.join(", ")})`,
         { orphanAnno: PlacesSyncUtils.bookmarks.SYNC_PARENT_ANNO });
 
       return children;
-    }.bind(this))
+    })
   );
 }
 
 // Helpers.
 
 /**
  * Merges objects into a new object, included non-enumerable properties.
  *
--- a/toolkit/components/places/PlacesTransactions.jsm
+++ b/toolkit/components/places/PlacesTransactions.jsm
@@ -616,17 +616,17 @@ var TransactionsManager = {
       if (aUndoEntries && aRedoEntries)
         TransactionsHistory.clearAllEntries();
       else if (aUndoEntries)
         TransactionsHistory.clearUndoEntries();
       else if (aRedoEntries)
         TransactionsHistory.clearRedoEntries();
       else
         throw new Error("either aUndoEntries or aRedoEntries should be true");
-    }.bind(this));
+    });
 
     this._transactEnqueuer.alsoWaitFor(promise);
     return promise;
   },
 
   // Updates commands in the undo group of the active window commands.
   // Inactive windows commands will be updated on focus.
   _updateCommandsOnActiveWindow() {
--- a/toolkit/components/places/PlacesUtils.jsm
+++ b/toolkit/components/places/PlacesUtils.jsm
@@ -1833,17 +1833,17 @@ this.PlacesUtils = {
         case Ci.nsINavBookmarksService.TYPE_SEPARATOR:
           item.type = PlacesUtils.TYPE_X_MOZ_PLACE_SEPARATOR;
           break;
         default:
           Cu.reportError("Unexpected bookmark type");
           break;
       }
       return item;
-    }.bind(this);
+    };
 
     const QUERY_STR =
       `/* do not warn (bug no): cannot use an index */
        WITH RECURSIVE
        descendants(fk, level, type, id, guid, parent, parentGuid, position,
                    title, dateAdded, lastModified) AS (
          SELECT b1.fk, 0, b1.type, b1.id, b1.guid, b1.parent,
                 (SELECT guid FROM moz_bookmarks WHERE id = b1.parent),
@@ -2268,17 +2268,17 @@ var Keywords = {
 
         yield PlacesSyncUtils.bookmarks.addSyncChangesForBookmarksWithURL(
           db, url, PlacesSyncUtils.bookmarks.determineSyncChangeDelta(source));
 
         cache.set(keyword, { keyword, url, postData });
 
         // In any case, notify about the new keyword.
         yield notifyKeywordChange(url.href, keyword, source);
-      }.bind(this))
+      })
     );
   },
 
   /**
    * Removes a keyword.
    *
    * @param keyword
    *        The keyword to remove.
@@ -2306,17 +2306,17 @@ var Keywords = {
       yield db.execute(`DELETE FROM moz_keywords WHERE keyword = :keyword`,
                        { keyword });
 
       yield PlacesSyncUtils.bookmarks.addSyncChangesForBookmarksWithURL(
         db, url, PlacesSyncUtils.bookmarks.determineSyncChangeDelta(source));
 
       // Notify bookmarks about the removal.
       yield notifyKeywordChange(url.href, "", source);
-    }.bind(this))) ;
+    }));
   }
 };
 
 // Set by the keywords API to distinguish notifications fired by the old API.
 // Once the old API will be gone, we can remove this and stop observing.
 var gIgnoreKeywordNotifications = false;
 
 XPCOMUtils.defineLazyGetter(this, "gKeywordsCachePromise", () =>
--- a/toolkit/components/places/UnifiedComplete.js
+++ b/toolkit/components/places/UnifiedComplete.js
@@ -1993,17 +1993,17 @@ UnifiedComplete.prototype = {
         // indices.  A larger cache helps reducing IO and improving performance.
         // The value used here is larger than the default Storage value defined
         // as MAX_CACHE_SIZE_BYTES in storage/mozStorageConnection.cpp.
         yield conn.execute("PRAGMA cache_size = -6144"); // 6MiB
 
         yield SwitchToTabStorage.initDatabase(conn);
 
         return conn;
-      }.bind(this)).then(null, ex => {
+      }).then(null, ex => {
  dump("Couldn't get database handle: " + ex + "\n");
                                        Cu.reportError(ex);
 });
     }
     return this._promiseDatabase;
   },
 
   // mozIPlacesAutoComplete
--- a/toolkit/components/reader/AboutReader.jsm
+++ b/toolkit/components/reader/AboutReader.jsm
@@ -906,17 +906,17 @@ AboutReader.prototype = {
 
         let items = segmentedButton.children;
         for (let j = items.length - 1; j >= 0; j--) {
           items[j].classList.remove("selected");
         }
 
         item.classList.add("selected");
         callback(option.value);
-      }.bind(this), true);
+      }, true);
 
       if (option.value === initialValue)
         item.classList.add("selected");
     }
   },
 
   _setupButton(id, callback, titleEntity, textEntity) {
     if (titleEntity) {
--- a/toolkit/components/telemetry/TelemetrySession.jsm
+++ b/toolkit/components/telemetry/TelemetrySession.jsm
@@ -1906,17 +1906,17 @@ var Impl = {
     case "idle-daily":
       // Enqueue to main-thread, otherwise components may be inited by the
       // idle-daily category and miss the gather-telemetry notification.
       Services.tm.mainThread.dispatch((function() {
         // Notify that data should be gathered now.
         // TODO: We are keeping this behaviour for now but it will be removed as soon as
         // bug 1127907 lands.
         Services.obs.notifyObservers(null, "gather-telemetry", null);
-      }).bind(this), Ci.nsIThread.DISPATCH_NORMAL);
+      }), Ci.nsIThread.DISPATCH_NORMAL);
       break;
 
     case "application-background":
       if (AppConstants.platform !== "android") {
         break;
       }
       // On Android, we can get killed without warning once we are in the background,
       // but we may also submit data and/or come back into the foreground without getting
--- a/toolkit/identity/IdentityProvider.jsm
+++ b/toolkit/identity/IdentityProvider.jsm
@@ -248,17 +248,17 @@ IdentityProviderService.prototype = {
       }
 
       provFlow.kp = kp;
 
       // Serialize the publicKey of the keypair and send it back to the
       // sandbox.
       log("genKeyPair: generated keypair for provisioning flow with id:", aProvId);
       provFlow.caller.doGenKeyPairCallback(provFlow.kp.serializedPublicKey);
-    }.bind(this));
+    });
   },
 
   /**
    * When navigator.id.registerCertificate is called from provisioning iframe
    * sandbox.
    *
    * Sets the certificate for the user for which a certificate was requested
    * via a preceding call to beginProvisioning (and genKeypair).
--- a/toolkit/modules/ProfileAge.jsm
+++ b/toolkit/modules/ProfileAge.jsm
@@ -46,17 +46,17 @@ this.ProfileAge.prototype = {
       }
       return onFailure.call(this, null, times);
     }
 
     function onFailure(err, times) {
       return this.computeAndPersistCreated(times)
                  .then(function onSuccess(created) {
                          return created;
-                       }.bind(this));
+                       });
     }
 
     return this.getTimes()
                .then(onSuccess.bind(this),
                      onFailure.bind(this));
   },
 
   /**
--- a/toolkit/modules/secondscreen/RokuApp.jsm
+++ b/toolkit/modules/secondscreen/RokuApp.jsm
@@ -55,17 +55,17 @@ RokuApp.prototype = {
         callback({ state: "unknown" });
       }
     }).bind(this), false);
 
     xhr.addEventListener("error", (function() {
       if (callback) {
         callback({ state: "unknown" });
       }
-    }).bind(this), false);
+    }), false);
 
     xhr.send(null);
   },
 
   start: function start(callback) {
     // We need to make sure we have cached the mediaAppID
     if (this.mediaAppID == -1) {
       this.status(function() {
@@ -86,46 +86,46 @@ RokuApp.prototype = {
     let xhr = Cc["@mozilla.org/xmlextras/xmlhttprequest;1"].createInstance(Ci.nsIXMLHttpRequest);
     xhr.open("POST", url, true);
     xhr.overrideMimeType("text/plain");
 
     xhr.addEventListener("load", (function() {
       if (callback) {
         callback(xhr.status === 200);
       }
-    }).bind(this), false);
+    }), false);
 
     xhr.addEventListener("error", (function() {
       if (callback) {
         callback(false);
       }
-    }).bind(this), false);
+    }), false);
 
     xhr.send(null);
   },
 
   stop: function stop(callback) {
     // Roku doesn't seem to support stopping an app, so let's just go back to
     // the Home screen
     let url = this.resourceURL + "keypress/Home";
     let xhr = Cc["@mozilla.org/xmlextras/xmlhttprequest;1"].createInstance(Ci.nsIXMLHttpRequest);
     xhr.open("POST", url, true);
     xhr.overrideMimeType("text/plain");
 
     xhr.addEventListener("load", (function() {
       if (callback) {
         callback(xhr.status === 200);
       }
-    }).bind(this), false);
+    }), false);
 
     xhr.addEventListener("error", (function() {
       if (callback) {
         callback(false);
       }
-    }).bind(this), false);
+    }), false);
 
     xhr.send(null);
   },
 
   remoteMedia: function remoteMedia(callback, listener) {
     if (this.mediaAppID != -1) {
       if (callback) {
         callback(new RemoteMedia(this.resourceURL, listener));
--- a/toolkit/modules/secondscreen/SimpleServiceDiscovery.jsm
+++ b/toolkit/modules/secondscreen/SimpleServiceDiscovery.jsm
@@ -75,17 +75,17 @@ var SimpleServiceDiscovery = {
     let service = {};
     response.forEach(function(row) {
       let name = row.toUpperCase();
       if (name.startsWith("LOCATION")) {
         service.location = row.substr(10).trim();
       } else if (name.startsWith("ST")) {
         service.target = row.substr(4).trim();
       }
-    }.bind(this));
+    });
 
     if (service.location && service.target) {
       service.location = this._forceTrailingSlash(service.location);
 
       // When we find a valid response, package up the service information
       // and pass it on.
       try {
         this._processService(service);
--- a/toolkit/mozapps/extensions/content/extensions.js
+++ b/toolkit/mozapps/extensions/content/extensions.js
@@ -3486,17 +3486,17 @@ var gDetailView = {
               firstSetting = setting;
             }
           }
 
           finish(firstSetting);
 
           if (aCallback)
             aCallback();
-        }).bind(this);
+        });
         xhr.onerror = function(aEvent) {
           Cu.reportError("Error " + aEvent.target.status +
                          " occurred while receiving " + this._addon.optionsURL);
           if (aCallback)
             aCallback();
         };
         xhr.send();
       }