From 6bf0a5cb5034a7e684dcc3500e841785237ce2dd Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Sun, 7 Apr 2024 19:32:43 +0200 Subject: Adding upstream version 1:115.7.0. Signed-off-by: Daniel Baumann --- dom/manifest/test/blue-150.png | Bin 0 -> 534 bytes dom/manifest/test/browser.ini | 18 ++ ...rowser_ManifestFinder_browserHasManifestLink.js | 89 +++++++ .../test/browser_ManifestIcons_browserFetchIcon.js | 66 +++++ .../test/browser_ManifestObtainer_credentials.js | 45 ++++ .../test/browser_ManifestObtainer_obtain.js | 268 +++++++++++++++++++++ dom/manifest/test/browser_Manifest_install.js | 58 +++++ dom/manifest/test/common.js | 139 +++++++++++ dom/manifest/test/cookie_checker.sjs | 22 ++ dom/manifest/test/cookie_setter.html | 8 + .../test/cookie_setter_with_credentials.html | 6 + ...ookie_setter_with_credentials_cross_origin.html | 14 ++ dom/manifest/test/file_testserver.sjs | 55 +++++ dom/manifest/test/icon.png | Bin 0 -> 8156 bytes dom/manifest/test/manifestLoader.html | 13 + dom/manifest/test/mochitest.ini | 24 ++ dom/manifest/test/red-50.png | Bin 0 -> 141 bytes dom/manifest/test/resource.sjs | 85 +++++++ .../test/test_ImageObjectProcessor_purpose.html | 120 +++++++++ .../test/test_ImageObjectProcessor_sizes.html | 88 +++++++ .../test/test_ImageObjectProcessor_src.html | 110 +++++++++ .../test/test_ImageObjectProcessor_type.html | 57 +++++ dom/manifest/test/test_ManifestProcessor_JSON.html | 48 ++++ .../test_ManifestProcessor_background_color.html | 22 ++ dom/manifest/test/test_ManifestProcessor_dir.html | 57 +++++ .../test/test_ManifestProcessor_display.html | 78 ++++++ .../test/test_ManifestProcessor_icons.html | 30 +++ dom/manifest/test/test_ManifestProcessor_id.html | 123 ++++++++++ dom/manifest/test/test_ManifestProcessor_lang.html | 139 +++++++++++ ...test_ManifestProcessor_name_and_short_name.html | 79 ++++++ .../test/test_ManifestProcessor_orientation.html | 86 +++++++ .../test/test_ManifestProcessor_scope.html | 113 +++++++++ .../test/test_ManifestProcessor_start_url.html | 83 +++++++ .../test/test_ManifestProcessor_theme_color.html | 22 ++ .../test/test_ManifestProcessor_warnings.html | 149 ++++++++++++ .../test/test_link_relList_supports_manifest.html | 47 ++++ 36 files changed, 2361 insertions(+) create mode 100644 dom/manifest/test/blue-150.png create mode 100644 dom/manifest/test/browser.ini create mode 100644 dom/manifest/test/browser_ManifestFinder_browserHasManifestLink.js create mode 100644 dom/manifest/test/browser_ManifestIcons_browserFetchIcon.js create mode 100644 dom/manifest/test/browser_ManifestObtainer_credentials.js create mode 100644 dom/manifest/test/browser_ManifestObtainer_obtain.js create mode 100644 dom/manifest/test/browser_Manifest_install.js create mode 100644 dom/manifest/test/common.js create mode 100644 dom/manifest/test/cookie_checker.sjs create mode 100644 dom/manifest/test/cookie_setter.html create mode 100644 dom/manifest/test/cookie_setter_with_credentials.html create mode 100644 dom/manifest/test/cookie_setter_with_credentials_cross_origin.html create mode 100644 dom/manifest/test/file_testserver.sjs create mode 100644 dom/manifest/test/icon.png create mode 100644 dom/manifest/test/manifestLoader.html create mode 100644 dom/manifest/test/mochitest.ini create mode 100644 dom/manifest/test/red-50.png create mode 100644 dom/manifest/test/resource.sjs create mode 100644 dom/manifest/test/test_ImageObjectProcessor_purpose.html create mode 100644 dom/manifest/test/test_ImageObjectProcessor_sizes.html create mode 100644 dom/manifest/test/test_ImageObjectProcessor_src.html create mode 100644 dom/manifest/test/test_ImageObjectProcessor_type.html create mode 100644 dom/manifest/test/test_ManifestProcessor_JSON.html create mode 100644 dom/manifest/test/test_ManifestProcessor_background_color.html create mode 100644 dom/manifest/test/test_ManifestProcessor_dir.html create mode 100644 dom/manifest/test/test_ManifestProcessor_display.html create mode 100644 dom/manifest/test/test_ManifestProcessor_icons.html create mode 100644 dom/manifest/test/test_ManifestProcessor_id.html create mode 100644 dom/manifest/test/test_ManifestProcessor_lang.html create mode 100644 dom/manifest/test/test_ManifestProcessor_name_and_short_name.html create mode 100644 dom/manifest/test/test_ManifestProcessor_orientation.html create mode 100644 dom/manifest/test/test_ManifestProcessor_scope.html create mode 100644 dom/manifest/test/test_ManifestProcessor_start_url.html create mode 100644 dom/manifest/test/test_ManifestProcessor_theme_color.html create mode 100644 dom/manifest/test/test_ManifestProcessor_warnings.html create mode 100644 dom/manifest/test/test_link_relList_supports_manifest.html (limited to 'dom/manifest/test') diff --git a/dom/manifest/test/blue-150.png b/dom/manifest/test/blue-150.png new file mode 100644 index 0000000000..f4a62faddf Binary files /dev/null and b/dom/manifest/test/blue-150.png differ diff --git a/dom/manifest/test/browser.ini b/dom/manifest/test/browser.ini new file mode 100644 index 0000000000..8ea569b261 --- /dev/null +++ b/dom/manifest/test/browser.ini @@ -0,0 +1,18 @@ +[DEFAULT] +support-files = + cookie_setter_with_credentials_cross_origin.html + cookie_setter_with_credentials.html + blue-150.png + cookie_checker.sjs + cookie_setter.html + file_testserver.sjs + manifestLoader.html + red-50.png + resource.sjs + +[browser_Manifest_install.js] +skip-if = verify +[browser_ManifestFinder_browserHasManifestLink.js] +[browser_ManifestIcons_browserFetchIcon.js] +[browser_ManifestObtainer_credentials.js] +[browser_ManifestObtainer_obtain.js] diff --git a/dom/manifest/test/browser_ManifestFinder_browserHasManifestLink.js b/dom/manifest/test/browser_ManifestFinder_browserHasManifestLink.js new file mode 100644 index 0000000000..360c98220b --- /dev/null +++ b/dom/manifest/test/browser_ManifestFinder_browserHasManifestLink.js @@ -0,0 +1,89 @@ +"use strict"; +const { ManifestFinder } = ChromeUtils.importESModule( + "resource://gre/modules/ManifestFinder.sys.mjs" +); +const defaultURL = new URL( + "http://example.org/browser/dom/manifest/test/resource.sjs" +); +defaultURL.searchParams.set("Content-Type", "text/html; charset=utf-8"); + +const tests = [ + { + body: ` + + + + `, + run(result) { + ok(result, "Document has a web manifest."); + }, + }, + { + body: ` + + + `, + run(result) { + ok(!result, "Document does not have a web manifest."); + }, + }, + { + body: ` + + `, + run(result) { + ok(!result, "Manifest link is has empty href."); + }, + }, + { + body: ` + + `, + run(result) { + ok(!result, "Manifest link is missing."); + }, + }, +]; + +function makeTestURL({ body }) { + const url = new URL(defaultURL); + url.searchParams.set("body", encodeURIComponent(body)); + return url.href; +} + +/** + * Test basic API error conditions + */ +add_task(async function () { + const expected = "Invalid types should throw a TypeError."; + for (let invalidValue of [undefined, null, 1, {}, "test"]) { + try { + await ManifestFinder.contentManifestLink(invalidValue); + ok(false, expected); + } catch (e) { + is(e.name, "TypeError", expected); + } + try { + await ManifestFinder.browserManifestLink(invalidValue); + ok(false, expected); + } catch (e) { + is(e.name, "TypeError", expected); + } + } +}); + +add_task(async function () { + const runningTests = tests + .map(test => ({ + gBrowser, + test, + url: makeTestURL(test), + })) + .map(tabOptions => + BrowserTestUtils.withNewTab(tabOptions, async function (browser) { + const result = await ManifestFinder.browserHasManifestLink(browser); + tabOptions.test.run(result); + }) + ); + await Promise.all(runningTests); +}); diff --git a/dom/manifest/test/browser_ManifestIcons_browserFetchIcon.js b/dom/manifest/test/browser_ManifestIcons_browserFetchIcon.js new file mode 100644 index 0000000000..e56e1e25c2 --- /dev/null +++ b/dom/manifest/test/browser_ManifestIcons_browserFetchIcon.js @@ -0,0 +1,66 @@ +"use strict"; + +Services.prefs.setBoolPref("dom.manifest.enabled", true); + +const { ManifestIcons } = ChromeUtils.importESModule( + "resource://gre/modules/ManifestIcons.sys.mjs" +); +const { ManifestObtainer } = ChromeUtils.importESModule( + "resource://gre/modules/ManifestObtainer.sys.mjs" +); + +const defaultURL = new URL( + "https://example.org/browser/dom/manifest/test/resource.sjs" +); +defaultURL.searchParams.set("Content-Type", "application/manifest+json"); + +const manifestMock = JSON.stringify({ + icons: [ + { + sizes: "50x50", + src: "red-50.png?Content-type=image/png", + }, + { + sizes: "150x150", + src: "blue-150.png?Content-type=image/png", + }, + ], +}); + +function makeTestURL() { + const url = new URL(defaultURL); + const body = ``; + url.searchParams.set("Content-Type", "text/html; charset=utf-8"); + url.searchParams.set("body", encodeURIComponent(body)); + return url.href; +} + +function getIconColor(icon) { + return new Promise((resolve, reject) => { + const canvas = content.document.createElement("canvas"); + const ctx = canvas.getContext("2d"); + const image = new content.Image(); + image.onload = function () { + ctx.drawImage(image, 0, 0); + resolve(ctx.getImageData(1, 1, 1, 1).data); + }; + image.onerror = function () { + reject(new Error("could not create image")); + }; + image.src = icon; + }); +} + +add_task(async function () { + const tabOptions = { gBrowser, url: makeTestURL() }; + await BrowserTestUtils.withNewTab(tabOptions, async function (browser) { + const manifest = await ManifestObtainer.browserObtainManifest(browser); + let icon = await ManifestIcons.browserFetchIcon(browser, manifest, 25); + let color = await SpecialPowers.spawn(browser, [icon], getIconColor); + is(color[0], 255, "Fetched red icon"); + + icon = await ManifestIcons.browserFetchIcon(browser, manifest, 500); + color = await SpecialPowers.spawn(browser, [icon], getIconColor); + is(color[2], 255, "Fetched blue icon"); + }); +}); diff --git a/dom/manifest/test/browser_ManifestObtainer_credentials.js b/dom/manifest/test/browser_ManifestObtainer_credentials.js new file mode 100644 index 0000000000..826ec24fc0 --- /dev/null +++ b/dom/manifest/test/browser_ManifestObtainer_credentials.js @@ -0,0 +1,45 @@ +"use strict"; + +Services.prefs.setBoolPref("dom.manifest.enabled", true); + +const { ManifestObtainer } = ChromeUtils.importESModule( + "resource://gre/modules/ManifestObtainer.sys.mjs" +); + +// Don't send cookies +add_task(async function () { + const testPath = "/browser/dom/manifest/test/cookie_setter.html"; + const tabURL = `https://example.com${testPath}`; + const browser = BrowserTestUtils.addTab(gBrowser, tabURL).linkedBrowser; + await BrowserTestUtils.browserLoaded(browser); + const { short_name } = await ManifestObtainer.browserObtainManifest(browser); + is(short_name, "no cookie"); + const tab = gBrowser.getTabForBrowser(browser); + gBrowser.removeTab(tab); +}); + +// Send cookies +add_task(async function () { + const testPath = + "/browser/dom/manifest/test/cookie_setter_with_credentials.html"; + const tabURL = `https://example.com${testPath}`; + const browser = BrowserTestUtils.addTab(gBrowser, tabURL).linkedBrowser; + await BrowserTestUtils.browserLoaded(browser); + const { short_name } = await ManifestObtainer.browserObtainManifest(browser); + is(short_name, "🍪"); + const tab = gBrowser.getTabForBrowser(browser); + gBrowser.removeTab(tab); +}); + +// Cross origin - we go from example.com to example.org +add_task(async function () { + const testPath = + "/browser/dom/manifest/test/cookie_setter_with_credentials_cross_origin.html"; + const tabURL = `https://example.com${testPath}`; + const browser = BrowserTestUtils.addTab(gBrowser, tabURL).linkedBrowser; + await BrowserTestUtils.browserLoaded(browser); + const { short_name } = await ManifestObtainer.browserObtainManifest(browser); + is(short_name, "no cookie"); + const tab = gBrowser.getTabForBrowser(browser); + gBrowser.removeTab(tab); +}); diff --git a/dom/manifest/test/browser_ManifestObtainer_obtain.js b/dom/manifest/test/browser_ManifestObtainer_obtain.js new file mode 100644 index 0000000000..a6d1dd6f23 --- /dev/null +++ b/dom/manifest/test/browser_ManifestObtainer_obtain.js @@ -0,0 +1,268 @@ +"use strict"; + +Services.prefs.setBoolPref("dom.manifest.enabled", true); +Services.prefs.setBoolPref("dom.security.https_first", false); + +const { ManifestObtainer } = ChromeUtils.importESModule( + "resource://gre/modules/ManifestObtainer.sys.mjs" +); +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"); +requestLongerTimeout(4); + +const tests = [ + // Fetch tests. + { + body: ``, + run(manifest) { + is(manifest, null, "Manifest without a href yields a null manifest."); + }, + }, + { + body: ``, + run(manifest) { + is(manifest, null, "Manifest without a href yields a null manifest."); + }, + }, + { + body: ` + + + `, + run(manifest) { + is( + manifest.name, + "pass-1", + "Manifest is first `link` where @rel contains token manifest." + ); + }, + }, + { + body: ` + + + `, + run(manifest) { + is( + manifest.name, + "pass-2", + "Manifest is first `link` where @rel contains token manifest." + ); + }, + }, + { + body: ``, + run(err) { + is( + err.name, + "TypeError", + "By default, manifest cannot load cross-origin." + ); + }, + }, + // CORS Tests. + { + get body() { + const body = 'body={"name": "pass-4"}'; + const CORS = `Access-Control-Allow-Origin=${defaultURL.origin}`; + const link = ``; + return link; + }, + run(manifest) { + is(manifest.name, "pass-4", "CORS enabled, manifest must be fetched."); + }, + }, + { + get body() { + const body = 'body={"name": "fail"}'; + const CORS = "Access-Control-Allow-Origin=http://not-here"; + const link = ``; + return link; + }, + run(err) { + is( + err.name, + "TypeError", + "Fetch blocked by CORS - origin does not match." + ); + }, + }, + { + body: ``, + run(err) { + is( + err.name, + "TypeError", + "Trying to load from about:whatever is TypeError." + ); + }, + }, + { + body: ``, + run(err) { + is( + err.name, + "TypeError", + "Trying to load from file://whatever is a TypeError." + ); + }, + }, + // URL parsing tests + { + body: ``, + run(err) { + is(err.name, "TypeError", "Trying to load invalid URL is a TypeError."); + }, + }, +]; + +function makeTestURL({ body }) { + const url = new URL(defaultURL); + url.searchParams.set("body", encodeURIComponent(body)); + return url.href; +} + +add_task(async 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; + }, []); + + await Promise.all(promises); + + function testObtainingManifest(aTest) { + return async function (aBrowser) { + try { + const manifest = await ManifestObtainer.browserObtainManifest(aBrowser); + aTest.run(manifest); + } catch (e) { + aTest.run(e); + } + }; + } +}); + +add_task(async () => { + // This loads a generic html page. + const url = new URL(defaultURL); + // The body get injected into the page on the server. + const body = ``; + url.searchParams.set("body", encodeURIComponent(body)); + + // Let's open a tab! + const tabOpts = { + gBrowser, + url: url.href, + }; + // Let's do the test + await BrowserTestUtils.withNewTab(tabOpts, async aBrowser => { + const obtainerOpts = { + checkConformance: true, // gives us back "moz_manifest_url" member + }; + const manifest = await ManifestObtainer.browserObtainManifest( + aBrowser, + obtainerOpts + ); + is(manifest.name, "conformance check"); + ok("moz_manifest_url" in manifest, "Has a moz_manifest_url member"); + const testString = defaultURL.origin + defaultURL.pathname; + ok( + manifest.moz_manifest_url.startsWith(testString), + `Expect to start with with the testString, but got ${manifest.moz_manifest_url} instead,` + ); + // Clean up! + gBrowser.removeTab(gBrowser.getTabForBrowser(aBrowser)); + }); +}); + +/* + * e10s race condition tests + * Open a bunch of tabs and load manifests + * in each tab. They should all return pass. + */ +add_task(async function () { + const defaultPath = "/browser/dom/manifest/test/manifestLoader.html"; + const tabURLs = [ + `http://example.com:80${defaultPath}`, + `http://example.org:80${defaultPath}`, + `http://example.org:8000${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://sub1.test1.mochi.test:8888${defaultPath}`, + `http://sub1.test2.example.com: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://test1.example.org:8000${defaultPath}`, + `http://test1.mochi.test:8888${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}`, + ]; + // Open tabs an collect corresponding browsers + let browsers = tabURLs.map( + url => BrowserTestUtils.addTab(gBrowser, url).linkedBrowser + ); + + // Once all the pages have loaded, run a bunch of tests in "parallel". + await Promise.all( + (function* () { + for (let browser of browsers) { + yield BrowserTestUtils.browserLoaded(browser); + } + })() + ); + // Flood random browsers with requests. Once promises settle, check that + // responses all pass. + const results = await Promise.all( + (function* () { + for (let browser of randBrowsers(browsers, 50)) { + yield ManifestObtainer.browserObtainManifest(browser); + } + })() + ); + const pass = results.every(manifest => manifest.name === "pass"); + ok(pass, "Expect every manifest to have name equal to `pass`."); + // 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++) { + const randNum = Math.round(Math.random() * (aBrowsers.length - 1)); + yield aBrowsers[randNum]; + } + } +}); diff --git a/dom/manifest/test/browser_Manifest_install.js b/dom/manifest/test/browser_Manifest_install.js new file mode 100644 index 0000000000..d3b949be19 --- /dev/null +++ b/dom/manifest/test/browser_Manifest_install.js @@ -0,0 +1,58 @@ +"use strict"; + +const { Manifests } = ChromeUtils.importESModule( + "resource://gre/modules/Manifest.sys.mjs" +); + +const defaultURL = new URL( + "http://example.org/browser/dom/manifest/test/resource.sjs" +); +defaultURL.searchParams.set("Content-Type", "application/manifest+json"); + +const manifestMock = JSON.stringify({ + short_name: "hello World", + scope: "/browser/", +}); +const manifestUrl = `${defaultURL}&body=${manifestMock}`; + +function makeTestURL() { + const url = new URL(defaultURL); + const body = ``; + url.searchParams.set("Content-Type", "text/html; charset=utf-8"); + url.searchParams.set("body", encodeURIComponent(body)); + return url.href; +} + +add_task(async function () { + const tabOptions = { gBrowser, url: makeTestURL() }; + + await BrowserTestUtils.withNewTab(tabOptions, async function (browser) { + let manifest = await Manifests.getManifest(browser, manifestUrl); + is(manifest.installed, false, "We haven't installed this manifest yet"); + + await manifest.install(browser); + is(manifest.name, "hello World", "Manifest has correct name"); + is(manifest.installed, true, "Manifest is installed"); + is(manifest.url, manifestUrl, "has correct url"); + is(manifest.browser, browser, "has correct browser"); + + manifest = await Manifests.getManifest(browser, manifestUrl); + is(manifest.installed, true, "New instances are installed"); + + manifest = await Manifests.getManifest(browser); + is(manifest.installed, true, "Will find manifest without being given url"); + + let foundManifest = Manifests.findManifestUrl( + "http://example.org/browser/dom/" + ); + is(foundManifest, manifestUrl, "Finds manifests within scope"); + + foundManifest = Manifests.findManifestUrl("http://example.org/"); + is(foundManifest, null, "Does not find manifests outside scope"); + }); + // Get the cached one now + await BrowserTestUtils.withNewTab(tabOptions, async browser => { + const manifest = await Manifests.getManifest(browser, manifestUrl); + is(manifest.browser, browser, "has updated browser object"); + }); +}); diff --git a/dom/manifest/test/common.js b/dom/manifest/test/common.js new file mode 100644 index 0000000000..50f27c119a --- /dev/null +++ b/dom/manifest/test/common.js @@ -0,0 +1,139 @@ +/** + * Common infrastructure for manifest tests. + **/ +"use strict"; +const { ManifestProcessor } = SpecialPowers.ChromeUtils.importESModule( + "resource://gre/modules/ManifestProcessor.sys.mjs" +); +const processor = ManifestProcessor; +const manifestURL = new URL(document.location.origin + "/manifest.json"); +const docURL = document.location; +const seperators = + "\u2028\u2029\u0020\u00A0\u1680\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200A\u202F\u205F\u3000"; +const lineTerminators = "\u000D\u000A\u2028\u2029"; +const whiteSpace = `${seperators}${lineTerminators}`; +const typeTests = [1, null, {}, [], false]; +const data = { + jsonText: "{}", + manifestURL, + docURL, +}; + +const validThemeColors = [ + ["maroon", "#800000ff"], + ["#f00", "#ff0000ff"], + ["#ff0000", "#ff0000ff"], + ["rgb(255,0,0)", "#ff0000ff"], + ["rgb(255,0,0,1)", "#ff0000ff"], + ["rgb(255,0,0,1.0)", "#ff0000ff"], + ["rgb(255,0,0,100%)", "#ff0000ff"], + ["rgb(255 0 0)", "#ff0000ff"], + ["rgb(255 0 0 / 1)", "#ff0000ff"], + ["rgb(255 0 0 / 1.0)", "#ff0000ff"], + ["rgb(255 0 0 / 100%)", "#ff0000ff"], + ["rgb(100%, 0%, 0%)", "#ff0000ff"], + ["rgb(100%, 0%, 0%, 1)", "#ff0000ff"], + ["rgb(100%, 0%, 0%, 1.0)", "#ff0000ff"], + ["rgb(100%, 0%, 0%, 100%)", "#ff0000ff"], + ["rgb(100% 0% 0%)", "#ff0000ff"], + ["rgb(100% 0% 0% / 1)", "#ff0000ff"], + ["rgb(100%, 0%, 0%, 1.0)", "#ff0000ff"], + ["rgb(100%, 0%, 0%, 100%)", "#ff0000ff"], + ["rgb(300,0,0)", "#ff0000ff"], + ["rgb(300 0 0)", "#ff0000ff"], + ["rgb(255,-10,0)", "#ff0000ff"], + ["rgb(110%, 0%, 0%)", "#ff0000ff"], + ["rgba(255,0,0)", "#ff0000ff"], + ["rgba(255,0,0,1)", "#ff0000ff"], + ["rgba(255 0 0 / 1)", "#ff0000ff"], + ["rgba(100%,0%,0%,1)", "#ff0000ff"], + ["rgba(0,0,255,0.5)", "#0000ff80"], + ["rgba(100%, 50%, 0%, 0.1)", "#ff80001a"], + ["hsl(120, 100%, 50%)", "#00ff00ff"], + ["hsl(120 100% 50%)", "#00ff00ff"], + ["hsl(120, 100%, 50%, 1.0)", "#00ff00ff"], + ["hsl(120 100% 50% / 1.0)", "#00ff00ff"], + ["hsla(120, 100%, 50%)", "#00ff00ff"], + ["hsla(120 100% 50%)", "#00ff00ff"], + ["hsla(120, 100%, 50%, 1.0)", "#00ff00ff"], + ["hsla(120 100% 50% / 1.0)", "#00ff00ff"], + ["hsl(120deg, 100%, 50%)", "#00ff00ff"], + ["hsl(133.33333333grad, 100%, 50%)", "#00ff00ff"], + ["hsl(2.0943951024rad, 100%, 50%)", "#00ff00ff"], + ["hsl(0.3333333333turn, 100%, 50%)", "#00ff00ff"], +]; + +function setupManifest(key, value) { + const manifest = {}; + manifest[key] = value; + data.jsonText = JSON.stringify(manifest); +} + +function testValidColors(key) { + validThemeColors.forEach(item => { + const [manifest_color, parsed_color] = item; + setupManifest(key, manifest_color); + const result = processor.process(data); + + is( + result[key], + parsed_color, + `Expect ${key} to be returned for ${manifest_color}` + ); + }); + + // Trim tests + validThemeColors.forEach(item => { + const [manifest_color, parsed_color] = item; + const expandedThemeColor = `${seperators}${lineTerminators}${manifest_color}${lineTerminators}${seperators}`; + setupManifest(key, expandedThemeColor); + const result = processor.process(data); + + is( + result[key], + parsed_color, + `Expect trimmed ${key} to be returned for ${manifest_color}` + ); + }); +} + +const invalidThemeColors = [ + "marooon", + "f000000", + "#ff00000", + "rgb(100, 0%, 0%)", + "rgb(255,0)", + "rbg(255,-10,0)", + "rgb(110, 0%, 0%)", + "(255,0,0) }", + "rgba(255)", + " rgb(100%,0%,0%) }", + "hsl(120, 100%, 50)", + "hsl(120, 100%, 50.0)", + "hsl 120, 100%, 50%", + "hsla{120, 100%, 50%, 1}", +]; + +function testInvalidColors(key) { + typeTests.forEach(type => { + setupManifest(key, type); + const result = processor.process(data); + + is( + result[key], + undefined, + `Expect non-string ${key} to be undefined: ${typeof type}.` + ); + }); + + invalidThemeColors.forEach(manifest_color => { + setupManifest(key, manifest_color); + const result = processor.process(data); + + is( + result[key], + undefined, + `Expect ${key} to be undefined: ${manifest_color}.` + ); + }); +} diff --git a/dom/manifest/test/cookie_checker.sjs b/dom/manifest/test/cookie_checker.sjs new file mode 100644 index 0000000000..fa5df00d44 --- /dev/null +++ b/dom/manifest/test/cookie_checker.sjs @@ -0,0 +1,22 @@ +"use strict"; +let { NetUtil } = ChromeUtils.import("resource://gre/modules/NetUtil.jsm"); + +function handleRequest(request, response) { + response.setStatusLine(request.httpVersion, 200); + // avoid confusing cache behaviors + response.setHeader("Cache-Control", "no-cache", false); + response.setHeader("Content-Type", "application/json", false); + + // CORS stuff + const origin = request.hasHeader("Origin") + ? request.getHeader("Origin") + : null; + if (origin) { + response.setHeader("Access-Control-Allow-Origin", origin); + response.setHeader("Access-Control-Allow-Credentials", "true"); + } + const short_name = request.hasHeader("Cookie") + ? request.getHeader("Cookie") + : "no cookie"; + response.write(JSON.stringify({ short_name })); +} diff --git a/dom/manifest/test/cookie_setter.html b/dom/manifest/test/cookie_setter.html new file mode 100644 index 0000000000..d8f412fbcb --- /dev/null +++ b/dom/manifest/test/cookie_setter.html @@ -0,0 +1,8 @@ + + + + diff --git a/dom/manifest/test/cookie_setter_with_credentials.html b/dom/manifest/test/cookie_setter_with_credentials.html new file mode 100644 index 0000000000..0d721b55ef --- /dev/null +++ b/dom/manifest/test/cookie_setter_with_credentials.html @@ -0,0 +1,6 @@ + + + + diff --git a/dom/manifest/test/cookie_setter_with_credentials_cross_origin.html b/dom/manifest/test/cookie_setter_with_credentials_cross_origin.html new file mode 100644 index 0000000000..6d1c4045c3 --- /dev/null +++ b/dom/manifest/test/cookie_setter_with_credentials_cross_origin.html @@ -0,0 +1,14 @@ + + +

