Backed out changeset 3bd665597cff (bug 1251175) for causing bc failures
authorCarsten "Tomcat" Book <cbook@mozilla.com>
Thu, 02 Jun 2016 12:50:47 +0200
changeset 339168 29fc4a93e85c4110604e590d5069339b1e4b40f2
parent 339167 130a21afe56281e8b876f7fa6c63335458bdeba1
child 339169 153b81041c1e63717880e425c09423236c7971b6
push id6249
push userjlund@mozilla.com
push dateMon, 01 Aug 2016 13:59:36 +0000
treeherdermozilla-beta@bad9d4f5bf7e [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
bugs1251175
milestone49.0a1
backs out3bd665597cffa106f9dbbeae3262d670e8fbe390
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
Backed out changeset 3bd665597cff (bug 1251175) for causing bc failures
dom/manifest/test/browser.ini
dom/manifest/test/browser_ManifestFinder_browserHasManifestLink.js
dom/manifest/test/browser_ManifestObtainer_obtain.js
dom/manifest/test/resource.sjs
--- a/dom/manifest/test/browser.ini
+++ b/dom/manifest/test/browser.ini
@@ -1,11 +1,8 @@
 [DEFAULT]
 support-files =
   manifestLoader.html
   file_reg_install_event.html
   file_testserver.sjs
-support-files =
-  resource.sjs
-  manifestLoader.html
 [browser_ManifestFinder_browserHasManifestLink.js]
 [browser_ManifestObtainer_obtain.js]
 [browser_fire_install_event.js]
\ No newline at end of file
--- a/dom/manifest/test/browser_ManifestFinder_browserHasManifestLink.js
+++ b/dom/manifest/test/browser_ManifestFinder_browserHasManifestLink.js
@@ -1,84 +1,114 @@
 //Used by JSHint:
-/*global Cu, BrowserTestUtils, ok, add_task, gBrowser */
+/*global Cu, BrowserTestUtils, is, ok, add_task, gBrowser, ManifestFinder */
 "use strict";
-const { ManifestFinder } = Cu.import("resource://gre/modules/ManifestFinder.jsm", {});
-const defaultURL = new URL("http://example.org/browser/dom/manifest/test/resource.sjs");
-defaultURL.searchParams.set("Content-Type", "text/html; charset=utf-8");
+Cu.import("resource://gre/modules/ManifestFinder.jsm", this);  // jshint ignore:line
 
+const defaultURL =
+  "http://example.org/tests/dom/manifest/test/resource.sjs";
 const tests = [{
-  body: `
-    <link rel="manifesto" href='${defaultURL}?body={"name":"fail"}'>
-    <link rel="foo bar manifest bar test" href='${defaultURL}?body={"name":"value"}'>
-    <link rel="manifest" href='${defaultURL}?body={"name":"fail"}'>
-  `,
+  expected: "Document has a web manifest.",
+  get tabURL() {
+    let query = [
+      `body=<h1>${this.expected}</h1>`,
+      "Content-Type=text/html; charset=utf-8",
+    ];
+    const URL = `${defaultURL}?${query.join("&")}`;
+    return URL;
+  },
   run(result) {
-    ok(result, "Document has a web manifest.");
+    is(result, true, this.expected);
   },
+  testData: `
+      <link rel="manifesto" href='${defaultURL}?body={"name":"fail"}'>
+      <link rel="foo bar manifest bar test" href='${defaultURL}?body={"name":"value"}'>
+      <link rel="manifest" href='${defaultURL}?body={"name":"fail"}'>`
 }, {
-  body: `
-    <link rel="amanifista" href='${defaultURL}?body={"name":"fail"}'>
-    <link rel="foo bar manifesto bar test" href='${defaultURL}?body={"name":"pass-1"}'>
-    <link rel="manifesto" href='${defaultURL}?body={"name":"fail"}'>`,
+  expected: "Document does not have a web manifest.",
+  get tabURL() {
+    let query = [
+      `body=<h1>${this.expected}</h1>`,
+      "Content-Type=text/html; charset=utf-8",
+    ];
+    const URL = `${defaultURL}?${query.join("&")}`;
+    return URL;
+  },
   run(result) {
-    ok(!result, "Document does not have a web manifest.");
+    is(result, false, this.expected);
   },
+  testData: `
+      <link rel="amanifista" href='${defaultURL}?body={"name":"fail"}'>
+      <link rel="foo bar manifesto bar test" href='${defaultURL}?body={"name":"pass-1"}'>
+      <link rel="manifesto" href='${defaultURL}?body={"name":"fail"}'>`
 }, {
-  body: `
-    <link rel="manifest" href="">
-    <link rel="manifest" href='${defaultURL}?body={"name":"fail"}'>`,
+  expected: "Manifest link is has empty href.",
+  get tabURL() {
+    let query = [
+      `body=<h1>${this.expected}</h1>`,
+      "Content-Type=text/html; charset=utf-8",
+    ];
+    const URL = `${defaultURL}?${query.join("&")}`;
+    return URL;
+  },
   run(result) {
-    ok(!result, "Manifest link is has empty href.");
+    is(result, false, this.expected);
   },
+  testData: `
+  <link rel="manifest" href="">
+  <link rel="manifest" href='${defaultURL}?body={"name":"fail"}'>`
 }, {
-  body: `
+  expected: "Manifest link is missing.",
+  get tabURL() {
+    let query = [
+      `body=<h1>${this.expected}</h1>`,
+      "Content-Type=text/html; charset=utf-8",
+    ];
+    const URL = `${defaultURL}?${query.join("&")}`;
+    return URL;
+  },
+  run(result) {
+    is(result, false, this.expected);
+  },
+  testData: `
     <link rel="manifest">
-    <link rel="manifest" href='${defaultURL}?body={"name":"fail"}'>`,
-  run(result) {
-    ok(!result, "Manifest link is missing.");
-  },
+    <link rel="manifest" href='${defaultURL}?body={"name":"fail"}'>`
 }];
 
-function makeTestURL({ body }) {
-  const url = new URL(defaultURL);
-  url.searchParams.set("body", encodeURIComponent(body));
-  return url.href;
-}
-
 /**
  * Test basic API error conditions
  */
-add_task(function*() {
-  const expected = "Invalid types should throw a TypeError.";
+add_task(function* () {
+  let expected = "Invalid types should throw a TypeError.";
   for (let invalidValue of [undefined, null, 1, {}, "test"]) {
     try {
       yield ManifestFinder.contentManifestLink(invalidValue);
       ok(false, expected);
     } catch (e) {
       is(e.name, "TypeError", expected);
     }
     try {
       yield ManifestFinder.browserManifestLink(invalidValue);
       ok(false, expected);
     } catch (e) {
       is(e.name, "TypeError", expected);
     }
   }
 });
 
-add_task(function*() {
-  const runningTests = tests
-    .map(
-      test => ({
-        gBrowser,
-        test,
-        url: makeTestURL(test),
-      })
-    )
-    .map(
-      tabOptions => BrowserTestUtils.withNewTab(tabOptions, function*(browser) {
-        const result = yield ManifestFinder.browserHasManifestLink(browser);
-        tabOptions.test.run(result);
-      })
+add_task(function* () {
+  for (let test of tests) {
+    let tabOptions = {
+      gBrowser: gBrowser,
+      url: test.tabURL,
+    };
+    yield BrowserTestUtils.withNewTab(
+      tabOptions,
+      browser => testHasManifest(browser, test)
     );
-  yield Promise.all(runningTests);
+  }
+
+  function* testHasManifest(aBrowser, aTest) {
+    aBrowser.contentWindowAsCPOW.document.head.innerHTML = aTest.testData;
+    const result = yield ManifestFinder.browserHasManifestLink(aBrowser);
+    aTest.run(result);
+  }
 });
--- a/dom/manifest/test/browser_ManifestObtainer_obtain.js
+++ b/dom/manifest/test/browser_ManifestObtainer_obtain.js
@@ -1,175 +1,249 @@
 //Used by JSHint:
-/*global is, Cu, BrowserTestUtils, add_task, gBrowser, makeTestURL*/
-'use strict';
-const { ManifestObtainer } = Cu.import('resource://gre/modules/ManifestObtainer.jsm', {});
-const remoteURL = 'http://mochi.test:8888/browser/dom/manifest/test/resource.sjs';
-const defaultURL = new URL('http://example.org/browser/dom/manifest/test/resource.sjs');
-defaultURL.searchParams.set('Content-Type', 'text/html; charset=utf-8');
+/*global requestLongerTimeout, Cu, BrowserTestUtils, add_task, SpecialPowers, gBrowser, Assert*/ 'use strict';
+const {
+  ManifestObtainer
+} = Cu.import('resource://gre/modules/ManifestObtainer.jsm', {});
 
+requestLongerTimeout(4); // e10s tests take time.
+const defaultURL =
+  'http://example.org/tests/dom/manifest/test/resource.sjs';
+const remoteURL =
+  'http://mochi.test:8888/tests/dom/manifest/test/resource.sjs';
 const tests = [
   // Fetch tests.
   {
-    body: `
-      <link rel="manifesto" href='resource.sjs?body={"name":"fail"}'>
-      <link rel="foo bar manifest bar test" href='resource.sjs?body={"name":"pass-1"}'>
-      <link rel="manifest" href='resource.sjs?body={"name":"fail"}'>`,
+    expected: 'Manifest is first `link` where @rel contains token manifest.',
+    get tabURL() {
+      let query = [
+        `body=<h1>${this.expected}</h1>`,
+        'Content-Type=text/html; charset=utf-8',
+      ];
+      const URL = `${defaultURL}?${query.join('&')}`;
+      return URL;
+    },
     run(manifest) {
-      is(manifest.name, 'pass-1', 'Manifest is first `link` where @rel contains token manifest.');
-    }
+      Assert.strictEqual(manifest.name, 'pass-1', this.expected);
+    },
+    testData: `
+      <link rel="manifesto" href='${defaultURL}?body={"name":"fail"}'>
+      <link rel="foo bar manifest bar test" href='${defaultURL}?body={"name":"pass-1"}'>
+      <link rel="manifest" href='${defaultURL}?body={"name":"fail"}'>`
   }, {
-    body: `
+    expected: 'Manifest is first `link` where @rel contains token manifest.',
+    get tabURL() {
+      let query = [
+        `body=<h1>${this.expected}</h1>`,
+        'Content-Type=text/html; charset=utf-8',
+      ];
+      const URL = `${defaultURL}?${query.join('&')}`;
+      return URL;
+    },
+    run(manifest) {
+      Assert.strictEqual(manifest.name, 'pass-2', this.expected);
+    },
+    testData: `
       <link rel="foo bar manifest bar test" href='resource.sjs?body={"name":"pass-2"}'>
       <link rel="manifest" href='resource.sjs?body={"name":"fail"}'>
-      <link rel="manifest foo bar test" href='resource.sjs?body={"name":"fail"}'>`,
-    run(manifest) {
-      is(manifest.name, 'pass-2', 'Manifest is first `link` where @rel contains token manifest.');
-    },
+      <link rel="manifest foo bar test" href='resource.sjs?body={"name":"fail"}'>`
   }, {
-    body: `<link rel="manifest" href='${remoteURL}?body={"name":"pass-3"}'>`,
+    expected: 'By default, manifest cannot load cross-origin.',
+    get tabURL() {
+      let query = [
+        `body=<h1>${this.expected}</h1>`,
+        'Content-Type=text/html; charset=utf-8',
+      ];
+      const URL = `${defaultURL}?${query.join('&')}`;
+      return URL;
+    },
     run(err) {
-      is(err.name, 'TypeError', 'By default, manifest cannot load cross-origin.');
+      Assert.strictEqual(err.name, 'TypeError', this.expected);
     },
+    testData: `<link rel="manifest" href='${remoteURL}?body={"name":"pass-3"}'>`
   },
   // CORS Tests.
   {
-    get body() {
+    expected: 'CORS enabled, manifest must be fetched.',
+    get tabURL() {
+      let query = [
+        `body=<h1>${this.expected}</h1>`,
+        'Content-Type=text/html; charset=utf-8',
+      ];
+      const URL = `${defaultURL}?${query.join('&')}`;
+      return URL;
+    },
+    run(manifest) {
+      Assert.strictEqual(manifest.name, 'pass-4', this.expected);
+    },
+    get testData() {
       const body = 'body={"name": "pass-4"}';
       const CORS =
-        `Access-Control-Allow-Origin=${defaultURL.origin}`;
+        `Access-Control-Allow-Origin=${new URL(this.tabURL).origin}`;
       const link =
         `<link
         crossorigin=anonymous
         rel="manifest"
         href='${remoteURL}?${body}&${CORS}'>`;
       return link;
+    }
+  }, {
+    expected: 'Fetch blocked by CORS - origin does not match.',
+    get tabURL() {
+      let query = [
+        `body=<h1>${this.expected}</h1>`,
+        'Content-Type=text/html; charset=utf-8',
+      ];
+      const URL = `${defaultURL}?${query.join('&')}`;
+      return URL;
     },
-    run(manifest) {
-      is(manifest.name, 'pass-4', 'CORS enabled, manifest must be fetched.');
+    run(err) {
+      Assert.strictEqual(err.name, 'TypeError', this.expected);
     },
-  }, {
-    get body() {
+    get testData() {
       const body = 'body={"name": "fail"}';
       const CORS = 'Access-Control-Allow-Origin=http://not-here';
       const link =
         `<link
         crossorigin
         rel="manifest"
         href='${remoteURL}?${body}&${CORS}'>`;
       return link;
+    }
+  },{
+    expected: 'Trying to load from about:whatever is a TypeError.',
+    get tabURL() {
+      let query = [
+        `body=<h1>${this.expected}</h1>`,
+        'Content-Type=text/html; charset=utf-8',
+      ];
+      const URL = `${defaultURL}?${query.join('&')}`;
+      return URL;
     },
     run(err) {
-      is(err.name, 'TypeError', 'Fetch blocked by CORS - origin does not match.');
+      Assert.strictEqual(err.name, 'TypeError', this.expected);
     },
-  }, {
-    body: `<link rel="manifest" href='about:whatever'>`,
+    testData: `<link rel="manifest" href='about:whatever'>`
+  },
+  {
+    expected: 'Trying to load from file://whatever is a TypeError.',
+    get tabURL() {
+      let query = [
+        `body=<h1>${this.expected}</h1>`,
+        'Content-Type=text/html; charset=utf-8',
+      ];
+      const URL = `${defaultURL}?${query.join('&')}`;
+      return URL;
+    },
     run(err) {
-      is(err.name, 'TypeError', 'Trying to load from about:whatever is TypeError.');
+      Assert.strictEqual(err.name, 'TypeError', this.expected);
     },
-  }, {
-    body: `<link rel="manifest" href='file://manifest'>`,
-    run(err) {
-      is(err.name, 'TypeError', 'Trying to load from file://whatever is a TypeError.');
-    },
+    testData: `<link rel="manifest" href='file://manifest'>`
   },
   //URL parsing tests
   {
-    body: `<link rel="manifest" href='http://[12.1212.21.21.12.21.12]'>`,
+    expected: 'Trying to load invalid URL is a TypeError.',
+    get tabURL() {
+      let query = [
+        `body=<h1>${this.expected}</h1>`,
+        'Content-Type=text/html; charset=utf-8',
+      ];
+      const URL = `${defaultURL}?${query.join('&')}`;
+      return URL;
+    },
     run(err) {
-      is(err.name, 'TypeError', 'Trying to load invalid URL is a TypeError.');
+      Assert.strictEqual(err.name, 'TypeError', this.expected);
     },
+    testData: `<link rel="manifest" href='http://[12.1212.21.21.12.21.12]'>`
   },
 ];
 
-function makeTestURL({ body }) {
-  const url = new URL(defaultURL);
-  url.searchParams.set("body", encodeURIComponent(body));
-  return url.href;
-}
+add_task(function*() {
+  yield new Promise(resolve => {
+    SpecialPowers.pushPrefEnv({
+      'set': [
+        ['dom.fetch.enabled', true]
+      ]
+    }, resolve);
+  });
+  for (let test of tests) {
+    let tabOptions = {
+      gBrowser: gBrowser,
+      url: test.tabURL,
+    };
+    yield BrowserTestUtils.withNewTab(
+      tabOptions,
+      browser => testObtainingManifest(browser, test)
+    );
+  }
 
-add_task(function*() {
-  const promises = tests
-    .map(test => ({
-      gBrowser,
-      testRunner: testObtainingManifest(test),
-      url: makeTestURL(test)
-    }))
-    .reduce((collector, tabOpts) => {
-      const promise = BrowserTestUtils.withNewTab(tabOpts, tabOpts.testRunner);
-      collector.push(promise);
-      return collector;
-    }, []);
-
-  const results = yield Promise.all(promises);
-
-  function testObtainingManifest(aTest) {
-    return function*(aBrowser) {
-      try {
-        const manifest = yield ManifestObtainer.browserObtainManifest(aBrowser);
-        aTest.run(manifest);
-      } catch (e) {
-        aTest.run(e);
-      }
-    };
+  function* testObtainingManifest(aBrowser, aTest) {
+    aBrowser.contentWindowAsCPOW.document.head.innerHTML = aTest.testData;
+    try {
+      const manifest = yield ManifestObtainer.browserObtainManifest(aBrowser);
+      aTest.run(manifest);
+    } catch (e) {
+      aTest.run(e);
+    }
   }
 });
 
 /*
  * e10s race condition tests
  * Open a bunch of tabs and load manifests
  * in each tab. They should all return pass.
  */
 add_task(function*() {
-  const defaultPath = '/browser/dom/manifest/test/manifestLoader.html';
+  const defaultPath = '/tests/dom/manifest/test/manifestLoader.html';
   const tabURLs = [
-    `http://example.com:80${defaultPath}`,
-    `http://example.org:80${defaultPath}`,
-    `http://example.org:8000${defaultPath}`,
+    `http://test:80${defaultPath}`,
     `http://mochi.test:8888${defaultPath}`,
-    `http://sub1.test1.example.com:80${defaultPath}`,
-    `http://sub1.test1.example.org:80${defaultPath}`,
-    `http://sub1.test1.example.org:8000${defaultPath}`,
+    `http://test1.mochi.test:8888${defaultPath}`,
     `http://sub1.test1.mochi.test:8888${defaultPath}`,
-    `http://sub1.test2.example.com:80${defaultPath}`,
+    `http://sub2.xn--lt-uia.mochi.test:8888${defaultPath}`,
+    `http://test2.mochi.test:8888${defaultPath}`,
+    `http://example.org:80${defaultPath}`,
+    `http://test1.example.org:80${defaultPath}`,
+    `http://test2.example.org:80${defaultPath}`,
+    `http://sub1.test1.example.org:80${defaultPath}`,
     `http://sub1.test2.example.org:80${defaultPath}`,
-    `http://sub1.test2.example.org:8000${defaultPath}`,
-    `http://sub2.test1.example.com:80${defaultPath}`,
     `http://sub2.test1.example.org:80${defaultPath}`,
-    `http://sub2.test1.example.org:8000${defaultPath}`,
-    `http://sub2.test2.example.com:80${defaultPath}`,
     `http://sub2.test2.example.org:80${defaultPath}`,
-    `http://sub2.test2.example.org:8000${defaultPath}`,
-    `http://sub2.xn--lt-uia.mochi.test:8888${defaultPath}`,
-    `http://test1.example.com:80${defaultPath}`,
-    `http://test1.example.org:80${defaultPath}`,
+    `http://example.org:8000${defaultPath}`,
     `http://test1.example.org:8000${defaultPath}`,
-    `http://test1.mochi.test:8888${defaultPath}`,
+    `http://test2.example.org:8000${defaultPath}`,
+    `http://sub1.test1.example.org:8000${defaultPath}`,
+    `http://sub1.test2.example.org:8000${defaultPath}`,
+    `http://sub2.test1.example.org:8000${defaultPath}`,
+    `http://sub2.test2.example.org:8000${defaultPath}`,
+    `http://example.com:80${defaultPath}`,
+    `http://www.example.com:80${defaultPath}`,
+    `http://test1.example.com:80${defaultPath}`,
     `http://test2.example.com:80${defaultPath}`,
-    `http://test2.example.org:80${defaultPath}`,
-    `http://test2.example.org:8000${defaultPath}`,
-    `http://test2.mochi.test:8888${defaultPath}`,
-    `http://test:80${defaultPath}`,
-    `http://www.example.com:80${defaultPath}`,
+    `http://sub1.test1.example.com:80${defaultPath}`,
+    `http://sub1.test2.example.com:80${defaultPath}`,
+    `http://sub2.test1.example.com:80${defaultPath}`,
+    `http://sub2.test2.example.com:80${defaultPath}`,
   ];
   // Open tabs an collect corresponding browsers
   let browsers = [
     for (url of tabURLs) gBrowser.addTab(url).linkedBrowser
   ];
   // Once all the pages have loaded, run a bunch of tests in "parallel".
   yield Promise.all((
     for (browser of browsers) BrowserTestUtils.browserLoaded(browser)
   ));
   // Flood random browsers with requests. Once promises settle, check that
   // responses all pass.
   const results = yield Promise.all((
     for (browser of randBrowsers(browsers, 100)) ManifestObtainer.browserObtainManifest(browser)
   ));
+  const expected = 'Expect every manifest to have name equal to `pass`.';
   const pass = results.every(manifest => manifest.name === 'pass');
-  ok(pass, 'Expect every manifest to have name equal to `pass`.');
+  Assert.ok(pass, expected);
   //cleanup
   browsers
     .map(browser => gBrowser.getTabForBrowser(browser))
     .forEach(tab => gBrowser.removeTab(tab));
 
   //Helper generator, spits out random browsers
   function* randBrowsers(aBrowsers, aMax) {
     for (let i = 0; i < aMax; i++) {
--- a/dom/manifest/test/resource.sjs
+++ b/dom/manifest/test/resource.sjs
@@ -15,17 +15,16 @@
  * Outputs:
  * HTTP/1.1 200 OK
  * Content-Type: text/html
  * Hello: hi
  * <h1>hello</h1>
  */
 //global handleRequest
 'use strict';
-Components.utils.importGlobalProperties(["URLSearchParams"]);
 const HTTPStatus = new Map([
   [100, 'Continue'],
   [101, 'Switching Protocol'],
   [200, 'OK'],
   [201, 'Created'],
   [202, 'Accepted'],
   [203, 'Non-Authoritative Information'],
   [204, 'No Content'],
@@ -62,24 +61,33 @@ const HTTPStatus = new Map([
   [501, 'Not Implemented'],
   [502, 'Bad Gateway'],
   [503, 'Service Unavailable'],
   [504, 'Gateway Timeout'],
   [505, 'HTTP Version Not Supported']
 ]);
 
 function handleRequest(request, response) {
-  const queryMap = new URLSearchParams(request.queryString);
+  const queryMap = createQueryMap(request);
   if (queryMap.has('statusCode')) {
     let statusCode = parseInt(queryMap.get('statusCode'));
     let statusText = HTTPStatus.get(statusCode);
     queryMap.delete('statusCode');
     response.setStatusLine('1.1', statusCode, statusText);
   }
   if (queryMap.has('body')) {
     let body = queryMap.get('body') || '';
     queryMap.delete('body');
-    response.write(decodeURIComponent(body));
+    response.write(body);
   }
-  for (let [key, value] of queryMap.entries()) {
+  for (let [key, value] of queryMap) {
     response.setHeader(key, value);
   }
+
+  function createQueryMap(request) {
+    const queryMap = new Map();
+    request.queryString.split('&')
+      //split on first "="
+      .map((component) => component.split(/=(.+)?/))
+      .forEach(pair => queryMap.set(pair[0], decodeURIComponent(pair[1])));
+    return queryMap;
+  }
 }