Bug 1572418 - Mitigate first-time HTTPS overhead to avoid ISPDB/addon.json fetch failures. r=BenB
authorNeil Rashbrook <neil@parkwaycc.co.uk>
Fri, 09 Aug 2019 13:10:34 +0100
changeset 27316 e056b7118c3a6b26fd06234b3bd66a8ca88aa938
parent 27315 d924fa692a4221f4f39490ab6c71cdfdee58886b
child 27317 c4e99f8017a764dcb8f1d9688e9bed2456b2884c
push id16278
push usermozilla@jorgk.com
push dateTue, 13 Aug 2019 18:23:10 +0000
treeherdercomm-central@e056b7118c3a [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersBenB
bugs1572418
Bug 1572418 - Mitigate first-time HTTPS overhead to avoid ISPDB/addon.json fetch failures. r=BenB Autoconfiguration represents the very first requests Thunderbird makes. This means that we hit the worst-case scenario for establishing HTTPS. In order to mitigate this, we do two things: - Pre-fetch a two URLs that we know we're likely to access - Increase the timeout on those two URLs for reliability
mail/components/accountcreation/content/emailWizard.js
mail/components/accountcreation/content/exchangeAutoDiscover.js
mail/components/accountcreation/content/fetchConfig.js
mail/components/accountcreation/content/fetchhttp.js
--- a/mail/components/accountcreation/content/emailWizard.js
+++ b/mail/components/accountcreation/content/emailWizard.js
@@ -383,16 +383,22 @@ EmailConfigWizard.prototype = {
     if (Services.io.offline) {
       if (this._currentConfig != null) {
         _hide("half-manual-test_button");
         _hide("create_button");
         _hide("manual-edit_button");
       }
     }
     window.sizeToContent();
+
+    // In a new profile, the first request to live.thunderbird.net
+    // is much slower because of one-time overheads.
+    // Let's create some dummy requests to prime the connections.
+    fetch(Services.prefs.getCharPref("mailnews.auto_config_url"), { method: "OPTIONS" });
+    fetch(Services.prefs.getCharPref("mailnews.auto_config.addons_url"), { method: "OPTIONS" });
   },
 
   /**
    * Start from beginning with possibly new email address.
    */
   onStartOver() {
     this._currentConfig = null;
     if (this._abortable) {
--- a/mail/components/accountcreation/content/exchangeAutoDiscover.js
+++ b/mail/components/accountcreation/content/exchangeAutoDiscover.js
@@ -304,17 +304,17 @@ function readAutoDiscoverXML(autoDiscove
  * @returns {Abortable}
  */
 function getAddonsList(config, successCallback, errorCallback) {
   let url = Services.prefs.getCharPref("mailnews.auto_config.addons_url");
   if (!url) {
     errorCallback(new Exception("no URL for addons list configured"));
     return new Abortable();
   }
-  let fetch = new FetchHTTP(url, { allowCache: true }, function(json) {
+  let fetch = new FetchHTTP(url, { allowCache: true, timeout: 10000 }, function(json) {
     let addons = readAddonsJSON(json);
     addons = addons.filter(addon => {
       // Find types matching the current config.
       // Pick the first in the list as the preferred one and
       // tell the UI to use that one.
       addon.useType = addon.supportedTypes.find(type =>
         config.incoming.owaURL && type.protocolType == "owa" ||
         config.incoming.ewsURL && type.protocolType == "ews" ||
--- a/mail/components/accountcreation/content/fetchConfig.js
+++ b/mail/components/accountcreation/content/fetchConfig.js
@@ -114,17 +114,17 @@ function fetchConfigFromDB(domain, succe
   domain = sanitize.hostname(domain);
 
   // If we don't specify a place to put the domain, put it at the end.
   if (!url.includes("{{domain}}"))
     url = url + domain;
   else
     url = url.replace("{{domain}}", domain);
 
-  let fetch = new FetchHTTP(url, {},
+  let fetch = new FetchHTTP(url, { timeout: 10000 },  // 10 seconds
     function(result) {
       successCallback(readFromXML(result));
     },
     errorCallback);
   fetch.start();
   return fetch;
 }
 
--- a/mail/components/accountcreation/content/fetchhttp.js
+++ b/mail/components/accountcreation/content/fetchhttp.js
@@ -97,16 +97,17 @@ function FetchHTTP(url, args, successCal
     args.headers = {};
   }
 
   this._args = args;
   this._args.post = sanitize.boolean(args.post || false); // default false
   this._args.allowCache = "allowCache" in args ? sanitize.boolean(args.allowCache) : true; // default true
   this._args.allowAuthPrompt = sanitize.boolean(args.allowAuthPrompt || false); // default false
   this._args.requireSecureAuth = sanitize.boolean(args.requireSecureAuth || false); // default false
+  this._args.timeout = sanitize.integer(args.timeout || 5000);  // default 5 seconds
   this._successCallback = successCallback;
   this._errorCallback = errorCallback;
   this._logger = Log4Moz.getConfiguredLogger("mail.setup");
   this._logger.info("Requesting <" + url + ">");
 }
 FetchHTTP.prototype = {
   __proto__: Abortable.prototype,
   _url: null, // URL as passed to ctor, without arguments
@@ -127,17 +128,17 @@ FetchHTTP.prototype = {
     request.mozBackgroundRequest = !this._args.allowAuthPrompt;
     let username = null, password = null;
     if (url.startsWith("https:") || !this._args.requireSecureAuth) {
       username = this._args.username;
       password = this._args.password;
     }
     request.open(this._args.post ? "POST" : "GET", url, true, username, password);
     request.channel.loadGroup = null;
-    request.timeout = 5000; // 5 seconds
+    request.timeout = this._args.timeout;
     // needs bug 407190 patch v4 (or higher) - uncomment if that lands.
     // try {
     //    var channel = request.channel.QueryInterface(Ci.nsIHttpChannel2);
     //    channel.connectTimeout = 5;
     //    channel.requestTimeout = 5;
     //    } catch (e) { dump(e + "\n"); }
 
     if (!this._args.allowCache) {