Cross origin cookie sender

+ + + diff --git a/dom/manifest/test/file_testserver.sjs b/dom/manifest/test/file_testserver.sjs new file mode 100644 index 0000000000..bcceb15504 --- /dev/null +++ b/dom/manifest/test/file_testserver.sjs @@ -0,0 +1,55 @@ +"use strict"; +let { NetUtil } = ChromeUtils.import("resource://gre/modules/NetUtil.jsm"); +Cu.importGlobalProperties(["URLSearchParams"]); + +function loadHTMLFromFile(path) { + // Load the HTML to return in the response from file. + // Since it's relative to the cwd of the test runner, we start there and + // append to get to the actual path of the file. + const testHTMLFile = Services.dirsvc.get("CurWorkD", Ci.nsIFile); + + const testHTMLFileStream = Cc[ + "@mozilla.org/network/file-input-stream;1" + ].createInstance(Ci.nsIFileInputStream); + + path + .split("/") + .filter(path_1 => path_1) + .reduce((file, path_2) => { + testHTMLFile.append(path_2); + return testHTMLFile; + }, testHTMLFile); + testHTMLFileStream.init(testHTMLFile, -1, 0, 0); + const isAvailable = testHTMLFileStream.available(); + return NetUtil.readInputStreamToString(testHTMLFileStream, isAvailable); +} + +function handleRequest(request, response) { + const query = new URLSearchParams(request.queryString); + + // avoid confusing cache behaviors + response.setHeader("Cache-Control", "no-cache", false); + + // Deliver the CSP policy encoded in the URL + if (query.has("csp")) { + response.setHeader("Content-Security-Policy", query.get("csp"), false); + } + + // Deliver the CSPRO policy encoded in the URL + if (query.has("cspro")) { + response.setHeader( + "Content-Security-Policy-Report-Only", + query.get("cspro"), + false + ); + } + + // Deliver the CORS header in the URL + if (query.has("cors")) { + response.setHeader("Access-Control-Allow-Origin", query.get("cors"), false); + } + + // Send HTML to test allowed/blocked behaviors + response.setHeader("Content-Type", "text/html", false); + response.write(loadHTMLFromFile(query.get("file"))); +} diff --git a/dom/manifest/test/icon.png b/dom/manifest/test/icon.png new file mode 100644 index 0000000000..bb87f783b7 Binary files /dev/null and b/dom/manifest/test/icon.png differ diff --git a/dom/manifest/test/manifestLoader.html b/dom/manifest/test/manifestLoader.html new file mode 100644 index 0000000000..e244260902 --- /dev/null +++ b/dom/manifest/test/manifestLoader.html @@ -0,0 +1,13 @@ + + + + +

Manifest loader

+

Uses resource.sjs to load a Web Manifest that can be loaded cross-origin. The manifest looks like this:

+
+{
+	"name":"pass"
+}
+
diff --git a/dom/manifest/test/mochitest.ini b/dom/manifest/test/mochitest.ini new file mode 100644 index 0000000000..73d7a65787 --- /dev/null +++ b/dom/manifest/test/mochitest.ini @@ -0,0 +1,24 @@ +[DEFAULT] +support-files = + common.js + resource.sjs + manifestLoader.html + file_testserver.sjs +[test_ImageObjectProcessor_purpose.html] +[test_ImageObjectProcessor_sizes.html] +[test_ImageObjectProcessor_src.html] +[test_ImageObjectProcessor_type.html] +[test_link_relList_supports_manifest.html] +[test_ManifestProcessor_background_color.html] +[test_ManifestProcessor_dir.html] +[test_ManifestProcessor_display.html] +[test_ManifestProcessor_icons.html] +[test_ManifestProcessor_id.html] +[test_ManifestProcessor_JSON.html] +[test_ManifestProcessor_lang.html] +[test_ManifestProcessor_name_and_short_name.html] +[test_ManifestProcessor_orientation.html] +[test_ManifestProcessor_scope.html] +[test_ManifestProcessor_start_url.html] +[test_ManifestProcessor_theme_color.html] +[test_ManifestProcessor_warnings.html] diff --git a/dom/manifest/test/red-50.png b/dom/manifest/test/red-50.png new file mode 100644 index 0000000000..e2ce365c3c Binary files /dev/null and b/dom/manifest/test/red-50.png differ diff --git a/dom/manifest/test/resource.sjs b/dom/manifest/test/resource.sjs new file mode 100644 index 0000000000..56deaa61d7 --- /dev/null +++ b/dom/manifest/test/resource.sjs @@ -0,0 +1,85 @@ +/* Generic responder that composes a response from + * the query string of a request. + * + * It reserves some special prop names: + * - body: get's used as the response body + * - statusCode: override the 200 OK response code + * (response text is set automatically) + * + * Any property names it doesn't know about get converted into + * HTTP headers. + * + * For example: + * http://test/resource.sjs?Content-Type=text/html&body=

hello

&Hello=hi + * + * Outputs: + * HTTP/1.1 200 OK + * Content-Type: text/html + * Hello: hi + *

hello

+ */ +//global handleRequest +"use strict"; +Cu.importGlobalProperties(["URLSearchParams"]); +const HTTPStatus = new Map([ + [100, "Continue"], + [101, "Switching Protocol"], + [200, "OK"], + [201, "Created"], + [202, "Accepted"], + [203, "Non-Authoritative Information"], + [204, "No Content"], + [205, "Reset Content"], + [206, "Partial Content"], + [300, "Multiple Choice"], + [301, "Moved Permanently"], + [302, "Found"], + [303, "See Other"], + [304, "Not Modified"], + [305, "Use Proxy"], + [306, "unused"], + [307, "Temporary Redirect"], + [308, "Permanent Redirect"], + [400, "Bad Request"], + [401, "Unauthorized"], + [402, "Payment Required"], + [403, "Forbidden"], + [404, "Not Found"], + [405, "Method Not Allowed"], + [406, "Not Acceptable"], + [407, "Proxy Authentication Required"], + [408, "Request Timeout"], + [409, "Conflict"], + [410, "Gone"], + [411, "Length Required"], + [412, "Precondition Failed"], + [413, "Request Entity Too Large"], + [414, "Request-URI Too Long"], + [415, "Unsupported Media Type"], + [416, "Requested Range Not Satisfiable"], + [417, "Expectation Failed"], + [500, "Internal Server Error"], + [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); + 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)); + } + for (let [key, value] of queryMap.entries()) { + response.setHeader(key, value); + } +} diff --git a/dom/manifest/test/test_ImageObjectProcessor_purpose.html b/dom/manifest/test/test_ImageObjectProcessor_purpose.html new file mode 100644 index 0000000000..386c4566d4 --- /dev/null +++ b/dom/manifest/test/test_ImageObjectProcessor_purpose.html @@ -0,0 +1,120 @@ + + + + + + Test for Bug + + + + + diff --git a/dom/manifest/test/test_ImageObjectProcessor_sizes.html b/dom/manifest/test/test_ImageObjectProcessor_sizes.html new file mode 100644 index 0000000000..9418b44118 --- /dev/null +++ b/dom/manifest/test/test_ImageObjectProcessor_sizes.html @@ -0,0 +1,88 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ImageObjectProcessor_src.html b/dom/manifest/test/test_ImageObjectProcessor_src.html new file mode 100644 index 0000000000..8d17c3048f --- /dev/null +++ b/dom/manifest/test/test_ImageObjectProcessor_src.html @@ -0,0 +1,110 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ImageObjectProcessor_type.html b/dom/manifest/test/test_ImageObjectProcessor_type.html new file mode 100644 index 0000000000..29627c5e46 --- /dev/null +++ b/dom/manifest/test/test_ImageObjectProcessor_type.html @@ -0,0 +1,57 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_JSON.html b/dom/manifest/test/test_ManifestProcessor_JSON.html new file mode 100644 index 0000000000..b072355f20 --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_JSON.html @@ -0,0 +1,48 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_background_color.html b/dom/manifest/test/test_ManifestProcessor_background_color.html new file mode 100644 index 0000000000..38073b8e4f --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_background_color.html @@ -0,0 +1,22 @@ + + + + + + Test for Bug 1195018 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_dir.html b/dom/manifest/test/test_ManifestProcessor_dir.html new file mode 100644 index 0000000000..b5dc84a9e4 --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_dir.html @@ -0,0 +1,57 @@ + + + + + + Test for Bug 1258899 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_display.html b/dom/manifest/test/test_ManifestProcessor_display.html new file mode 100644 index 0000000000..f5ea5fbc4f --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_display.html @@ -0,0 +1,78 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_icons.html b/dom/manifest/test/test_ManifestProcessor_icons.html new file mode 100644 index 0000000000..578f49f5dc --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_icons.html @@ -0,0 +1,30 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_id.html b/dom/manifest/test/test_ManifestProcessor_id.html new file mode 100644 index 0000000000..336d1d3a77 --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_id.html @@ -0,0 +1,123 @@ + + + + + + Test for Bug 1731940 - implement id member + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_lang.html b/dom/manifest/test/test_ManifestProcessor_lang.html new file mode 100644 index 0000000000..568950c2ba --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_lang.html @@ -0,0 +1,139 @@ + + + + +Test for Bug 1143879 - Implement lang member of Web manifest + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_name_and_short_name.html b/dom/manifest/test/test_ManifestProcessor_name_and_short_name.html new file mode 100644 index 0000000000..e843b583e4 --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_name_and_short_name.html @@ -0,0 +1,79 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_orientation.html b/dom/manifest/test/test_ManifestProcessor_orientation.html new file mode 100644 index 0000000000..9333eecbe3 --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_orientation.html @@ -0,0 +1,86 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_scope.html b/dom/manifest/test/test_ManifestProcessor_scope.html new file mode 100644 index 0000000000..590d76a251 --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_scope.html @@ -0,0 +1,113 @@ + + + + + + Test for Bug 1079453 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_start_url.html b/dom/manifest/test/test_ManifestProcessor_start_url.html new file mode 100644 index 0000000000..1d172df555 --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_start_url.html @@ -0,0 +1,83 @@ + + + + + + Test for Bug 1079453 + + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_theme_color.html b/dom/manifest/test/test_ManifestProcessor_theme_color.html new file mode 100644 index 0000000000..c73832748d --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_theme_color.html @@ -0,0 +1,22 @@ + + + + + + Test for Bug 1195018 + + + + + diff --git a/dom/manifest/test/test_ManifestProcessor_warnings.html b/dom/manifest/test/test_ManifestProcessor_warnings.html new file mode 100644 index 0000000000..f2092c1dcf --- /dev/null +++ b/dom/manifest/test/test_ManifestProcessor_warnings.html @@ -0,0 +1,149 @@ + + + + + + Test for Bug 1086997 + + + + + diff --git a/dom/manifest/test/test_link_relList_supports_manifest.html b/dom/manifest/test/test_link_relList_supports_manifest.html new file mode 100644 index 0000000000..af678ddb5f --- /dev/null +++ b/dom/manifest/test/test_link_relList_supports_manifest.html @@ -0,0 +1,47 @@ + + + + + + + Test for Bug 1596040 - Link relList support returns false for manifest + + + + -- cgit v1.2.3