author | Mike Pennisi <mike@mikepennisi.com> |
Wed, 06 Jun 2018 14:51:11 +0000 | |
changeset 422151 | 85d401e121224b10987c798b0e4fb07549c5de24 |
parent 422150 | 59dab3cb67fadfa80a3fe08eb5313ba0f9fb38e0 |
child 422152 | f41374897ca8a132f34a1a3d0ea16d04461f2f47 |
push id | 34122 |
push user | ebalazs@mozilla.com |
push date | Mon, 11 Jun 2018 09:37:00 +0000 |
treeherder | mozilla-central@9941eb8c3b29 [default view] [failures only] |
perfherder | [talos] [build metrics] [platform microbench] (compared to previous push) |
reviewers | testonly |
bugs | 1464320, 11011 |
milestone | 62.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
|
--- a/testing/web-platform/meta/MANIFEST.json +++ b/testing/web-platform/meta/MANIFEST.json @@ -301516,17 +301516,17 @@ {} ] ], "webrtc/dictionary-helper.js": [ [ {} ] ], - "webrtc/identity-helper.js": [ + "webrtc/identity-helper.sub.js": [ [ {} ] ], "webrtc/protocol/README.txt": [ [ {} ] @@ -316150,31 +316150,31 @@ ] ], "content-security-policy/navigation/to-javascript-url-script-src.html": [ [ "/content-security-policy/navigation/to-javascript-url-script-src.html", {} ] ], - "content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.html": [ - [ - "/content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.html", + "content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.sub.html": [ + [ + "/content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.sub.html", {} ] ], "content-security-policy/nonce-hiding/script-nonces-hidden.tentative.html": [ [ "/content-security-policy/nonce-hiding/script-nonces-hidden.tentative.html", {} ] ], - "content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.html": [ - [ - "/content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.html", + "content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.sub.html": [ + [ + "/content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.sub.html", {} ] ], "content-security-policy/nonce-hiding/svgscript-nonces-hidden.tentative.html": [ [ "/content-security-policy/nonce-hiding/svgscript-nonces-hidden.tentative.html", {} ] @@ -341162,19 +341162,19 @@ ] ], "html/semantics/embedded-content/the-iframe-element/content_document_changes_only_after_load_matures.html": [ [ "/html/semantics/embedded-content/the-iframe-element/content_document_changes_only_after_load_matures.html", {} ] ], - "html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.html": [ - [ - "/html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.html", + "html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.sub.html": [ + [ + "/html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.sub.html", {} ] ], "html/semantics/embedded-content/the-iframe-element/document-getters-return-null-for-cross-origin.html": [ [ "/html/semantics/embedded-content/the-iframe-element/document-getters-return-null-for-cross-origin.html", {} ] @@ -342612,19 +342612,19 @@ ] ], "html/semantics/forms/the-input-element/week.html": [ [ "/html/semantics/forms/the-input-element/week.html", {} ] ], - "html/semantics/forms/the-label-element/label-attributes.html": [ - [ - "/html/semantics/forms/the-label-element/label-attributes.html", + "html/semantics/forms/the-label-element/label-attributes.sub.html": [ + [ + "/html/semantics/forms/the-label-element/label-attributes.sub.html", {} ] ], "html/semantics/forms/the-label-element/labelable-elements.html": [ [ "/html/semantics/forms/the-label-element/labelable-elements.html", {} ] @@ -376426,19 +376426,19 @@ ] ], "webrtc/RTCPeerConnection-getDefaultIceServers.html": [ [ "/webrtc/RTCPeerConnection-getDefaultIceServers.html", {} ] ], - "webrtc/RTCPeerConnection-getIdentityAssertion.html": [ - [ - "/webrtc/RTCPeerConnection-getIdentityAssertion.html", + "webrtc/RTCPeerConnection-getIdentityAssertion.sub.html": [ + [ + "/webrtc/RTCPeerConnection-getIdentityAssertion.sub.html", {} ] ], "webrtc/RTCPeerConnection-getStats.https.html": [ [ "/webrtc/RTCPeerConnection-getStats.https.html", {} ] @@ -402264,17 +402264,17 @@ "8ab843e17aa153bcf91282be3770ed2009061b11", "support" ], "./check_stability.ini": [ "5addd67f09e895336644c5a9f5049c03e1ffe615", "support" ], "./lint.whitelist": [ - "f18a6bb277d2392446c790aa85eb008d5f3fe05d", + "0992e710e33823c6fb6be2725ec1e7f3c7eaa330", "support" ], "./serve.py": [ "0efa39b1f26f86d73f2fce4f9e46003d62057b41", "support" ], "./server-side.md": [ "c51b17fbac2a2e3121dc74f7badbd2873ce92f61", @@ -412960,17 +412960,17 @@ "352a8a947bfa42fd59a93181f8aedb64ee6e37ae", "support" ], "clear-site-data/support/service_worker.js": [ "eb87eb25d4b84ae78c57a7bd3cd3d43b4df99881", "support" ], "clear-site-data/support/test_utils.sub.js": [ - "10f5f9d409ef513edb129e0e8522aa5f74d51ce8", + "8b95088e042059506f15b013e2a22c62d46cb227", "support" ], "client-hints/OWNERS": [ "e096c94435cc7364a4959597cf51a86b3fee81a6", "support" ], "client-hints/accept_ch.http.html": [ "ec820e569029ef412f776d35c4bc79a2a7ecf107", @@ -430936,17 +430936,17 @@ "3b77edcd9a327a7cb7120ee0fb4975f936430211", "testharness" ], "content-security-policy/base-uri/base-uri_iframe_sandbox.sub.html": [ "19d2027dc8784a479722b7f405fee31973808e2f", "testharness" ], "content-security-policy/base-uri/report-uri-does-not-respect-base-uri.sub.html": [ - "a8c074a65a874df3f2a0f7f994c2094f4c8647b9", + "1f649852eaa9ce8471559411021f89e1bc7030f7", "testharness" ], "content-security-policy/base-uri/report-uri-does-not-respect-base-uri.sub.html.sub.headers": [ "6adacb07a9ade6e135b5c24ef658384d26ed2dff", "support" ], "content-security-policy/blob/blob-urls-do-not-match-self.sub.html": [ "8fb0231ccaff9062464119096a4ae89c04216b42", @@ -431492,21 +431492,21 @@ "8f275f169e1257400cea6e7dff26b0d457f3f82f", "testharness" ], "content-security-policy/generic/generic-0_2_3.html": [ "c202f424814bb3c4f662c8fbec49031ed3ed405f", "testharness" ], "content-security-policy/generic/generic-0_8.sub.html": [ - "6e9aeddf1a5e308036ca1a659d138cc45fd7ea00", + "0ca657574473e38790559a120eec745a6567e698", "testharness" ], "content-security-policy/generic/generic-0_8_1.sub.html": [ - "e5913fc5feb3e2352172c96e366389e4216c55f3", + "1ff936bf7b9520f374971bf25d9e778a2bf304b8", "testharness" ], "content-security-policy/generic/generic-0_9.sub.html": [ "5b0adf26a3922c5a596333ea26a4102066e8ff8a", "testharness" ], "content-security-policy/generic/negativeTests.js": [ "1d2009b245fa9483ad9058e0a587d5873e3578f3", @@ -431943,30 +431943,30 @@ "content-security-policy/navigation/to-javascript-url-frame-src.html": [ "3070ea56bcb7dc454d7bc252377f0dc5bcb03c7c", "testharness" ], "content-security-policy/navigation/to-javascript-url-script-src.html": [ "26e0c14927bab1b2fd6ce44b59472f336a700aa4", "testharness" ], - "content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.html": [ - "a1de5c33148f7e202d13bc5c25d115a29ac81b3b", + "content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.sub.html": [ + "20e284dc7fb3c7dbdca501d144b03604ffbf8a19", "testharness" ], "content-security-policy/nonce-hiding/script-nonces-hidden.tentative.html": [ "44982a605aaef57edfd9bbd9af98b1eee8d9ba1d", "testharness" ], "content-security-policy/nonce-hiding/script-nonces-hidden.tentative.html.headers": [ "28c376fd32a880f58de3f67fd3b19288c38d63f3", "support" ], - "content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.html": [ - "9ea075f30ba75a712f1fd7c05d413caaca0af67a", + "content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.sub.html": [ + "eac2a1a48fcb8363c857ae91ec96df6fa9cac56d", "testharness" ], "content-security-policy/nonce-hiding/svgscript-nonces-hidden.tentative.html": [ "7345b65ebfdecad898ce1d3acd6ee5353163a38d", "testharness" ], "content-security-policy/nonce-hiding/svgscript-nonces-hidden.tentative.html.headers": [ "28c376fd32a880f58de3f67fd3b19288c38d63f3", @@ -564660,17 +564660,17 @@ "e6c2afd6cef41d358016d4d021b7c3e0e1185704", "testharness" ], "fetch/api/request/request-reset-attributes.https.html": [ "132b917c77c61230f7c5e84c3c9cafe4d1f0b565", "testharness" ], "fetch/api/request/request-structure.html": [ - "2af02f3ecf8449c91f2f1d28effc3478a4bfc235", + "450f8c91149638fe77bab2b65f345e6e24646c95", "testharness" ], "fetch/api/request/request-type-attribute-historical.html": [ "68620f3ea16b7ae1a9f1efde1cd0bb47f1150b9f", "testharness" ], "fetch/api/request/resources/cache.py": [ "fa831de695ef775b03a2b89a6cb691636b26027f", @@ -568512,17 +568512,17 @@ "844b162882b27fd3ec0a07c8d4c1a6a6254b69ca", "testharness" ], "html/browsers/origin/relaxing-the-same-origin-restriction/document_domain.html": [ "9839a9c24ce78ec42da8a60d2175df06e19983c1", "testharness" ], "html/browsers/origin/relaxing-the-same-origin-restriction/document_domain_setter.html": [ - "74417f69455c12f894207e23496c0f92edff7eae", + "13210ebcc5093d24f7072e1dc43769ad6cb71048", "testharness" ], "html/browsers/origin/relaxing-the-same-origin-restriction/document_domain_setter_null.tentative.html": [ "212e7be483bcb35413156231afcda8fe074558fc", "testharness" ], "html/browsers/origin/relaxing-the-same-origin-restriction/document_domain_setter_srcdoc.html": [ "f707d1f40216d35afd04f4cd68cce66feaadddfd", @@ -579571,18 +579571,18 @@ "html/semantics/embedded-content/the-iframe-element/cross_origin_child.html": [ "a42082bb612b280eda5aa598ed750cfce3edd537", "support" ], "html/semantics/embedded-content/the-iframe-element/cross_origin_grandchild.html": [ "5654d0f8b2a68e96f4d13d480f768f8fadea39e2", "support" ], - "html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.html": [ - "30f590a975529a8975bea659be46192c755f2bac", + "html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.sub.html": [ + "74ab28fb69338b2b17eed45d95c8fd06e1ef3290", "testharness" ], "html/semantics/embedded-content/the-iframe-element/document-getters-return-null-for-cross-origin.html": [ "87392a410d9ce76febe6ea3f5b2e15568e457b1a", "testharness" ], "html/semantics/embedded-content/the-iframe-element/historical.html": [ "cf6e961b764d5c6e7e1289f3db988fe94efaf030", @@ -581119,18 +581119,18 @@ "html/semantics/forms/the-label-element/.gitkeep": [ "da39a3ee5e6b4b0d3255bfef95601890afd80709", "support" ], "html/semantics/forms/the-label-element/iframe-label-attributes.html": [ "3629d93c34f27a575114b15256803941c9893f6e", "support" ], - "html/semantics/forms/the-label-element/label-attributes.html": [ - "2482d37cd516b5f79e7bbf39c157e7c20e2f2100", + "html/semantics/forms/the-label-element/label-attributes.sub.html": [ + "084ab750c7706f2d01b934cddcfb8f296f06bf9c", "testharness" ], "html/semantics/forms/the-label-element/labelable-elements.html": [ "80275984254360d8b713b5b330c18ae34138b670", "testharness" ], "html/semantics/forms/the-label-element/proxy-click-to-associated-element.html": [ "49f17bfea3e8080fd8690b7be4bc3aa0c82e63e2", @@ -589640,17 +589640,17 @@ "935c963cbec9f000ea0564a0e0c4ce872da40ea8", "testharness" ], "navigation-timing/nav2_test_attributes_exist.html": [ "6ed5a8f92b282d956d7d946cf031296ed7bfef50", "testharness" ], "navigation-timing/nav2_test_attributes_values.html": [ - "e5f14ce9a725cbb3a88a73b5f137625334f1e3de", + "8feb632d11913f36a9f9c0df9c2e871b84134a30", "testharness" ], "navigation-timing/nav2_test_document_open.html": [ "22ff29845d8417ccbae58123efe8e1c9b9c81eaf", "testharness" ], "navigation-timing/nav2_test_document_replaced.html": [ "b36ccb9a595ea5ab318f53dbff75b3c8f7c5b044", @@ -589660,17 +589660,17 @@ "8ed53df25ff06d2affa9c438e3bb85d6dc9f34a1", "testharness" ], "navigation-timing/nav2_test_instance_accessible_from_the_start.html": [ "79bd2cff7e144ef3d1b093c542ad69302a0138b3", "testharness" ], "navigation-timing/nav2_test_instance_accessors.html": [ - "c4960ce93c9379763845fb2cae9249d4e4c18376", + "174ed39ea3b79363142e49b781b70d506829f9ca", "testharness" ], "navigation-timing/nav2_test_navigate_within_document.html": [ "81d5d810a10e1aa235cdab6edd830000d407629a", "testharness" ], "navigation-timing/nav2_test_navigation_type_backforward.html": [ "da9905abdfc580e1b41809db5beaff40866a1f02", @@ -618663,18 +618663,18 @@ "webrtc/RTCPeerConnection-generateCertificate.html": [ "27fb46922255203da0fc26a63808aeb98a60b640", "testharness" ], "webrtc/RTCPeerConnection-getDefaultIceServers.html": [ "208bb45887440df3bf1e45dd63f09d2d5b70857d", "testharness" ], - "webrtc/RTCPeerConnection-getIdentityAssertion.html": [ - "e87f8367bcd63ed4407e256b6fea42f9f66ecd40", + "webrtc/RTCPeerConnection-getIdentityAssertion.sub.html": [ + "1008ce2bf98829460c2de29d59558ca10e0e81e9", "testharness" ], "webrtc/RTCPeerConnection-getStats.https.html": [ "913cbc3d2aaf724e70108e7854f56ad5bb9b2283", "testharness" ], "webrtc/RTCPeerConnection-getTransceivers.html": [ "b4c97af4f907a3d02fe1ebd24f00ab110b387575", @@ -618700,17 +618700,17 @@ "ca1cbd230de7aec4844879ae43f822941f566620", "testharness" ], "webrtc/RTCPeerConnection-ontrack.https.html": [ "3db4d8b29f4e1372055a50a279cae525f52cbb40", "testharness" ], "webrtc/RTCPeerConnection-peerIdentity.html": [ - "5aa9f3d712dd320cc85645abd39f960b5072349b", + "d821c1516578820206ecc4a9f36dc4f28f2e52dd", "testharness" ], "webrtc/RTCPeerConnection-removeTrack.https.html": [ "561575bea206ec1c9572e1e5e6f97d1e0bebe2d1", "testharness" ], "webrtc/RTCPeerConnection-setDescription-transceiver.html": [ "a21fe04592ad6941aa4277535d6482519b67ae74", @@ -618887,18 +618887,18 @@ "webrtc/getstats.html": [ "4c47dcbadf09fdaecafc3ddcabd5510975dd5154", "testharness" ], "webrtc/historical.html": [ "d0579ad82d492ba5cd957561ca70b5b8a344452c", "testharness" ], - "webrtc/identity-helper.js": [ - "7e12bca67dadbdcec5cbba31817dbec3f01da57c", + "webrtc/identity-helper.sub.js": [ + "8286dcf59e5eae0320a569c2097423d9589b0be2", "support" ], "webrtc/interfaces.https.html": [ "ef5a449587001f2bdfe82dad68920972f2aeafb1", "testharness" ], "webrtc/no-media-call.html": [ "e9f056be5a865f1bb73d60ec72c38f8d5f16d747", @@ -618916,17 +618916,17 @@ "60f8a95a3fe3aac9b361e52d2d974cdd2483a46d", "testharness" ], "webrtc/simplecall.https.html": [ "146432ca56e487a035df8ad9d5a7fa4a495b5405", "testharness" ], "webrtc/tools/.eslintrc.js": [ - "ceb052e89c7e9bef32fd37942515b2d38d59d269", + "3ae35a91ae46bfba2c2ef959338ba1b61d1b3761", "support" ], "webrtc/tools/README.md": [ "4a7dfd32e2129c362e153a83e4645fcc77b74247", "support" ], "webrtc/tools/package-lock.json": [ "731c41b82c17db5d5c3e0c636c197fcba01df344",
--- a/testing/web-platform/tests/clear-site-data/support/test_utils.sub.js +++ b/testing/web-platform/tests/clear-site-data/support/test_utils.sub.js @@ -262,16 +262,16 @@ var TestUtils = (function() { * @return The URL of a page that contains a resource requesting the deletion * of storage. */ TestUtils.getPageWithResourceUrl = function(page_scheme, resource_scheme) { if (page_scheme != "https" && page_scheme != "http") throw "Unsupported scheme: " + page_scheme; if (resource_scheme != "https" && resource_scheme != "http") throw "Unsupported scheme: " + resource_scheme; - return page_scheme + "://web-platform.test:" + + return page_scheme + "://{{domains[]}}:" + (page_scheme == "https" ? {{ports[https][0]}} : {{ports[http][0]}}) + "/clear-site-data/support/page_with_resource.sub.html?scheme=" + resource_scheme; } return TestUtils; })();
--- a/testing/web-platform/tests/content-security-policy/base-uri/report-uri-does-not-respect-base-uri.sub.html +++ b/testing/web-platform/tests/content-security-policy/base-uri/report-uri-does-not-respect-base-uri.sub.html @@ -1,16 +1,16 @@ <!DOCTYPE HTML> <html> <head> <title>Test that base does not affect report-uri</title> <script src='/resources/testharness.js'></script> <script src='/resources/testharnessreport.js'></script> <!-- if base is used for resolving the URL to report to then we will not get a report --> - <base href="http://nonexistent.web-platform.test"> + <base href="http://nonexistent.{{domains[]}}"> </head> <body> <script> var t1 = async_test("Test that image does not load"); async_test(function(t2) { window.addEventListener("securitypolicyviolation", t2.step_func(function(e) { assert_equals(e.blockedURI, "{{location[scheme]}}://{{location[host]}}/content-security-policy/support/fail.png"); assert_equals(e.violatedDirective, "img-src");
--- a/testing/web-platform/tests/content-security-policy/generic/generic-0_8.sub.html +++ b/testing/web-platform/tests/content-security-policy/generic/generic-0_8.sub.html @@ -1,12 +1,12 @@ <!DOCTYPE HTML> <html> <head> - <title>test wildcard host name matching (*.web-platform.test is good)</title> + <title>test wildcard host name matching (asterisk as a subdomain of the current domain)</title> <meta http-equiv="Content-Security-Policy" content="script-src 'self' *.{{host}}:{{ports[http][0]}} 'unsafe-inline';"> <script src='/resources/testharness.js'></script> <script src='/resources/testharnessreport.js'></script> <script src='wildcardHostTest.js'></script> <script> var t = async_test("Test that script does not fire violation event"); window.addEventListener("securitypolicyviolation", t.unreached_func("Should not have fired a violation event")); @@ -17,12 +17,12 @@ head.appendChild(script); </script> <script> t.done(); </script> </head> <body> - <h1>test wildcard host name matching (*.web-platform.test is good)</h1> + <h1>test wildcard host name matching (asterisk as a subdomain of the current domain)</h1> <div id='log'></div> </body> </html>
--- a/testing/web-platform/tests/content-security-policy/generic/generic-0_8_1.sub.html +++ b/testing/web-platform/tests/content-security-policy/generic/generic-0_8_1.sub.html @@ -1,12 +1,12 @@ <!DOCTYPE HTML> <html> <head> - <title>test wildcard host name matching (www*.web-platform.test is bad, *www.web-platform.test is bad)</title> + <title>test wildcard host name matching (asterisk as part of a subdomain is not accepted)</title> <meta http-equiv="Content-Security-Policy" content="script-src 'self' *w.{{host}}:{{ports[http][0]}} w*.{{host}}:{{ports[http][0]}} 'unsafe-inline';"> <script src='/resources/testharness.js'></script> <script src='/resources/testharnessreport.js'></script> <script src='wildcardHostTestFailure.js'></script> <script> var t_spv = async_test("Should fire violation events for every failed violation"); window.addEventListener("securitypolicyviolation", t_spv.step_func_done(function(e) { assert_equals(e.violatedDirective, "script-src"); @@ -15,12 +15,12 @@ var head = document.getElementsByTagName('head')[0]; var script = document.createElement('script'); script.type = 'text/javascript'; script.src = "http://www." + location.hostname + ":" + location.port + "/content-security-policy/generic/wildcardHostTestSuceeds.js"; head.appendChild(script); </script> </head> <body> - <h1>test wildcard host name matching (www*.web-platform.test is bad, *www.web-platform.test is bad)</h1> + <h1>test wildcard host name matching (asterisk as part of a subdomain is not accepted)</h1> <div id='log'></div> </body> </html>
deleted file mode 100644 --- a/testing/web-platform/tests/content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.html +++ /dev/null @@ -1,130 +0,0 @@ -<!DOCTYPE html> -<script src="/resources/testharness.js"></script> -<script src="/resources/testharnessreport.js"></script> - -<meta http-equiv="content-security-policy" content="script-src 'nonce-abc'; img-src 'none'"> - -<body> -<!-- Basics --> -<script nonce="abc" id="testScript"> - document.currentScript.setAttribute('executed', 'yay'); -</script> - -<script nonce="abc"> - var script = document.querySelector('#testScript'); - - test(t => { - // Query Selector - assert_equals(document.querySelector('body [nonce]'), script); - assert_equals(document.querySelector('body [nonce=""]'), null); - assert_equals(document.querySelector('body [nonce=abc]'), script); - - assert_equals(script.getAttribute('nonce'), 'abc'); - assert_equals(script.nonce, 'abc'); - }, "Reading 'nonce' content attribute and IDL attribute."); - - // Clone node. - test(t => { - script.setAttribute('executed', 'boo'); - var s2 = script.cloneNode(); - assert_equals(s2.nonce, 'abc', 'IDL attribute'); - assert_equals(s2.getAttribute('nonce'), 'abc'); - }, "Cloned node retains nonce."); - - async_test(t => { - var s2 = script.cloneNode(); - document.head.appendChild(s2); - assert_equals(s2.nonce, 'abc'); - assert_equals(s2.getAttribute('nonce'), 'abc'); - window.addEventListener('load', t.step_func_done(_ => { - // The cloned script won't execute, as its 'already started' flag is set. - assert_equals(s2.getAttribute('executed'), 'boo'); - })); - }, "Cloned node retains nonce when inserted."); - - // Set the content attribute to 'foo' - test(t => { - script.setAttribute('nonce', 'foo'); - assert_equals(script.getAttribute('nonce'), 'foo'); - assert_equals(script.nonce, 'foo'); - }, "Writing 'nonce' content attribute."); - - // Set the IDL attribute to 'bar' - test(t => { - script.nonce = 'bar'; - assert_equals(script.nonce, 'bar'); - assert_equals(script.getAttribute('nonce'), 'foo'); - }, "Writing 'nonce' IDL attribute."); - - // Fragment parser. - var documentWriteTest = async_test("Document-written script executes."); - document.write(`<script nonce='abc'> - documentWriteTest.done(); - test(t => { - var script = document.currentScript; - assert_equals(script.getAttribute('nonce'), 'abc'); - assert_equals(script.nonce, 'abc'); - }, "Document-written script's nonce value."); - </scr` + `ipt>`); - - // Create node. - async_test(t => { - var s = document.createElement('script'); - s.innerText = script.innerText; - s.nonce = 'abc'; - document.head.appendChild(s); - assert_equals(s.nonce, 'abc'); - assert_equals(s.getAttribute('nonce'), null); - - window.addEventListener('load', t.step_func_done(_ => { - assert_equals(s.getAttribute('executed'), 'yay'); - })); - }, "createElement.nonce."); - - async_test(t => { - var s = document.createElement('script'); - s.innerText = script.innerText; - s.nonce = 'zyx'; - s.setAttribute('nonce', 'abc'); - assert_equals(s.nonce, 'abc'); - document.head.appendChild(s); - assert_equals(s.nonce, 'abc'); - assert_equals(s.getAttribute('nonce'), 'abc'); - - window.addEventListener('load', t.step_func_done(_ => { - assert_equals(s.getAttribute('executed'), 'yay'); - })); - }, "setAttribute('nonce') overwrites '.nonce' upon insertion."); - - // Create node. - async_test(t => { - var s = document.createElement('script'); - s.innerText = script.innerText; - s.setAttribute('nonce', 'abc'); - assert_equals(s.getAttribute('nonce'), 'abc', "Pre-insertion content"); - assert_equals(s.nonce, 'abc', "Pre-insertion IDL"); - document.head.appendChild(s); - assert_equals(s.nonce, 'abc', "Post-insertion IDL"); - assert_equals(s.getAttribute('nonce'), 'abc', "Post-insertion content"); - - window.addEventListener('load', t.step_func_done(_ => { - assert_equals(s.getAttribute('executed'), 'yay'); - })); - }, "createElement.setAttribute."); -</script> - -<!-- CSS Leakage --> -<style> - #cssTest { display: block; } - #cssTest[nonce=abc] { background: url(/security/resources/abe.png); } -</style> -<script nonce="abc" id="cssTest"> - async_test(t => { - requestAnimationFrame(t.step_func_done(_ => { - var script = document.querySelector('#cssTest'); - var style = getComputedStyle(script); - assert_equals(style['display'], 'block'); - assert_equals(style['background-image'], "url(\"http://web-platform.test:8001/security/resources/abe.png\")"); - })); - }, "Nonces leak via CSS side-channels."); -</script>
new file mode 100644 --- /dev/null +++ b/testing/web-platform/tests/content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.sub.html @@ -0,0 +1,130 @@ +<!DOCTYPE html> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<meta http-equiv="content-security-policy" content="script-src 'nonce-abc'; img-src 'none'"> + +<body> +<!-- Basics --> +<script nonce="abc" id="testScript"> + document.currentScript.setAttribute('executed', 'yay'); +</script> + +<script nonce="abc"> + var script = document.querySelector('#testScript'); + + test(t => { + // Query Selector + assert_equals(document.querySelector('body [nonce]'), script); + assert_equals(document.querySelector('body [nonce=""]'), null); + assert_equals(document.querySelector('body [nonce=abc]'), script); + + assert_equals(script.getAttribute('nonce'), 'abc'); + assert_equals(script.nonce, 'abc'); + }, "Reading 'nonce' content attribute and IDL attribute."); + + // Clone node. + test(t => { + script.setAttribute('executed', 'boo'); + var s2 = script.cloneNode(); + assert_equals(s2.nonce, 'abc', 'IDL attribute'); + assert_equals(s2.getAttribute('nonce'), 'abc'); + }, "Cloned node retains nonce."); + + async_test(t => { + var s2 = script.cloneNode(); + document.head.appendChild(s2); + assert_equals(s2.nonce, 'abc'); + assert_equals(s2.getAttribute('nonce'), 'abc'); + window.addEventListener('load', t.step_func_done(_ => { + // The cloned script won't execute, as its 'already started' flag is set. + assert_equals(s2.getAttribute('executed'), 'boo'); + })); + }, "Cloned node retains nonce when inserted."); + + // Set the content attribute to 'foo' + test(t => { + script.setAttribute('nonce', 'foo'); + assert_equals(script.getAttribute('nonce'), 'foo'); + assert_equals(script.nonce, 'foo'); + }, "Writing 'nonce' content attribute."); + + // Set the IDL attribute to 'bar' + test(t => { + script.nonce = 'bar'; + assert_equals(script.nonce, 'bar'); + assert_equals(script.getAttribute('nonce'), 'foo'); + }, "Writing 'nonce' IDL attribute."); + + // Fragment parser. + var documentWriteTest = async_test("Document-written script executes."); + document.write(`<script nonce='abc'> + documentWriteTest.done(); + test(t => { + var script = document.currentScript; + assert_equals(script.getAttribute('nonce'), 'abc'); + assert_equals(script.nonce, 'abc'); + }, "Document-written script's nonce value."); + </scr` + `ipt>`); + + // Create node. + async_test(t => { + var s = document.createElement('script'); + s.innerText = script.innerText; + s.nonce = 'abc'; + document.head.appendChild(s); + assert_equals(s.nonce, 'abc'); + assert_equals(s.getAttribute('nonce'), null); + + window.addEventListener('load', t.step_func_done(_ => { + assert_equals(s.getAttribute('executed'), 'yay'); + })); + }, "createElement.nonce."); + + async_test(t => { + var s = document.createElement('script'); + s.innerText = script.innerText; + s.nonce = 'zyx'; + s.setAttribute('nonce', 'abc'); + assert_equals(s.nonce, 'abc'); + document.head.appendChild(s); + assert_equals(s.nonce, 'abc'); + assert_equals(s.getAttribute('nonce'), 'abc'); + + window.addEventListener('load', t.step_func_done(_ => { + assert_equals(s.getAttribute('executed'), 'yay'); + })); + }, "setAttribute('nonce') overwrites '.nonce' upon insertion."); + + // Create node. + async_test(t => { + var s = document.createElement('script'); + s.innerText = script.innerText; + s.setAttribute('nonce', 'abc'); + assert_equals(s.getAttribute('nonce'), 'abc', "Pre-insertion content"); + assert_equals(s.nonce, 'abc', "Pre-insertion IDL"); + document.head.appendChild(s); + assert_equals(s.nonce, 'abc', "Post-insertion IDL"); + assert_equals(s.getAttribute('nonce'), 'abc', "Post-insertion content"); + + window.addEventListener('load', t.step_func_done(_ => { + assert_equals(s.getAttribute('executed'), 'yay'); + })); + }, "createElement.setAttribute."); +</script> + +<!-- CSS Leakage --> +<style> + #cssTest { display: block; } + #cssTest[nonce=abc] { background: url(/security/resources/abe.png); } +</style> +<script nonce="abc" id="cssTest"> + async_test(t => { + requestAnimationFrame(t.step_func_done(_ => { + var script = document.querySelector('#cssTest'); + var style = getComputedStyle(script); + assert_equals(style['display'], 'block'); + assert_equals(style['background-image'], "url(\"http://{{domains[]}}:{{ports[http][0]}}/security/resources/abe.png\")"); + })); + }, "Nonces leak via CSS side-channels."); +</script>
deleted file mode 100644 --- a/testing/web-platform/tests/content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.html +++ /dev/null @@ -1,116 +0,0 @@ -<!DOCTYPE html> -<script src="/resources/testharness.js"></script> -<script src="/resources/testharnessreport.js"></script> - -<meta http-equiv="content-security-policy" content="script-src 'nonce-abc'; img-src 'none'"> - -<body> -<!-- Basics --> -<svg xmlns="http://www.w3.org/2000/svg"> - <script nonce="abc" id="testScript"> - document.currentScript.setAttribute('executed', 'yay'); - </script> -</svg> - -<script nonce="abc"> - var script = document.querySelector('#testScript'); - - test(t => { - // Query Selector - assert_equals(document.querySelector('[nonce]'), script); - assert_equals(document.querySelector('[nonce=""]'), null); - assert_equals(document.querySelector('[nonce=abc]'), script); - - assert_equals(script.getAttribute('nonce'), 'abc'); - assert_equals(script.nonce, 'abc'); - }, "Reading 'nonce' content attribute and IDL attribute."); - - // Clone node. - test(t => { - script.setAttribute('executed', 'boo'); - var s2 = script.cloneNode(); - assert_equals(s2.nonce, 'abc', 'IDL attribute'); - assert_equals(s2.getAttribute('nonce'), 'abc'); - }, "Cloned node retains nonce."); - - async_test(t => { - var s2 = script.cloneNode(); - document.head.appendChild(s2); - assert_equals(s2.nonce, 'abc'); - assert_equals(s2.getAttribute('nonce'), 'abc'); - - window.addEventListener('load', t.step_func_done(_ => { - // The cloned script won't execute, as its 'already started' flag is set. - assert_equals(s2.getAttribute('executed'), 'boo'); - })); - }, "Cloned node retains nonce when inserted."); - - // Set the content attribute to 'foo' - test(t => { - script.setAttribute('nonce', 'foo'); - assert_equals(script.getAttribute('nonce'), 'foo'); - assert_equals(script.nonce, 'abc'); - }, "Writing 'nonce' content attribute."); - - // Set the IDL attribute to 'bar' - test(t => { - script.nonce = 'bar'; - assert_equals(script.nonce, 'bar'); - assert_equals(script.getAttribute('nonce'), 'foo'); - }, "Writing 'nonce' IDL attribute."); - - // Fragment parser. - var documentWriteTest = async_test("Document-written script executes."); - document.write(`<svg xmlns="http://www.w3.org/2000/svg"><script nonce='abc'> - documentWriteTest.done(); - test(t => { - var script = document.currentScript; - assert_equals(script.getAttribute('nonce'), 'abc'); - assert_equals(script.nonce, 'abc'); - }, "Document-written script's nonce value."); - </scr` + `ipt></svg>`); - - // Create node. - test(t => { - var s = document.createElement('svg'); - var innerScript = document.createElement('innerScript'); - innerScript.innerText = script.innerText; - innerScript.nonce = 'abc'; - s.appendChild(innerScript); - document.body.appendChild(s); - assert_equals(innerScript.nonce, 'abc'); - assert_equals(innerScript.getAttribute('nonce'), null, 'innerScript.getAttribute nonce'); - }, "createElement.nonce."); - - // Create node. - test(t => { - var s = document.createElement('svg'); - var innerScript = document.createElement('script'); - innerScript.innerText = script.innerText; - innerScript.setAttribute('nonce', 'abc'); - assert_equals(innerScript.getAttribute('nonce'), 'abc', "Pre-insertion content"); - assert_equals(innerScript.nonce, 'abc', "Pre-insertion IDL"); - s.appendChild(innerScript); - document.body.appendChild(s); - assert_equals(innerScript.nonce, 'abc', "Post-insertion IDL"); - assert_equals(innerScript.getAttribute('nonce'), 'abc', "Post-insertion content"); - }, "createElement.setAttribute."); -</script> - -<!-- CSS Leakage --> -<style> - #cssTest { display: block; } - #cssTest[nonce=abc] { background: url(/security/resources/abe.png); } -</style> -<svg xmlns="http://www.w3.org/2000/svg"> - <script nonce="abc" id="cssTest"> - async_test(t => { - requestAnimationFrame(t.step_func_done(_ => { - var script = document.querySelector('#cssTest'); - var style = getComputedStyle(script); - assert_equals(style['display'], 'block'); - assert_equals(style['background-image'], "url(\"http://web-platform.test:8001/security/resources/abe.png\")"); - })); - }, "Nonces don't leak via CSS side-channels."); - </script> -</svg>
new file mode 100644 --- /dev/null +++ b/testing/web-platform/tests/content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.sub.html @@ -0,0 +1,116 @@ +<!DOCTYPE html> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> + +<meta http-equiv="content-security-policy" content="script-src 'nonce-abc'; img-src 'none'"> + +<body> +<!-- Basics --> +<svg xmlns="http://www.w3.org/2000/svg"> + <script nonce="abc" id="testScript"> + document.currentScript.setAttribute('executed', 'yay'); + </script> +</svg> + +<script nonce="abc"> + var script = document.querySelector('#testScript'); + + test(t => { + // Query Selector + assert_equals(document.querySelector('[nonce]'), script); + assert_equals(document.querySelector('[nonce=""]'), null); + assert_equals(document.querySelector('[nonce=abc]'), script); + + assert_equals(script.getAttribute('nonce'), 'abc'); + assert_equals(script.nonce, 'abc'); + }, "Reading 'nonce' content attribute and IDL attribute."); + + // Clone node. + test(t => { + script.setAttribute('executed', 'boo'); + var s2 = script.cloneNode(); + assert_equals(s2.nonce, 'abc', 'IDL attribute'); + assert_equals(s2.getAttribute('nonce'), 'abc'); + }, "Cloned node retains nonce."); + + async_test(t => { + var s2 = script.cloneNode(); + document.head.appendChild(s2); + assert_equals(s2.nonce, 'abc'); + assert_equals(s2.getAttribute('nonce'), 'abc'); + + window.addEventListener('load', t.step_func_done(_ => { + // The cloned script won't execute, as its 'already started' flag is set. + assert_equals(s2.getAttribute('executed'), 'boo'); + })); + }, "Cloned node retains nonce when inserted."); + + // Set the content attribute to 'foo' + test(t => { + script.setAttribute('nonce', 'foo'); + assert_equals(script.getAttribute('nonce'), 'foo'); + assert_equals(script.nonce, 'abc'); + }, "Writing 'nonce' content attribute."); + + // Set the IDL attribute to 'bar' + test(t => { + script.nonce = 'bar'; + assert_equals(script.nonce, 'bar'); + assert_equals(script.getAttribute('nonce'), 'foo'); + }, "Writing 'nonce' IDL attribute."); + + // Fragment parser. + var documentWriteTest = async_test("Document-written script executes."); + document.write(`<svg xmlns="http://www.w3.org/2000/svg"><script nonce='abc'> + documentWriteTest.done(); + test(t => { + var script = document.currentScript; + assert_equals(script.getAttribute('nonce'), 'abc'); + assert_equals(script.nonce, 'abc'); + }, "Document-written script's nonce value."); + </scr` + `ipt></svg>`); + + // Create node. + test(t => { + var s = document.createElement('svg'); + var innerScript = document.createElement('innerScript'); + innerScript.innerText = script.innerText; + innerScript.nonce = 'abc'; + s.appendChild(innerScript); + document.body.appendChild(s); + assert_equals(innerScript.nonce, 'abc'); + assert_equals(innerScript.getAttribute('nonce'), null, 'innerScript.getAttribute nonce'); + }, "createElement.nonce."); + + // Create node. + test(t => { + var s = document.createElement('svg'); + var innerScript = document.createElement('script'); + innerScript.innerText = script.innerText; + innerScript.setAttribute('nonce', 'abc'); + assert_equals(innerScript.getAttribute('nonce'), 'abc', "Pre-insertion content"); + assert_equals(innerScript.nonce, 'abc', "Pre-insertion IDL"); + s.appendChild(innerScript); + document.body.appendChild(s); + assert_equals(innerScript.nonce, 'abc', "Post-insertion IDL"); + assert_equals(innerScript.getAttribute('nonce'), 'abc', "Post-insertion content"); + }, "createElement.setAttribute."); +</script> + +<!-- CSS Leakage --> +<style> + #cssTest { display: block; } + #cssTest[nonce=abc] { background: url(/security/resources/abe.png); } +</style> +<svg xmlns="http://www.w3.org/2000/svg"> + <script nonce="abc" id="cssTest"> + async_test(t => { + requestAnimationFrame(t.step_func_done(_ => { + var script = document.querySelector('#cssTest'); + var style = getComputedStyle(script); + assert_equals(style['display'], 'block'); + assert_equals(style['background-image'], "url(\"http://{{domains[]}}:{{ports[http][0]}}/security/resources/abe.png\")"); + })); + }, "Nonces don't leak via CSS side-channels."); + </script> +</svg>
--- a/testing/web-platform/tests/fetch/api/request/request-structure.html +++ b/testing/web-platform/tests/fetch/api/request/request-structure.html @@ -40,17 +40,17 @@ switch (attributeToCheck) { case "method": defaultValue = "GET"; newValue = "POST"; break; case "url": //default value is base url - //i.e http://web-platform.test:8000/fetch/api/request-structure.html + //i.e http://example.com/fetch/api/request-structure.html newValue = "http://url.test"; break; case "headers": request.headers = new Headers ({"name":"value"}); assert_false(request.headers.has("name"), "Headers attribute is read only"); return; break;
--- a/testing/web-platform/tests/html/browsers/origin/relaxing-the-same-origin-restriction/document_domain_setter.html +++ b/testing/web-platform/tests/html/browsers/origin/relaxing-the-same-origin-restriction/document_domain_setter.html @@ -6,27 +6,27 @@ <script src="/resources/testharnessreport.js"></script> <script src="/common/get-host-info.sub.js"></script> </head> <body> <iframe id="iframe"></iframe> <script> var host_info = get_host_info(); var HTTP_PORT = host_info.HTTP_PORT; - var ORIGINAL_HOST = host_info.ORIGINAL_HOST; // e.g. "web-platform.test" + var ORIGINAL_HOST = host_info.ORIGINAL_HOST; var SUFFIX_HOST = ORIGINAL_HOST.substring(ORIGINAL_HOST.lastIndexOf('.') + 1); // e.g. "test" - var PREFIX_HOST = "www1." + ORIGINAL_HOST; // e.g. "www1.web-platform.test" + var REMOTE_HOST = host_info.REMOTE_HOST; var iframe = document.getElementById("iframe"); var iframe_url = new URL("support/document_domain_setter_iframe.html", document.location); - iframe_url.hostname = PREFIX_HOST; + iframe_url.hostname = REMOTE_HOST; iframe.src = iframe_url; test(function() { assert_throws("SecurityError", function() { document.domain = SUFFIX_HOST; }); assert_throws("SecurityError", function() { document.domain = "." + SUFFIX_HOST; }); - assert_throws("SecurityError", function() { document.domain = PREFIX_HOST; }); + assert_throws("SecurityError", function() { document.domain = REMOTE_HOST; }); assert_throws("SecurityError", function() { document.domain = "example.com"; }); }, "failed setting of document.domain"); async_test(function(t) { iframe.addEventListener("load", t.step_func_done(function() { // Before setting document.domain, the iframe is not // same-origin-domain, so security checks fail. assert_equals(iframe.contentDocument, null); assert_throws("SecurityError", () => iframe.contentWindow.frameElement);
deleted file mode 100644 --- a/testing/web-platform/tests/html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.html +++ /dev/null @@ -1,19 +0,0 @@ -<!doctype html> -<meta charset="utf-8"> -<title>Check the frame heriarchy</title> -<script src="/resources/testharness.js"></script> -<script src="/resources/testharnessreport.js"></script> -<script src="iframe_harness.js"></script> -<body> - <iframe src="http://www1.web-platform.test:8000/html/semantics/embedded-content/the-iframe-element/cross_origin_child.html"></iframe> -</body> -<script> - get_test_results('bffa23ee-b45a-4e9a-9405-87ab437d5cfa'); - get_test_results('79a52de8-4222-427e-92db-caec28e75f8e'); - get_test_results('6c8da65d-2c5e-44ef-bb0b-b8b9849aab19'); - send_test_results({ - "id": 'bffa23ee-b45a-4e9a-9405-87ab437d5cfa', - "parent": window.parent === window, - "top": window.top === window, - }); -</script>
new file mode 100644 --- /dev/null +++ b/testing/web-platform/tests/html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.sub.html @@ -0,0 +1,19 @@ +<!doctype html> +<meta charset="utf-8"> +<title>Check the frame heriarchy</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="iframe_harness.js"></script> +<body> + <iframe src="http://{{domains[www1]}}:{{ports[http][0]}}/html/semantics/embedded-content/the-iframe-element/cross_origin_child.html"></iframe> +</body> +<script> + get_test_results('bffa23ee-b45a-4e9a-9405-87ab437d5cfa'); + get_test_results('79a52de8-4222-427e-92db-caec28e75f8e'); + get_test_results('6c8da65d-2c5e-44ef-bb0b-b8b9849aab19'); + send_test_results({ + "id": 'bffa23ee-b45a-4e9a-9405-87ab437d5cfa', + "parent": window.parent === window, + "top": window.top === window, + }); +</script>
deleted file mode 100644 --- a/testing/web-platform/tests/html/semantics/forms/the-label-element/label-attributes.html +++ /dev/null @@ -1,353 +0,0 @@ -<!DOCTYPE html> -<meta charset="utf-8"> -<title>HTML Test: The label element</title> -<link rel="author" title="Intel" href="http://www.intel.com/"> -<script src="/resources/testharness.js"></script> -<script src="/resources/testharnessreport.js"></script> -<div id="log"></div> -<form id="fm" style="display:none"> - <label id="lbl0" for="test0"></label> - <b id="test0"></b> - - <input id="test1"></input> - - <label id="lbl1"> - <a id="test2"></a> - <div><input id="test3"></div> - <input id="test4"> - </label> - - <label id="lbl2" for="testx"> - <input id="test5"> - </label> - - <label id="lbl3" for="test6"> - <b id="test6"></b> - <input id="test6" class="class1"> - </label> - - <label id="lbl4" for=""> - <input id="" class="class2"> - </label> - - <label id="lbl5" for="test7"></label> - <input id="test7"> - - <label id="lbl7"> - <label id="lbl8"> - <div id="div1"> - <input id="test8"> - </div> - </label> - </label> - <div id="div2"></div> - - <label id="lbl9"> - <label id="lbl10" for="test10"> - <div id="div3"> - <input id="test9"> - </div> - </label> - </label> - <div id="div4"><input id="test10"></div> - - <label id="lbl11"> - <object id="obj"> - <input id="test11"> - <input id="test12"> - </object> - </label> - <label id="lbl12" for="test12"><div id="div5"></div></label> - - <label id="lbl13"> - <p id="p1"> - <input id="test13"> - </p> - </label> - - <div id="div6"> - <div id="div7"> - <label id="lbl14"> - <label id="lbl15" for="test15"> - <input id="test14"> - </label> - </label> - </div> - </div> - <input id="test15"> -</form> - -<label id="lbl6" for="test7"></label> -<div id="content" style="display: none"> -<script> - - //control attribute - test(function () { - assert_not_equals(document.getElementById("lbl0").control, document.getElementById("test0"), - "An element that's not a labelable element can't be a label element's labeled control."); - assert_equals(document.getElementById("lbl0").control, null, - "A label element whose 'for' attribute doesn't reference any labelable element shouldn't have any labeled control."); - }, "A label element with a 'for' attribute should only be associated with a labelable element."); - - test(function () { - var label = document.createElement("label"); - label.htmlFor = "test1"; - assert_not_equals(label.control, document.getElementById("test1"), - "A label element not in a document should not label an element in a document."); - document.body.appendChild(label); - assert_equals(label.control, document.getElementById("test1")); - label.remove(); - }, "A label element not in a document can not label any element in the document."); - - test(function () { - var labels = document.getElementById("test3").labels; - assert_equals(document.getElementById("lbl1").control, document.getElementById("test3"), - "The first labelable descendant of a label element should be its labeled control."); - - var input = document.createElement("input"); - document.getElementById("lbl1").insertBefore(input, document.getElementById("test2")); - assert_equals(document.getElementById("lbl1").control, input, - "The first labelable descendant of a label element in tree order should be its labeled control."); - assert_equals(input.labels.length, 1, - "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); - assert_equals(labels.length, 0, - "The number of labels should be 0 if it's not the first labelable descendant of a label element."); - input.remove(); - }, "The labeled control for a label element that has no 'for' attribute is the first labelable element which is a descendant of that label element."); - - test(function () { - assert_equals(document.getElementById("lbl2").control, null, - "The label's 'control' property should return null if its 'for' attribute points to an inexistent element."); - }, "The 'for' attribute points to an inexistent id."); - - test(function () { - assert_equals(document.getElementById("lbl3").control, null, "The label should have no control associated."); - assert_equals(document.querySelector(".class1").labels.length, 0); - }, "A non-control follows by a control with same ID."); - - test(function () { - assert_equals(document.getElementById("lbl4").control, null, - "A label element with an empty 'for' attribute should not associate with anything."); - }, "The 'for' attribute is an empty string."); - - //labels attribute - test(function () { - var labels = document.getElementById("test7").labels; - assert_true(labels instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(labels.length, 2, - "The number of labels associated with a form control should be the number of label elements for which it is a labeled control."); - assert_array_equals(labels, [document.getElementById("lbl5"), document.getElementById("lbl6")], - "The labels for a form control should be returned in tree order."); - - var newLabel = document.createElement("label"); - newLabel.htmlFor = "test7"; - document.getElementById("fm").insertBefore(newLabel, document.getElementById("lbl0")); - assert_array_equals(document.getElementById("test7").labels, [newLabel, document.getElementById("lbl5"), document.getElementById("lbl6")], - "The labels for a form control should be returned in tree order."); - newLabel.remove(); - }, "A form control has multiple labels."); - - test(function () { - var labels = document.getElementById("test8").labels; - assert_true(labels instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(labels.length, 2, - "The form control has two ancestors with no explicit associated label, and is the first labelable descendant."); - assert_array_equals(labels, [document.getElementById("lbl7"), document.getElementById("lbl8")], - "The labels for a form control should be returned in tree order."); - - document.getElementById('div2').insertBefore(document.getElementById('div1'), document.getElementById('div2').firstChild); - assert_equals(labels.length, 0, - "The number of labels should be 0 after the labelable element is moved to outside of nested associated labels."); - }, "A labelable element is moved to outside of nested associated labels."); - - test(function () { - var labels1 = document.getElementById("test9").labels; - var labels2 = document.getElementById("test10").labels; - assert_true(labels1 instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_true(labels2 instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(labels1.length, 1, - "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); - assert_equals(labels2.length, 1, - "The number of labels associated with a form control should be the number of label elements for which it is a labeled control."); - assert_array_equals(labels1, [document.getElementById("lbl9")], - "The labels for a form control should be returned in tree order."); - assert_array_equals(labels2, [document.getElementById("lbl10")], - "The labels for a form control should be returned in tree order."); - document.getElementById('div3').insertBefore(document.getElementById('div4'), document.getElementById('div3').firstChild); - assert_equals(labels1.length, 0, - "The number of labels should be 0 if it's not the first labelable descendant of a label element."); - assert_equals(labels2.length, 2, - "The form control has an ancestor with an explicit associated label, and is the first labelable descendant."); - }, "A labelable element is moved to inside of nested associated labels."); - - test(function () { - var labels1 = document.getElementById("test11").labels; - var labels2 = document.getElementById("test12").labels; - assert_true(labels1 instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_true(labels2 instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(labels1.length, 1, - "The form control has an ancestor with no explicit associated label, and it is the first labelable descendant."); - assert_equals(labels2.length, 1, - "The number of labels should be 1 since there is a label with a 'for' attribute associated with this labelable element."); - assert_array_equals(labels1, [document.getElementById("lbl11")], - "The labels for a form control should be returned in tree order."); - assert_array_equals(labels2, [document.getElementById("lbl12")], - "The labels for a form control should be returned in tree order."); - document.getElementById('div5').appendChild(document.getElementById('obj')); - assert_equals(labels1.length, 0, - "The number of labels should be 0 after the labelable element is moved to outside of associated label."); - assert_equals(labels2.length, 1, - "The number of labels should be 1 after the labelable element is moved to outside of associated label."); - }, "A labelable element which is a descendant of non-labelable element is moved to outside of associated label."); - - async_test(function () { - var labels = document.getElementById("test13").labels; - assert_true(labels instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(labels.length, 1, - "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); - assert_array_equals(labels, [document.getElementById("lbl13")], - "The labels for a form control should be returned in tree order."); - let iframe = document.createElement('iframe'); - - iframe.onload = this.step_func_done(() => { - iframe.contentWindow.document.getElementById("div1").appendChild(document.getElementById("p1")); - assert_equals(labels.length, 2, - "The number of labels should be 2 after the labelable element is moved to iframe."); - }); - - iframe.setAttribute('src', 'http://web-platform.test:8000/html/semantics/forms/the-label-element/iframe-label-attributes.html'); - document.body.appendChild(iframe); - }, "A labelable element is moved to iframe."); - - test(function () { - var test14 = document.getElementById("test14"); - var labels1 = test14.labels; - var labels2 = document.getElementById("test15").labels; - assert_true(labels1 instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(labels1.length, 1, - "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); - assert_equals(labels2.length, 1, - "The number of labels associated with a form control should be the number of label elements for which it is a labeled control."); - assert_array_equals(labels1, [document.getElementById("lbl14")], - "The labels for a form control should be returned in tree order."); - assert_array_equals(labels2, [document.getElementById("lbl15")], - "The labels for a form control should be returned in tree order."); - - document.getElementById('div6').removeChild(document.getElementById('div7')); - assert_equals(labels1.length, 1, - "The number of labels should be 1 after the labelable element is removed but label element is still in the same tree."); - assert_equals(labels2.length, 0, - "The number of labels should be 0 since there is no label with a 'for' attribute associated with this labelable element."); - test14.remove(); - assert_equals(labels1.length, 0, - "The number of labels should be 0 after the labelable element is removed."); - }, "A div element which contains labelable element is removed."); - - test(function () { - // <label><input id="test16"><label for="test16"></label></label> - var label1 = document.createElement('label'); - label1.innerHTML = "<input id='test16'>"; - var label2 = document.createElement('label'); - label2.htmlFor = "test16"; - label1.appendChild(label2); - - var input = label1.firstChild; - var labels = input.labels; - - assert_equals(labels.length, 2, - "The number of labels associated with a form control should be the number of label elements for which it is a labeled control."); - assert_true(labels instanceof NodeList, - "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(label1.control, input, "The first labelable descendant of a label element should be its labeled control."); - assert_equals(label2.control, input, "The labeled cotrol should be associated with the control whose ID is equal to the value of the 'for' attribute."); - }, "A labelable element not in a document can label element in the same tree."); - - test(function () { - var isShadowDOMV0; - if ("createShadowRoot" in document.getElementById('content')) { - isShadowDOMV0 = true; - } - var root1; - if (isShadowDOMV0) { - root1 = document.getElementById('content').createShadowRoot(); - } else { - root1 = document.getElementById('content').attachShadow({mode: 'open'}); - } - assert_true(root1 instanceof DocumentFragment, - "ShadowRoot should be an instance of DocumentFragment."); - // <label><input id="shadow1"/></label><div id="div1"></div> - var label1 = document.createElement('label'); - var input1 = document.createElement('input'); - input1.setAttribute("id", "shadow1"); - label1.appendChild(input1); - root1.appendChild(label1); - - var div1 = document.createElement('div'); - label1.appendChild(div1); - // <label for="shadow2"></label><input id="shadow2"/> - var root2; - if (isShadowDOMV0) { - root2 = div1.createShadowRoot(); - } else { - root2 = div1.attachShadow({mode: 'open'}); - } - - assert_true(root2 instanceof DocumentFragment, - "ShadowRoot should be an instance of DocumentFragment."); - var label2 = document.createElement('label'); - label2.setAttribute("for", "shadow2"); - - var input2 = document.createElement('input'); - input2.setAttribute("id", "shadow2"); - root2.appendChild(label2); - root2.appendChild(input2); - - assert_equals(root1.getElementById("shadow1").labels.length, 1, - "The form control has an ancestor with no explicit associated label, and it is the first labelable descendant."); - assert_equals(root2.getElementById("shadow2").labels.length, 1, - "The number of labels should be 1 since there is a label with a 'for' attribute associated with this labelable element."); - }, "A labelable element inside the shadow DOM."); - - test(function () { - var labels = document.getElementById("test3").labels; - assert_true(labels instanceof NodeList, "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(labels.length, 1, "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); - }, "A form control has an implicit label."); - - test(function () { - var labels = document.getElementById("test4").labels; - assert_true(labels instanceof NodeList, "A form control's 'labels' property should be an instance of a NodeList."); - assert_equals(labels.length, 0, "The form control has an ancestor with no explicit associated label, but is *not* the first labelable descendant"); - }, "A form control has no label 1."); - - test(function () { - assert_equals(document.getElementById("test5").labels.length, 0, - "The number of labels should be 0 if the form control has an ancestor label element that the for attribute points to another control."); - assert_equals(document.getElementById("lbl2").control, null, - "The labeled cotrol should be associated with the control whose ID is equal to the value of the 'for' attribute."); - }, "A form control has no label 2."); - - // form attribute - test(function () { - assert_equals(document.getElementById("lbl0").form, null, - "The 'form' property for a label should return null if label.control is null."); - }, "A label in a form without a control"); - - test(function () { - assert_equals(document.getElementById("lbl6").form, document.getElementById("fm"), - "The 'form' property for a label should return label.control.form."); - }, "A label outside a form with a control inside the form"); - - // htmlFor attribute - test(function () { - assert_equals(document.getElementById("lbl2").htmlFor, "testx"); - }, "A label's htmlFor attribute must reflect the for content attribute"); -</script>
new file mode 100644 --- /dev/null +++ b/testing/web-platform/tests/html/semantics/forms/the-label-element/label-attributes.sub.html @@ -0,0 +1,353 @@ +<!DOCTYPE html> +<meta charset="utf-8"> +<title>HTML Test: The label element</title> +<link rel="author" title="Intel" href="http://www.intel.com/"> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<div id="log"></div> +<form id="fm" style="display:none"> + <label id="lbl0" for="test0"></label> + <b id="test0"></b> + + <input id="test1"></input> + + <label id="lbl1"> + <a id="test2"></a> + <div><input id="test3"></div> + <input id="test4"> + </label> + + <label id="lbl2" for="testx"> + <input id="test5"> + </label> + + <label id="lbl3" for="test6"> + <b id="test6"></b> + <input id="test6" class="class1"> + </label> + + <label id="lbl4" for=""> + <input id="" class="class2"> + </label> + + <label id="lbl5" for="test7"></label> + <input id="test7"> + + <label id="lbl7"> + <label id="lbl8"> + <div id="div1"> + <input id="test8"> + </div> + </label> + </label> + <div id="div2"></div> + + <label id="lbl9"> + <label id="lbl10" for="test10"> + <div id="div3"> + <input id="test9"> + </div> + </label> + </label> + <div id="div4"><input id="test10"></div> + + <label id="lbl11"> + <object id="obj"> + <input id="test11"> + <input id="test12"> + </object> + </label> + <label id="lbl12" for="test12"><div id="div5"></div></label> + + <label id="lbl13"> + <p id="p1"> + <input id="test13"> + </p> + </label> + + <div id="div6"> + <div id="div7"> + <label id="lbl14"> + <label id="lbl15" for="test15"> + <input id="test14"> + </label> + </label> + </div> + </div> + <input id="test15"> +</form> + +<label id="lbl6" for="test7"></label> +<div id="content" style="display: none"> +<script> + + //control attribute + test(function () { + assert_not_equals(document.getElementById("lbl0").control, document.getElementById("test0"), + "An element that's not a labelable element can't be a label element's labeled control."); + assert_equals(document.getElementById("lbl0").control, null, + "A label element whose 'for' attribute doesn't reference any labelable element shouldn't have any labeled control."); + }, "A label element with a 'for' attribute should only be associated with a labelable element."); + + test(function () { + var label = document.createElement("label"); + label.htmlFor = "test1"; + assert_not_equals(label.control, document.getElementById("test1"), + "A label element not in a document should not label an element in a document."); + document.body.appendChild(label); + assert_equals(label.control, document.getElementById("test1")); + label.remove(); + }, "A label element not in a document can not label any element in the document."); + + test(function () { + var labels = document.getElementById("test3").labels; + assert_equals(document.getElementById("lbl1").control, document.getElementById("test3"), + "The first labelable descendant of a label element should be its labeled control."); + + var input = document.createElement("input"); + document.getElementById("lbl1").insertBefore(input, document.getElementById("test2")); + assert_equals(document.getElementById("lbl1").control, input, + "The first labelable descendant of a label element in tree order should be its labeled control."); + assert_equals(input.labels.length, 1, + "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); + assert_equals(labels.length, 0, + "The number of labels should be 0 if it's not the first labelable descendant of a label element."); + input.remove(); + }, "The labeled control for a label element that has no 'for' attribute is the first labelable element which is a descendant of that label element."); + + test(function () { + assert_equals(document.getElementById("lbl2").control, null, + "The label's 'control' property should return null if its 'for' attribute points to an inexistent element."); + }, "The 'for' attribute points to an inexistent id."); + + test(function () { + assert_equals(document.getElementById("lbl3").control, null, "The label should have no control associated."); + assert_equals(document.querySelector(".class1").labels.length, 0); + }, "A non-control follows by a control with same ID."); + + test(function () { + assert_equals(document.getElementById("lbl4").control, null, + "A label element with an empty 'for' attribute should not associate with anything."); + }, "The 'for' attribute is an empty string."); + + //labels attribute + test(function () { + var labels = document.getElementById("test7").labels; + assert_true(labels instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(labels.length, 2, + "The number of labels associated with a form control should be the number of label elements for which it is a labeled control."); + assert_array_equals(labels, [document.getElementById("lbl5"), document.getElementById("lbl6")], + "The labels for a form control should be returned in tree order."); + + var newLabel = document.createElement("label"); + newLabel.htmlFor = "test7"; + document.getElementById("fm").insertBefore(newLabel, document.getElementById("lbl0")); + assert_array_equals(document.getElementById("test7").labels, [newLabel, document.getElementById("lbl5"), document.getElementById("lbl6")], + "The labels for a form control should be returned in tree order."); + newLabel.remove(); + }, "A form control has multiple labels."); + + test(function () { + var labels = document.getElementById("test8").labels; + assert_true(labels instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(labels.length, 2, + "The form control has two ancestors with no explicit associated label, and is the first labelable descendant."); + assert_array_equals(labels, [document.getElementById("lbl7"), document.getElementById("lbl8")], + "The labels for a form control should be returned in tree order."); + + document.getElementById('div2').insertBefore(document.getElementById('div1'), document.getElementById('div2').firstChild); + assert_equals(labels.length, 0, + "The number of labels should be 0 after the labelable element is moved to outside of nested associated labels."); + }, "A labelable element is moved to outside of nested associated labels."); + + test(function () { + var labels1 = document.getElementById("test9").labels; + var labels2 = document.getElementById("test10").labels; + assert_true(labels1 instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_true(labels2 instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(labels1.length, 1, + "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); + assert_equals(labels2.length, 1, + "The number of labels associated with a form control should be the number of label elements for which it is a labeled control."); + assert_array_equals(labels1, [document.getElementById("lbl9")], + "The labels for a form control should be returned in tree order."); + assert_array_equals(labels2, [document.getElementById("lbl10")], + "The labels for a form control should be returned in tree order."); + document.getElementById('div3').insertBefore(document.getElementById('div4'), document.getElementById('div3').firstChild); + assert_equals(labels1.length, 0, + "The number of labels should be 0 if it's not the first labelable descendant of a label element."); + assert_equals(labels2.length, 2, + "The form control has an ancestor with an explicit associated label, and is the first labelable descendant."); + }, "A labelable element is moved to inside of nested associated labels."); + + test(function () { + var labels1 = document.getElementById("test11").labels; + var labels2 = document.getElementById("test12").labels; + assert_true(labels1 instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_true(labels2 instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(labels1.length, 1, + "The form control has an ancestor with no explicit associated label, and it is the first labelable descendant."); + assert_equals(labels2.length, 1, + "The number of labels should be 1 since there is a label with a 'for' attribute associated with this labelable element."); + assert_array_equals(labels1, [document.getElementById("lbl11")], + "The labels for a form control should be returned in tree order."); + assert_array_equals(labels2, [document.getElementById("lbl12")], + "The labels for a form control should be returned in tree order."); + document.getElementById('div5').appendChild(document.getElementById('obj')); + assert_equals(labels1.length, 0, + "The number of labels should be 0 after the labelable element is moved to outside of associated label."); + assert_equals(labels2.length, 1, + "The number of labels should be 1 after the labelable element is moved to outside of associated label."); + }, "A labelable element which is a descendant of non-labelable element is moved to outside of associated label."); + + async_test(function () { + var labels = document.getElementById("test13").labels; + assert_true(labels instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(labels.length, 1, + "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); + assert_array_equals(labels, [document.getElementById("lbl13")], + "The labels for a form control should be returned in tree order."); + let iframe = document.createElement('iframe'); + + iframe.onload = this.step_func_done(() => { + iframe.contentWindow.document.getElementById("div1").appendChild(document.getElementById("p1")); + assert_equals(labels.length, 2, + "The number of labels should be 2 after the labelable element is moved to iframe."); + }); + + iframe.setAttribute('src', 'http://{{domains[]}}:{{ports[http][0]}}/html/semantics/forms/the-label-element/iframe-label-attributes.html'); + document.body.appendChild(iframe); + }, "A labelable element is moved to iframe."); + + test(function () { + var test14 = document.getElementById("test14"); + var labels1 = test14.labels; + var labels2 = document.getElementById("test15").labels; + assert_true(labels1 instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(labels1.length, 1, + "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); + assert_equals(labels2.length, 1, + "The number of labels associated with a form control should be the number of label elements for which it is a labeled control."); + assert_array_equals(labels1, [document.getElementById("lbl14")], + "The labels for a form control should be returned in tree order."); + assert_array_equals(labels2, [document.getElementById("lbl15")], + "The labels for a form control should be returned in tree order."); + + document.getElementById('div6').removeChild(document.getElementById('div7')); + assert_equals(labels1.length, 1, + "The number of labels should be 1 after the labelable element is removed but label element is still in the same tree."); + assert_equals(labels2.length, 0, + "The number of labels should be 0 since there is no label with a 'for' attribute associated with this labelable element."); + test14.remove(); + assert_equals(labels1.length, 0, + "The number of labels should be 0 after the labelable element is removed."); + }, "A div element which contains labelable element is removed."); + + test(function () { + // <label><input id="test16"><label for="test16"></label></label> + var label1 = document.createElement('label'); + label1.innerHTML = "<input id='test16'>"; + var label2 = document.createElement('label'); + label2.htmlFor = "test16"; + label1.appendChild(label2); + + var input = label1.firstChild; + var labels = input.labels; + + assert_equals(labels.length, 2, + "The number of labels associated with a form control should be the number of label elements for which it is a labeled control."); + assert_true(labels instanceof NodeList, + "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(label1.control, input, "The first labelable descendant of a label element should be its labeled control."); + assert_equals(label2.control, input, "The labeled cotrol should be associated with the control whose ID is equal to the value of the 'for' attribute."); + }, "A labelable element not in a document can label element in the same tree."); + + test(function () { + var isShadowDOMV0; + if ("createShadowRoot" in document.getElementById('content')) { + isShadowDOMV0 = true; + } + var root1; + if (isShadowDOMV0) { + root1 = document.getElementById('content').createShadowRoot(); + } else { + root1 = document.getElementById('content').attachShadow({mode: 'open'}); + } + assert_true(root1 instanceof DocumentFragment, + "ShadowRoot should be an instance of DocumentFragment."); + // <label><input id="shadow1"/></label><div id="div1"></div> + var label1 = document.createElement('label'); + var input1 = document.createElement('input'); + input1.setAttribute("id", "shadow1"); + label1.appendChild(input1); + root1.appendChild(label1); + + var div1 = document.createElement('div'); + label1.appendChild(div1); + // <label for="shadow2"></label><input id="shadow2"/> + var root2; + if (isShadowDOMV0) { + root2 = div1.createShadowRoot(); + } else { + root2 = div1.attachShadow({mode: 'open'}); + } + + assert_true(root2 instanceof DocumentFragment, + "ShadowRoot should be an instance of DocumentFragment."); + var label2 = document.createElement('label'); + label2.setAttribute("for", "shadow2"); + + var input2 = document.createElement('input'); + input2.setAttribute("id", "shadow2"); + root2.appendChild(label2); + root2.appendChild(input2); + + assert_equals(root1.getElementById("shadow1").labels.length, 1, + "The form control has an ancestor with no explicit associated label, and it is the first labelable descendant."); + assert_equals(root2.getElementById("shadow2").labels.length, 1, + "The number of labels should be 1 since there is a label with a 'for' attribute associated with this labelable element."); + }, "A labelable element inside the shadow DOM."); + + test(function () { + var labels = document.getElementById("test3").labels; + assert_true(labels instanceof NodeList, "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(labels.length, 1, "The form control has an ancestor with no explicit associated label, and is the first labelable descendant."); + }, "A form control has an implicit label."); + + test(function () { + var labels = document.getElementById("test4").labels; + assert_true(labels instanceof NodeList, "A form control's 'labels' property should be an instance of a NodeList."); + assert_equals(labels.length, 0, "The form control has an ancestor with no explicit associated label, but is *not* the first labelable descendant"); + }, "A form control has no label 1."); + + test(function () { + assert_equals(document.getElementById("test5").labels.length, 0, + "The number of labels should be 0 if the form control has an ancestor label element that the for attribute points to another control."); + assert_equals(document.getElementById("lbl2").control, null, + "The labeled cotrol should be associated with the control whose ID is equal to the value of the 'for' attribute."); + }, "A form control has no label 2."); + + // form attribute + test(function () { + assert_equals(document.getElementById("lbl0").form, null, + "The 'form' property for a label should return null if label.control is null."); + }, "A label in a form without a control"); + + test(function () { + assert_equals(document.getElementById("lbl6").form, document.getElementById("fm"), + "The 'form' property for a label should return label.control.form."); + }, "A label outside a form with a control inside the form"); + + // htmlFor attribute + test(function () { + assert_equals(document.getElementById("lbl2").htmlFor, "testx"); + }, "A label's htmlFor attribute must reflect the for content attribute"); +</script>
--- a/testing/web-platform/tests/lint.whitelist +++ b/testing/web-platform/tests/lint.whitelist @@ -767,24 +767,8 @@ MISSING-LINK: css/cssom-view/scrollTop-d # TODO https://github.com/w3c/web-platform-tests/issues/5770 MISSING-LINK: css/geometry/*.worker.js MISSING-LINK: css/filter-effects/*.any.js # Tests that use WebKit/Blink testing APIs LAYOUTTESTS APIS: css/css-regions/interactivity/* LAYOUTTESTS APIS: resources/chromium/generic_sensor_mocks.js - -# Existing use of WEB-PLATFORM.TEST -WEB-PLATFORM.TEST: clear-site-data/support/test_utils.sub.js -WEB-PLATFORM.TEST: content-security-policy/base-uri/report-uri-does-not-respect-base-uri.sub.html -WEB-PLATFORM.TEST: content-security-policy/generic/generic-0_8.sub.html -WEB-PLATFORM.TEST: content-security-policy/generic/generic-0_8_1.sub.html -WEB-PLATFORM.TEST: content-security-policy/nonce-hiding/script-nonces-hidden-meta.tentative.html -WEB-PLATFORM.TEST: content-security-policy/nonce-hiding/svgscript-nonces-hidden-meta.tentative.html -WEB-PLATFORM.TEST: fetch/api/request/request-structure.html -WEB-PLATFORM.TEST: html/browsers/origin/relaxing-the-same-origin-restriction/document_domain_setter.html -WEB-PLATFORM.TEST: html/semantics/embedded-content/the-iframe-element/cross_origin_parentage.html -WEB-PLATFORM.TEST: html/semantics/forms/the-label-element/label-attributes.html -WEB-PLATFORM.TEST: navigation-timing/nav2_test_attributes_values.html -WEB-PLATFORM.TEST: navigation-timing/nav2_test_instance_accessors.html -WEB-PLATFORM.TEST: webrtc/RTCPeerConnection-getIdentityAssertion.html -WEB-PLATFORM.TEST: webrtc/identity-helper.js
--- a/testing/web-platform/tests/navigation-timing/nav2_test_attributes_values.html +++ b/testing/web-platform/tests/navigation-timing/nav2_test_attributes_values.html @@ -2,22 +2,33 @@ <html> <head> <meta charset="utf-8"> <title>Navigation Timing 2 WPT</title> <link rel="author" title="Google" href="http://www.google.com/" /> <link rel="help" href="http://www.w3.org/TR/navigation-timing-2/#sec-PerformanceNavigationTiming"/> <script src="/resources/testharness.js"></script> <script src="/resources/testharnessreport.js"></script> + <script src="/common/get-host-info.sub.js"></script> </head> <body> <h1>Description</h1> <p>This test validates that the values of nav timing 2 instance's timing-related attributes are in certain order and the others are of expected values.</p> <script> + // Host names and ports may be configured at test execution time. The + // web-platform-tests server offers two mechanisms for retrieving these + // values dynamically: direct text substitution and the `get-host-info` + // script. The former is inapproprate for this test because it + // influences the size of the document, and this test includes static + // assertions for that value. + var host_info = get_host_info(); + var expectedUrl = "http://" + host_info.ORIGINAL_HOST + ":" + + host_info.HTTP_PORT + + "/navigation-timing/nav2_test_attributes_values.html"; var navTiming2EventOrder1 = [ 'startTime', 'redirectStart', //'unloadEventStart', 'redirectEnd', //'unloadEventEnd', 'fetchStart', 'domainLookupStart', @@ -76,30 +87,30 @@ } async_test(function (t) { var observer = new PerformanceObserver( t.step_func(function (entryList) { var entries = entryList.getEntries(); assert_equals(entries[0].entryType, "navigation", "Expected entryType to be: navigation."); - assert_equals(entries[0].name, "http://web-platform.test:8001/navigation-timing/nav2_test_attributes_values.html"); + assert_equals(entries[0].name, expectedUrl); assert_equals(entries[0].startTime, 0, "Expected startTime to be: 0."); assert_equals(entries[0].duration, entries[0].loadEventEnd, "Expected duration to be equal to loadEventEnd."); assert_equals(entries[0].initiatorType, "navigation", "Expected initiatorType to be: navigation."); assert_equals(entries[0].nextHopProtocol, "http/1.1"); // This test may fail when response is from cach. Disable or clean cach before // running this test. assert_true(entries[0].transferSize > entries[0].encodedBodySize, "Expected transferSize to be greater than encodedBodySize in uncached navigation."); - assert_equals(entries[0].encodedBodySize, 5328); - assert_equals(entries[0].decodedBodySize, 5328); + assert_equals(entries[0].encodedBodySize, 5955); + assert_equals(entries[0].decodedBodySize, 5955); verifyTimingEventOrder(entries[0], navTiming2EventOrder1); // Verify if the reported timing is not that different // from what is reported by Navigation Timing 1. navTiming1EventOrder.forEach( function(event) { if (window.performance.timing[event] - window.performance.timing.navigationStart > 0) { assert_greater_than(entries[0][event], 0,
--- a/testing/web-platform/tests/navigation-timing/nav2_test_instance_accessors.html +++ b/testing/web-platform/tests/navigation-timing/nav2_test_instance_accessors.html @@ -2,22 +2,26 @@ <html> <head> <meta charset="utf-8"> <title>Navigation Timing 2 WPT</title> <link rel="author" title="Google" href="http://www.google.com/" /> <link rel="help" href="http://www.w3.org/TR/navigation-timing-2/#sec-PerformanceNavigationTiming"/> <script src="/resources/testharness.js"></script> <script src="/resources/testharnessreport.js"></script> + <script src="/common/get-host-info.sub.js"></script> </head> <body> <h1>Description</h1> <p>This test validates that nav timing 2 instance can be accessed by three different accessors once available: window.performance.getEntries()/getEntriesByType("navigation")/getEntriesByName("document")</p> <script> + var host_info = get_host_info(); + var expectedUrl = "http://" + host_info.ORIGINAL_HOST + ":" + + host_info.HTTP_PORT + "/navigation-timing/nav2_test_instance_accessors.html"; var navTiming2Attributes = [ 'connectEnd', 'connectStart', 'decodedBodySize', 'domComplete', 'domContentLoadedEventEnd', 'domContentLoadedEventStart', 'domInteractive', @@ -45,20 +49,20 @@ 'workerStart' ]; async_test(function (t) { var observer = new PerformanceObserver( t.step_func(function (entryList) { var instance1 = performance.getEntries()[0]; var instance2 = performance.getEntriesByType("navigation")[0]; - var instance3 = performance.getEntriesByName("http://web-platform.test:8001/navigation-timing/nav2_test_instance_accessors.html")[0]; + var instance3 = performance.getEntriesByName(expectedUrl)[0]; assert_equals(performance.getEntriesByType("navigation").length, 1, "Expected there is only one navigation timing instance."); - assert_equals(performance.getEntriesByName("http://web-platform.test:8001/navigation-timing/nav2_test_instance_accessors.html").length, 1, "Expected there is only one navigation timing instance."); + assert_equals(performance.getEntriesByName(expectedUrl).length, 1, "Expected there is only one navigation timing instance."); for (var i = 0; i < navTiming2Attributes.length; i++) { assert_equals(instance1[navTiming2Attributes[i]], instance2[navTiming2Attributes[i]]); } for (var i = 0; i < navTiming2Attributes.length; i++) { assert_equals(instance1[navTiming2Attributes[i]], instance3[navTiming2Attributes[i]]); }
deleted file mode 100644 --- a/testing/web-platform/tests/webrtc/RTCPeerConnection-getIdentityAssertion.html +++ /dev/null @@ -1,400 +0,0 @@ -<!doctype html> -<meta charset=utf-8> -<title>RTCPeerConnection.prototype.getIdentityAssertion</title> -<script src="/resources/testharness.js"></script> -<script src="/resources/testharnessreport.js"></script> -<script src="identity-helper.js"></script> -<script> - 'use strict'; - - // Test is based on the following editor draft: - // https://w3c.github.io/webrtc-pc/archives/20170605/webrtc.html - - // The tests here interacts with the mock identity provider located at - // /.well-known/idp-proxy/mock-idp.js - - // The following helper functions are called from identity-helper.js - // parseAssertionResult - // getIdpDomains - // assert_rtcerror_rejection - // hostString - - /* - 9.6. RTCPeerConnection Interface Extensions - partial interface RTCPeerConnection { - void setIdentityProvider(DOMString provider, - optional RTCIdentityProviderOptions options); - Promise<DOMString> getIdentityAssertion(); - readonly attribute Promise<RTCIdentityAssertion> peerIdentity; - readonly attribute DOMString? idpLoginUrl; - readonly attribute DOMString? idpErrorInfo; - }; - - dictionary RTCIdentityProviderOptions { - DOMString protocol = "default"; - DOMString usernameHint; - DOMString peerIdentity; - }; - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - const port = window.location.port; - - const [idpDomain] = getIdpDomains(); - const idpHost = hostString(idpDomain, port); - - pc.setIdentityProvider(idpHost, { - protocol: 'mock-idp.js?foo=bar', - usernameHint: `alice@${idpDomain}`, - peerIdentity: 'bob@example.org' - }); - - return pc.getIdentityAssertion() - .then(assertionResultStr => { - const { idp, assertion } = parseAssertionResult(assertionResultStr); - - assert_equals(idp.domain, idpHost, - 'Expect mock-idp.js to construct domain from its location.host'); - - assert_equals(idp.protocol, 'mock-idp.js', - 'Expect mock-idp.js to return protocol of itself with no query string'); - - const { - watermark, - args, - env, - query, - } = assertion; - - assert_equals(watermark, 'mock-idp.js.watermark', - 'Expect assertion result to contain watermark left by mock-idp.js'); - - assert_equals(args.origin, window.origin, - 'Expect args.origin argument to be the origin of this window'); - - assert_equals(env.location, - `https://${idpHost}/.well-known/idp-proxy/idp-test.js?foo=bar`, - 'Expect IdP proxy to be loaded with full well-known URL constructed from provider and protocol'); - - assert_equals(env.origin, `https://${idpHost}`, - 'Expect IdP to have its own origin'); - - assert_equals(args.options.protocol, 'idp-test.js?foo=bar', - 'Expect options.protocol to be the same value as being passed from here'); - - assert_equals(args.options.usernameHint, `alice@${idpDomain}`, - 'Expect options.usernameHint to be the same value as being passed from here'); - - assert_equals(args.options.peerIdentity, 'bob@example.org', - 'Expect options.peerIdentity to be the same value as being passed from here'); - - assert_equals(query.foo, 'bar', - 'Expect query string to be parsed by mock-idp.js and returned back'); - }); - }, 'getIdentityAssertion() should load IdP proxy and return assertion generated'); - - // When generating assertion, the RTCPeerConnection doesn't care if the returned assertion - // represents identity of different domain - promise_test(t => { - const pc = new RTCPeerConnection(); - const port = window.location.port; - - const [idpDomain1, idpDomain2] = getIdpDomains(); - assert_not_equals(idpDomain1, idpDomain2, - 'Sanity check two idpDomains are different'); - - // Ask mock-idp.js to return a custom domain idpDomain2 and custom protocol foo - pc.setIdentityProvider(hostString(idpDomain1, port), { - protocol: `mock-idp.js?generatorAction=return-custom-idp&domain=${idpDomain2}&protocol=foo`, - usernameHint: `alice@${idpDomain2}`, - }); - - return pc.getIdentityAssertion() - .then(assertionResultStr => { - const { idp, assertion } = parseAssertionResult(assertionResultStr); - assert_equals(idp.domain, idpDomain2); - assert_equals(idp.protocol, 'foo'); - assert_equals(assertion.options.usernameHint, `alice@${idpDomain2}`); - }); - }, 'getIdentityAssertion() should succeed if mock-idp.js return different domain and protocol in assertion'); - - /* - 9.3. Requesting Identity Assertions - 4. If the IdP proxy produces an error or returns a promise that does not resolve to - a valid RTCIdentityValidationResult (see 9.5 IdP Error Handling), then identity - validation fails. - - 9.5. IdP Error Handling - - If an identity provider throws an exception or returns a promise that is ultimately - rejected, then the procedure that depends on the IdP MUST also fail. These types of - errors will cause an IdP failure with an RTCError with errorDetail set to - "idp-execution-failure". - - 9.6. RTCPeerConnection Interface Extensions - idpErrorInfo - An attribute that the IdP can use to pass additional information back to the - applications about the error. The format of this string is defined by the IdP and - may be JSON. - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - - assert_equals(pc.idpErrorInfo, null, - 'Expect initial pc.idpErrorInfo to be null'); - - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - - // Ask mock-idp.js to throw an error with err.errorInfo set to bar - pc.setIdentityProvider(hostString(idpDomain, port), { - protocol: `mock-idp.js?generatorAction=throw-error&errorInfo=bar`, - usernameHint: `alice@${idpDomain}`, - }); - - return assert_rtcerror_rejection('idp-execution-failure', - pc.getIdentityAssertion()) - .then(() => { - assert_equals(pc.idpErrorInfo, 'bar', - 'Expect pc.idpErrorInfo to be set to the err.idpErrorInfo thrown by mock-idp.js'); - }); - }, `getIdentityAssertion() should reject with RTCError('idp-execution-failure') if mock-idp.js throws error`); - - /* - 9.5. IdP Error Handling - - If the script loaded from the identity provider is not valid JavaScript or does - not implement the correct interfaces, it causes an IdP failure with an RTCError - with errorDetail set to "idp-bad-script-failure". - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - - // Ask mock-idp.js to not register its callback to the - // RTCIdentityProviderRegistrar - pc.setIdentityProvider(hostString(idpDomain, port), { - protocol: `mock-idp.js?action=do-not-register`, - usernameHint: `alice@${idpDomain}`, - }); - - return assert_rtcerror_rejection('idp-bad-script-failure', - pc.getIdentityAssertion()); - - }, `getIdentityAssertion() should reject with RTCError('idp-bad-script-failure') if IdP proxy script do not register its callback`); - - /* - 9.3. Requesting Identity Assertions - 4. If the IdP proxy produces an error or returns a promise that does not resolve - to a valid RTCIdentityAssertionResult (see 9.5 IdP Error Handling), then assertion - generation fails. - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - - // Ask mock-idp.js to return an invalid result that is not proper - // RTCIdentityAssertionResult - pc.setIdentityProvider(hostString(idpDomain, port), { - protocol: `mock-idp.js?generatorAction=return-invalid-result`, - usernameHint: `alice@${idpDomain}`, - }); - - return promise_rejects(t, 'OperationError', - pc.getIdentityAssertion()); - }, `getIdentityAssertion() should reject with OperationError if mock-idp.js return invalid result`); - - /* - 9.5. IdP Error Handling - - A RTCPeerConnection might be configured with an identity provider, but loading of - the IdP URI fails. Any procedure that attempts to invoke such an identity provider - and cannot load the URI fails with an RTCError with errorDetail set to - "idp-load-failure" and the httpRequestStatusCode attribute of the error set to the - HTTP status code of the response. - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - - pc.setIdentityProvider('nonexistent.web-platform.test', { - protocol: `non-existent`, - usernameHint: `alice@example.org`, - }); - - return assert_rtcerror_rejection('idp-load-failure', - pc.getIdentityAssertion()); - }, `getIdentityAssertion() should reject with RTCError('idp-load-failure') if IdP cannot be loaded`); - - /* - 9.3.1. User Login Procedure - Rejecting the promise returned by generateAssertion will cause the error to - propagate to the application. Login errors are indicated by rejecting the - promise with an RTCError with errorDetail set to "idp-need-login". - - The URL to login at will be passed to the application in the idpLoginUrl - attribute of the RTCPeerConnection. - - 9.5. IdP Error Handling - - If the identity provider requires the user to login, the operation will fail - RTCError with errorDetail set to "idp-need-login" and the idpLoginUrl attribute - of the error set to the URL that can be used to login. - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - - assert_equals(pc.idpLoginUrl, null, - 'Expect initial pc.idpLoginUrl to be null'); - - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - const idpHost = hostString(idpDomain, port); - - pc.setIdentityProvider(idpHost, { - protocol: `mock-idp.js?generatorAction=require-login`, - usernameHint: `alice@${idpDomain}`, - }); - - return assert_rtcerror_rejection('idp-need-login', - pc.getIdentityAssertion()) - .then(err => { - assert_equals(err.idpLoginUrl, `https://${idpHost}/login`, - 'Expect err.idpLoginUrl to be set to url set by mock-idp.js'); - - assert_equals(pc.idpLoginUrl, `https://${idpHost}/login`, - 'Expect pc.idpLoginUrl to be set to url set by mock-idp.js'); - - assert_equals(pc.idpErrorInfo, 'login required', - 'Expect pc.idpErrorInfo to be set to info set by mock-idp.js'); - }); - }, `getIdentityAssertion() should reject with RTCError('idp-need-login') when mock-idp.js requires login`); - - /* - RTCIdentityProviderOptions Members - peerIdentity - The identity of the peer. For identity providers that bind their assertions to a - particular pair of communication peers, this allows them to generate an assertion - that includes both local and remote identities. If this value is omitted, but a - value is provided for the peerIdentity member of RTCConfiguration, the value from - RTCConfiguration is used. - */ - promise_test(t => { - const pc = new RTCPeerConnection({ - peerIdentity: 'bob@example.net' - }); - - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - const idpHost = hostString(idpDomain, port); - - pc.setIdentityProvider(idpHost, { - protocol: 'mock-idp.js' - }); - - return pc.getIdentityAssertion() - .then(assertionResultStr => { - const { assertion } = parseAssertionResult(assertionResultStr); - assert_equals(assertion.args.options.peerIdentity, 'bob@example.net'); - }); - }, 'setIdentityProvider() with no peerIdentity provided should use peerIdentity value from getConfiguration()'); - - /* - 9.6. setIdentityProvider - 3. If any identity provider value has changed, discard any stored identity assertion. - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - const idpHost = hostString(idpDomain, port); - - pc.setIdentityProvider(idpHost, { - protocol: 'mock-idp.js?mark=first' - }); - - return pc.getIdentityAssertion() - .then(assertionResultStr => { - const { assertion } = parseAssertionResult(assertionResultStr); - assert_equals(assertion.query.mark, 'first'); - - pc.setIdentityProvider(idpHost, { - protocol: 'mock-idp.js?mark=second' - }); - - return pc.getIdentityAssertion(); - }) - .then(assertionResultStr => { - const { assertion } = parseAssertionResult(assertionResultStr); - assert_equals(assertion.query.mark, 'second', - 'Expect generated assertion is from second IdP config'); - }); - }, `Calling setIdentityProvider() multiple times should reset identity assertions`); - - promise_test(t => { - const pc = new RTCPeerConnection(); - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - - pc.setIdentityProvider(hostString(idpDomain, port), { - protocol: 'mock-idp.js', - usernameHint: `alice@${idpDomain}` - }); - - return pc.getIdentityAssertion() - .then(assertionResultStr => - pc.createOffer() - .then(offer => { - assert_true(offer.sdp.includes(`\r\na=identity:${assertionResultStr}`, - 'Expect SDP to have a=identity line containing assertion string')); - })); - }, 'createOffer() should return SDP containing identity assertion string if identity provider is set'); - - /* - 4.4.2. Steps to create an offer - 1. If the need for an identity assertion was identified when createOffer was - invoked, wait for the identity assertion request process to complete. - 2. If the identity provider was unable to produce an identity assertion, reject p - with a newly created NotReadableError and abort these steps. - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - - pc.setIdentityProvider(hostString(idpDomain, port), { - protocol: 'mock-idp.js?generatorAction=throw-error', - usernameHint: `alice@${idpDomain}` - }); - - return promise_rejects(t, 'NotReadableError', - pc.createOffer()); - }, 'createOffer() should reject with NotReadableError if identitity assertion request fails'); - - /* - 4.4.2. Steps to create an answer - 1. If the need for an identity assertion was identified when createAnswer was - invoked, wait for the identity assertion request process to complete. - - 2. If the identity provider was unable to produce an identity assertion, reject p - with a newly created NotReadableError and abort these steps. - */ - promise_test(t => { - const pc = new RTCPeerConnection(); - const port = window.location.port; - const [idpDomain] = getIdpDomains(); - - pc.setIdentityProvider(hostString(idpDomain, port), { - protocol: 'mock-idp.js?generatorAction=throw-error', - usernameHint: `alice@${idpDomain}` - }); - - return new RTCPeerConnection() - .createOffer() - .then(offer => pc.setRemoteDescription(offer)) - .then(() => - promise_rejects(t, 'NotReadableError', - pc.createAnswer())); - - }, 'createAnswer() should reject with NotReadableError if identitity assertion request fails'); - -</script>
new file mode 100644 --- /dev/null +++ b/testing/web-platform/tests/webrtc/RTCPeerConnection-getIdentityAssertion.sub.html @@ -0,0 +1,400 @@ +<!doctype html> +<meta charset=utf-8> +<title>RTCPeerConnection.prototype.getIdentityAssertion</title> +<script src="/resources/testharness.js"></script> +<script src="/resources/testharnessreport.js"></script> +<script src="identity-helper.sub.js"></script> +<script> + 'use strict'; + + // Test is based on the following editor draft: + // https://w3c.github.io/webrtc-pc/archives/20170605/webrtc.html + + // The tests here interacts with the mock identity provider located at + // /.well-known/idp-proxy/mock-idp.js + + // The following helper functions are called from identity-helper.sub.js + // parseAssertionResult + // getIdpDomains + // assert_rtcerror_rejection + // hostString + + /* + 9.6. RTCPeerConnection Interface Extensions + partial interface RTCPeerConnection { + void setIdentityProvider(DOMString provider, + optional RTCIdentityProviderOptions options); + Promise<DOMString> getIdentityAssertion(); + readonly attribute Promise<RTCIdentityAssertion> peerIdentity; + readonly attribute DOMString? idpLoginUrl; + readonly attribute DOMString? idpErrorInfo; + }; + + dictionary RTCIdentityProviderOptions { + DOMString protocol = "default"; + DOMString usernameHint; + DOMString peerIdentity; + }; + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + const port = window.location.port; + + const [idpDomain] = getIdpDomains(); + const idpHost = hostString(idpDomain, port); + + pc.setIdentityProvider(idpHost, { + protocol: 'mock-idp.js?foo=bar', + usernameHint: `alice@${idpDomain}`, + peerIdentity: 'bob@example.org' + }); + + return pc.getIdentityAssertion() + .then(assertionResultStr => { + const { idp, assertion } = parseAssertionResult(assertionResultStr); + + assert_equals(idp.domain, idpHost, + 'Expect mock-idp.js to construct domain from its location.host'); + + assert_equals(idp.protocol, 'mock-idp.js', + 'Expect mock-idp.js to return protocol of itself with no query string'); + + const { + watermark, + args, + env, + query, + } = assertion; + + assert_equals(watermark, 'mock-idp.js.watermark', + 'Expect assertion result to contain watermark left by mock-idp.js'); + + assert_equals(args.origin, window.origin, + 'Expect args.origin argument to be the origin of this window'); + + assert_equals(env.location, + `https://${idpHost}/.well-known/idp-proxy/idp-test.js?foo=bar`, + 'Expect IdP proxy to be loaded with full well-known URL constructed from provider and protocol'); + + assert_equals(env.origin, `https://${idpHost}`, + 'Expect IdP to have its own origin'); + + assert_equals(args.options.protocol, 'idp-test.js?foo=bar', + 'Expect options.protocol to be the same value as being passed from here'); + + assert_equals(args.options.usernameHint, `alice@${idpDomain}`, + 'Expect options.usernameHint to be the same value as being passed from here'); + + assert_equals(args.options.peerIdentity, 'bob@example.org', + 'Expect options.peerIdentity to be the same value as being passed from here'); + + assert_equals(query.foo, 'bar', + 'Expect query string to be parsed by mock-idp.js and returned back'); + }); + }, 'getIdentityAssertion() should load IdP proxy and return assertion generated'); + + // When generating assertion, the RTCPeerConnection doesn't care if the returned assertion + // represents identity of different domain + promise_test(t => { + const pc = new RTCPeerConnection(); + const port = window.location.port; + + const [idpDomain1, idpDomain2] = getIdpDomains(); + assert_not_equals(idpDomain1, idpDomain2, + 'Sanity check two idpDomains are different'); + + // Ask mock-idp.js to return a custom domain idpDomain2 and custom protocol foo + pc.setIdentityProvider(hostString(idpDomain1, port), { + protocol: `mock-idp.js?generatorAction=return-custom-idp&domain=${idpDomain2}&protocol=foo`, + usernameHint: `alice@${idpDomain2}`, + }); + + return pc.getIdentityAssertion() + .then(assertionResultStr => { + const { idp, assertion } = parseAssertionResult(assertionResultStr); + assert_equals(idp.domain, idpDomain2); + assert_equals(idp.protocol, 'foo'); + assert_equals(assertion.options.usernameHint, `alice@${idpDomain2}`); + }); + }, 'getIdentityAssertion() should succeed if mock-idp.js return different domain and protocol in assertion'); + + /* + 9.3. Requesting Identity Assertions + 4. If the IdP proxy produces an error or returns a promise that does not resolve to + a valid RTCIdentityValidationResult (see 9.5 IdP Error Handling), then identity + validation fails. + + 9.5. IdP Error Handling + - If an identity provider throws an exception or returns a promise that is ultimately + rejected, then the procedure that depends on the IdP MUST also fail. These types of + errors will cause an IdP failure with an RTCError with errorDetail set to + "idp-execution-failure". + + 9.6. RTCPeerConnection Interface Extensions + idpErrorInfo + An attribute that the IdP can use to pass additional information back to the + applications about the error. The format of this string is defined by the IdP and + may be JSON. + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + + assert_equals(pc.idpErrorInfo, null, + 'Expect initial pc.idpErrorInfo to be null'); + + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + + // Ask mock-idp.js to throw an error with err.errorInfo set to bar + pc.setIdentityProvider(hostString(idpDomain, port), { + protocol: `mock-idp.js?generatorAction=throw-error&errorInfo=bar`, + usernameHint: `alice@${idpDomain}`, + }); + + return assert_rtcerror_rejection('idp-execution-failure', + pc.getIdentityAssertion()) + .then(() => { + assert_equals(pc.idpErrorInfo, 'bar', + 'Expect pc.idpErrorInfo to be set to the err.idpErrorInfo thrown by mock-idp.js'); + }); + }, `getIdentityAssertion() should reject with RTCError('idp-execution-failure') if mock-idp.js throws error`); + + /* + 9.5. IdP Error Handling + - If the script loaded from the identity provider is not valid JavaScript or does + not implement the correct interfaces, it causes an IdP failure with an RTCError + with errorDetail set to "idp-bad-script-failure". + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + + // Ask mock-idp.js to not register its callback to the + // RTCIdentityProviderRegistrar + pc.setIdentityProvider(hostString(idpDomain, port), { + protocol: `mock-idp.js?action=do-not-register`, + usernameHint: `alice@${idpDomain}`, + }); + + return assert_rtcerror_rejection('idp-bad-script-failure', + pc.getIdentityAssertion()); + + }, `getIdentityAssertion() should reject with RTCError('idp-bad-script-failure') if IdP proxy script do not register its callback`); + + /* + 9.3. Requesting Identity Assertions + 4. If the IdP proxy produces an error or returns a promise that does not resolve + to a valid RTCIdentityAssertionResult (see 9.5 IdP Error Handling), then assertion + generation fails. + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + + // Ask mock-idp.js to return an invalid result that is not proper + // RTCIdentityAssertionResult + pc.setIdentityProvider(hostString(idpDomain, port), { + protocol: `mock-idp.js?generatorAction=return-invalid-result`, + usernameHint: `alice@${idpDomain}`, + }); + + return promise_rejects(t, 'OperationError', + pc.getIdentityAssertion()); + }, `getIdentityAssertion() should reject with OperationError if mock-idp.js return invalid result`); + + /* + 9.5. IdP Error Handling + - A RTCPeerConnection might be configured with an identity provider, but loading of + the IdP URI fails. Any procedure that attempts to invoke such an identity provider + and cannot load the URI fails with an RTCError with errorDetail set to + "idp-load-failure" and the httpRequestStatusCode attribute of the error set to the + HTTP status code of the response. + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + + pc.setIdentityProvider('nonexistent.{{domains[]}}', { + protocol: `non-existent`, + usernameHint: `alice@example.org`, + }); + + return assert_rtcerror_rejection('idp-load-failure', + pc.getIdentityAssertion()); + }, `getIdentityAssertion() should reject with RTCError('idp-load-failure') if IdP cannot be loaded`); + + /* + 9.3.1. User Login Procedure + Rejecting the promise returned by generateAssertion will cause the error to + propagate to the application. Login errors are indicated by rejecting the + promise with an RTCError with errorDetail set to "idp-need-login". + + The URL to login at will be passed to the application in the idpLoginUrl + attribute of the RTCPeerConnection. + + 9.5. IdP Error Handling + - If the identity provider requires the user to login, the operation will fail + RTCError with errorDetail set to "idp-need-login" and the idpLoginUrl attribute + of the error set to the URL that can be used to login. + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + + assert_equals(pc.idpLoginUrl, null, + 'Expect initial pc.idpLoginUrl to be null'); + + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + const idpHost = hostString(idpDomain, port); + + pc.setIdentityProvider(idpHost, { + protocol: `mock-idp.js?generatorAction=require-login`, + usernameHint: `alice@${idpDomain}`, + }); + + return assert_rtcerror_rejection('idp-need-login', + pc.getIdentityAssertion()) + .then(err => { + assert_equals(err.idpLoginUrl, `https://${idpHost}/login`, + 'Expect err.idpLoginUrl to be set to url set by mock-idp.js'); + + assert_equals(pc.idpLoginUrl, `https://${idpHost}/login`, + 'Expect pc.idpLoginUrl to be set to url set by mock-idp.js'); + + assert_equals(pc.idpErrorInfo, 'login required', + 'Expect pc.idpErrorInfo to be set to info set by mock-idp.js'); + }); + }, `getIdentityAssertion() should reject with RTCError('idp-need-login') when mock-idp.js requires login`); + + /* + RTCIdentityProviderOptions Members + peerIdentity + The identity of the peer. For identity providers that bind their assertions to a + particular pair of communication peers, this allows them to generate an assertion + that includes both local and remote identities. If this value is omitted, but a + value is provided for the peerIdentity member of RTCConfiguration, the value from + RTCConfiguration is used. + */ + promise_test(t => { + const pc = new RTCPeerConnection({ + peerIdentity: 'bob@example.net' + }); + + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + const idpHost = hostString(idpDomain, port); + + pc.setIdentityProvider(idpHost, { + protocol: 'mock-idp.js' + }); + + return pc.getIdentityAssertion() + .then(assertionResultStr => { + const { assertion } = parseAssertionResult(assertionResultStr); + assert_equals(assertion.args.options.peerIdentity, 'bob@example.net'); + }); + }, 'setIdentityProvider() with no peerIdentity provided should use peerIdentity value from getConfiguration()'); + + /* + 9.6. setIdentityProvider + 3. If any identity provider value has changed, discard any stored identity assertion. + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + const idpHost = hostString(idpDomain, port); + + pc.setIdentityProvider(idpHost, { + protocol: 'mock-idp.js?mark=first' + }); + + return pc.getIdentityAssertion() + .then(assertionResultStr => { + const { assertion } = parseAssertionResult(assertionResultStr); + assert_equals(assertion.query.mark, 'first'); + + pc.setIdentityProvider(idpHost, { + protocol: 'mock-idp.js?mark=second' + }); + + return pc.getIdentityAssertion(); + }) + .then(assertionResultStr => { + const { assertion } = parseAssertionResult(assertionResultStr); + assert_equals(assertion.query.mark, 'second', + 'Expect generated assertion is from second IdP config'); + }); + }, `Calling setIdentityProvider() multiple times should reset identity assertions`); + + promise_test(t => { + const pc = new RTCPeerConnection(); + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + + pc.setIdentityProvider(hostString(idpDomain, port), { + protocol: 'mock-idp.js', + usernameHint: `alice@${idpDomain}` + }); + + return pc.getIdentityAssertion() + .then(assertionResultStr => + pc.createOffer() + .then(offer => { + assert_true(offer.sdp.includes(`\r\na=identity:${assertionResultStr}`, + 'Expect SDP to have a=identity line containing assertion string')); + })); + }, 'createOffer() should return SDP containing identity assertion string if identity provider is set'); + + /* + 4.4.2. Steps to create an offer + 1. If the need for an identity assertion was identified when createOffer was + invoked, wait for the identity assertion request process to complete. + 2. If the identity provider was unable to produce an identity assertion, reject p + with a newly created NotReadableError and abort these steps. + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + + pc.setIdentityProvider(hostString(idpDomain, port), { + protocol: 'mock-idp.js?generatorAction=throw-error', + usernameHint: `alice@${idpDomain}` + }); + + return promise_rejects(t, 'NotReadableError', + pc.createOffer()); + }, 'createOffer() should reject with NotReadableError if identitity assertion request fails'); + + /* + 4.4.2. Steps to create an answer + 1. If the need for an identity assertion was identified when createAnswer was + invoked, wait for the identity assertion request process to complete. + + 2. If the identity provider was unable to produce an identity assertion, reject p + with a newly created NotReadableError and abort these steps. + */ + promise_test(t => { + const pc = new RTCPeerConnection(); + const port = window.location.port; + const [idpDomain] = getIdpDomains(); + + pc.setIdentityProvider(hostString(idpDomain, port), { + protocol: 'mock-idp.js?generatorAction=throw-error', + usernameHint: `alice@${idpDomain}` + }); + + return new RTCPeerConnection() + .createOffer() + .then(offer => pc.setRemoteDescription(offer)) + .then(() => + promise_rejects(t, 'NotReadableError', + pc.createAnswer())); + + }, 'createAnswer() should reject with NotReadableError if identitity assertion request fails'); + +</script>
--- a/testing/web-platform/tests/webrtc/RTCPeerConnection-peerIdentity.html +++ b/testing/web-platform/tests/webrtc/RTCPeerConnection-peerIdentity.html @@ -1,24 +1,24 @@ <!doctype html> <meta charset=utf-8> <title>RTCPeerConnection.prototype.peerIdentity</title> <script src="/resources/testharness.js"></script> <script src="/resources/testharnessreport.js"></script> -<script src="identity-helper.js"></script> +<script src="identity-helper.sub.js"></script> <script> 'use strict'; // Test is based on the following editor draft: // https://w3c.github.io/webrtc-pc/archives/20170605/webrtc.html // The tests here interacts with the mock identity provider located at // /.well-known/idp-proxy/mock-idp.js - // The following helper functions are called from identity-helper.js + // The following helper functions are called from identity-helper.sub.js // parseAssertionResult // getIdpDomains // assert_rtcerror_rejection // hostString /* 9.6. RTCPeerConnection Interface Extensions partial interface RTCPeerConnection {
deleted file mode 100644 --- a/testing/web-platform/tests/webrtc/identity-helper.js +++ /dev/null @@ -1,70 +0,0 @@ -'use strict'; - -/* - In web-platform-test, the following domains are required to be set up locally: - 127.0.0.1 web-platform.test - 127.0.0.1 www.web-platform.test - 127.0.0.1 www1.web-platform.test - 127.0.0.1 www2.web-platform.test - 127.0.0.1 xn--n8j6ds53lwwkrqhv28a.web-platform.test - 127.0.0.1 xn--lve-6lad.web-platform.test - 0.0.0.0 nonexistent.web-platform.test - */ - -/* - dictionary RTCIdentityProviderDetails { - required DOMString domain; - DOMString protocol = "default"; - }; - */ - -// Parse a base64 JSON encoded string returned from getIdentityAssertion(). -// This is also the string that is set in the a=identity line. -// Returns a { idp, assertion } where idp is of type RTCIdentityProviderDetails -// and assertion is the deserialized JSON that was returned by the -// IdP proxy's generateAssertion() function. -function parseAssertionResult(assertionResultStr) { - const assertionResult = JSON.parse(atob(assertionResultStr)); - - const { idp } = assertionResult; - const assertion = JSON.parse(assertionResult.assertion); - - return { idp, assertion }; -} - -// Return two distinct IdP domains that are different from current domain -function getIdpDomains() { - if(window.location.hostname === 'www1.web-platform.test') { - return ['www.web-platform.test', 'www2.web-platform.test']; - } else if(window.location.hostname === 'www2.web-platform.test') { - return ['www.web-platform.test', 'www1.web-platform.test']; - } else { - return ['www1.web-platform.test', 'www2.web-platform.test']; - } -} - -function assert_rtcerror_rejection(errorDetail, promise, desc) { - return promise.then( - res => { - assert_unreached(`Expect promise to be rejected with RTCError, but instead got ${res}`); - }, err => { - assert_true(err instanceof RTCError, - 'Expect error object to be instance of RTCError'); - - assert_equals(err.errorDetail, errorDetail, - `Expect RTCError object have errorDetail set to ${errorDetail}`); - - return err; - }); -} - -// construct a host string consist of domain and optionally port -// If the default HTTP/HTTPS port is used, window.location.port returns -// empty string. -function hostString(domain, port) { - if(port === '') { - return domain; - } else { - return `${domain}:${port}`; - } -}
new file mode 100644 --- /dev/null +++ b/testing/web-platform/tests/webrtc/identity-helper.sub.js @@ -0,0 +1,70 @@ +'use strict'; + +/* + In web-platform-test, a number of domains are required to be set up locally. + The list is available at docs/_writing-tests/server-features.md. The + appropriate hosts file entries can be generated with the WPT CLI via the + following command: `wpt make-hosts-file`. + */ + +/* + dictionary RTCIdentityProviderDetails { + required DOMString domain; + DOMString protocol = "default"; + }; + */ + +// Parse a base64 JSON encoded string returned from getIdentityAssertion(). +// This is also the string that is set in the a=identity line. +// Returns a { idp, assertion } where idp is of type RTCIdentityProviderDetails +// and assertion is the deserialized JSON that was returned by the +// IdP proxy's generateAssertion() function. +function parseAssertionResult(assertionResultStr) { + const assertionResult = JSON.parse(atob(assertionResultStr)); + + const { idp } = assertionResult; + const assertion = JSON.parse(assertionResult.assertion); + + return { idp, assertion }; +} + +// Return two distinct IdP domains that are different from current domain +function getIdpDomains() { + const domainA = '{{domains[www]}}'; + const domainB = '{{domains[www1]}}'; + const domainC = '{{domains[www2]}}'; + + if(window.location.hostname === domainA) { + return [domainB, domainC]; + } else if(window.location.hostname === domainB) { + return [domainA, domainC]; + } else { + return [domainA, domainB]; + } +} + +function assert_rtcerror_rejection(errorDetail, promise, desc) { + return promise.then( + res => { + assert_unreached(`Expect promise to be rejected with RTCError, but instead got ${res}`); + }, err => { + assert_true(err instanceof RTCError, + 'Expect error object to be instance of RTCError'); + + assert_equals(err.errorDetail, errorDetail, + `Expect RTCError object have errorDetail set to ${errorDetail}`); + + return err; + }); +} + +// construct a host string consist of domain and optionally port +// If the default HTTP/HTTPS port is used, window.location.port returns +// empty string. +function hostString(domain, port) { + if(port === '') { + return domain; + } else { + return `${domain}:${port}`; + } +}
--- a/testing/web-platform/tests/webrtc/tools/.eslintrc.js +++ b/testing/web-platform/tests/webrtc/tools/.eslintrc.js @@ -67,17 +67,17 @@ module.exports = { assert_optional_int_field: true, assert_optional_string_field: true, assert_optional_number_field: true, assert_optional_boolean_field: true, assert_optional_array_field: true, assert_optional_dict_field: true, assert_optional_enum_field: true, - // identity-helper.js + // identity-helper.sub.js parseAssertionResult: true, getIdpDomains: true, assert_rtcerror_rejection: true, hostString: true, // RTCConfiguration-helper.js config_test: true,