From 43a97878ce14b72f0981164f87f2e35e14151312 Mon Sep 17 00:00:00 2001 From: Daniel Baumann Date: Sun, 7 Apr 2024 11:22:09 +0200 Subject: Adding upstream version 110.0.1. Signed-off-by: Daniel Baumann --- .../web-platform/tests/compute-pressure/README.md | 2 + ...ompute_pressure_basic.tentative.https.window.js | 9 ++ ..._pressure_basic_async.tentative.https.window.js | 88 ++++++++++++++ ...e_pressure_detached_iframe.tentative.https.html | 97 +++++++++++++++ ...e_pressure_disconnect.tentative.https.window.js | 40 +++++++ ...disconnect_idempotent.tentative.https.window.js | 33 ++++++ ...isconnect_immediately.tentative.https.window.js | 63 ++++++++++ ...ure_duplicate_updates.tentative.https.window.js | 61 ++++++++++ ...pute_pressure_factors.tentative.https.window.js | 18 +++ ...ute_pressure_multiple.tentative.https.window.js | 30 +++++ ...ltiple_across_iframes.tentative.https.window.js | 40 +++++++ ...re_observe_idempotent.tentative.https.window.js | 16 +++ ...rve_unobserve_failure.tentative.https.window.js | 17 +++ ...pute_pressure_options.tentative.https.window.js | 23 ++++ ...pressure_privacy_test.tentative.https.window.js | 130 +++++++++++++++++++++ ...ure_supported_sources.tentative.https.window.js | 19 +++ ...pressure_take_records.tentative.https.window.js | 29 +++++ ...te_pressure_timestamp.tentative.https.window.js | 77 ++++++++++++ .../compute-pressure/idlharness.https.window.js | 14 +++ ...ns-policy-attribute-redirect-on-load.https.html | 39 +++++++ ...owed-by-permissions-policy-attribute.https.html | 37 ++++++ ...essure-allowed-by-permissions-policy.https.html | 55 +++++++++ ...llowed-by-permissions-policy.https.html.headers | 1 + ...on-self-origin-by-permissions-policy.https.html | 44 +++++++ ...origin-by-permissions-policy.https.html.headers | 1 + ...-pressure-default-permissions-policy.https.html | 34 ++++++ ...ssure-disabled-by-permissions-policy.https.html | 62 ++++++++++ ...sabled-by-permissions-policy.https.html.headers | 1 + ...e-pressure-supported-by-permissions-policy.html | 11 ++ .../compute-pressure/resources/pressure-helpers.js | 35 ++++++ .../compute-pressure/resources/support-iframe.html | 30 +++++ 31 files changed, 1156 insertions(+) create mode 100644 testing/web-platform/tests/compute-pressure/README.md create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_basic.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_basic_async.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_detached_iframe.tentative.https.html create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_disconnect.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_disconnect_idempotent.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_disconnect_immediately.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_duplicate_updates.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_factors.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_multiple.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_multiple_across_iframes.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_observe_idempotent.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_observe_unobserve_failure.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_options.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_privacy_test.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_supported_sources.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_take_records.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/compute_pressure_timestamp.tentative.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/idlharness.https.window.js create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy-attribute-redirect-on-load.https.html create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy-attribute.https.html create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy.https.html create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy.https.html.headers create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-on-self-origin-by-permissions-policy.https.html create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-on-self-origin-by-permissions-policy.https.html.headers create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-default-permissions-policy.https.html create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-disabled-by-permissions-policy.https.html create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-disabled-by-permissions-policy.https.html.headers create mode 100644 testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-supported-by-permissions-policy.html create mode 100644 testing/web-platform/tests/compute-pressure/resources/pressure-helpers.js create mode 100644 testing/web-platform/tests/compute-pressure/resources/support-iframe.html (limited to 'testing/web-platform/tests/compute-pressure') diff --git a/testing/web-platform/tests/compute-pressure/README.md b/testing/web-platform/tests/compute-pressure/README.md new file mode 100644 index 0000000000..05bacb7f16 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/README.md @@ -0,0 +1,2 @@ +This directory contains (tentative) tests for the +[Compute Pressure](https://wicg.github.io/compute-pressure/) specification. diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_basic.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_basic.tentative.https.window.js new file mode 100644 index 0000000000..2f463e502b --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_basic.tentative.https.window.js @@ -0,0 +1,9 @@ +'use strict'; + +promise_test(async t => { + await new Promise((resolve, reject) => { + const observer = new PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + observer.observe('cpu').catch(reject); + }); +}, 'An active PressureObserver calls its callback at least once'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_basic_async.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_basic_async.tentative.https.window.js new file mode 100644 index 0000000000..3a9a32dedc --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_basic_async.tentative.https.window.js @@ -0,0 +1,88 @@ +// META: timeout=long +// META: script=/resources/test-only-api.js +// META: script=resources/pressure-helpers.js + +'use strict'; + +pressure_test((t, mockPressureService) => { + const observer = new PressureObserver(() => { + assert_unreached('The observer callback should not be called'); + }); + + mockPressureService.setExpectedFailure( + new DOMException('', 'NotSupportedError')); + return promise_rejects_dom(t, 'NotSupportedError', observer.observe('cpu')); +}, 'Return NotSupportedError when calling observer()'); + +pressure_test(async (t, mockPressureService) => { + const changes = await new Promise(resolve => { + const observer = new PressureObserver(resolve); + observer.observe('cpu'); + mockPressureService.setPressureUpdate('critical'); + mockPressureService.startPlatformCollector(/*sampleRate=*/ 1.0); + }); + assert_true(changes.length === 1); + assert_equals(changes[0].state, 'critical'); + assert_equals(changes[0].source, 'cpu'); + assert_equals(typeof changes[0].time, 'number'); +}, 'Basic functionality test'); + +pressure_test((t, mockPressureService) => { + const observer = new PressureObserver(() => { + assert_unreached('The observer callback should not be called'); + }); + + const promise = observer.observe('cpu'); + observer.unobserve('cpu'); + mockPressureService.setPressureUpdate('critical'); + mockPressureService.startPlatformCollector(/*sampleRate=*/ 1.0); + + return promise_rejects_dom(t, 'NotSupportedError', promise); +}, 'Removing observer before observe() resolves works'); + +pressure_test(async (t, mockPressureService) => { + const callbackPromises = []; + const observePromises = []; + + for (let i = 0; i < 2; i++) { + callbackPromises.push(new Promise(resolve => { + const observer = new PressureObserver(resolve); + observePromises.push(observer.observe('cpu')); + })); + } + + await Promise.all(observePromises); + + mockPressureService.setPressureUpdate('critical'); + mockPressureService.startPlatformCollector(/*sampleRate=*/ 1.0); + + return Promise.all(callbackPromises); +}, 'Calling observe() multiple times works'); + +pressure_test(async (t, mockPressureService) => { + const observer1_changes = []; + await new Promise(resolve => { + const observer1 = new PressureObserver(changes => { + observer1_changes.push(changes); + resolve(); + }); + t.add_cleanup(() => observer1.disconnect()); + observer1.observe('cpu'); + mockPressureService.setPressureUpdate('critical'); + mockPressureService.startPlatformCollector(/*sampleRate=*/ 1.0); + }); + assert_true(observer1_changes.length === 1); + assert_equals(observer1_changes[0][0].state, 'critical'); + + const observer2_changes = []; + await new Promise(resolve => { + const observer2 = new PressureObserver(changes => { + observer2_changes.push(changes); + resolve(); + }); + t.add_cleanup(() => observer2.disconnect()); + observer2.observe('cpu'); + }); + assert_true(observer2_changes.length === 1); + assert_equals(observer2_changes[0][0].state, 'critical'); +}, 'Starting a new observer after an observer has started works'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_detached_iframe.tentative.https.html b/testing/web-platform/tests/compute-pressure/compute_pressure_detached_iframe.tentative.https.html new file mode 100644 index 0000000000..3b0a5504e5 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_detached_iframe.tentative.https.html @@ -0,0 +1,97 @@ + + +PressureObserver on DOMWindow of detached iframe + + + + + diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect.tentative.https.window.js new file mode 100644 index 0000000000..c9950f2dc8 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect.tentative.https.window.js @@ -0,0 +1,40 @@ +'use strict'; + +test(t => { + const observer = new PressureObserver(() => { + assert_unreached('The observer callback should not be called'); + }); + t.add_cleanup(() => observer.disconnect()); + observer.disconnect(); +}, 'Call disconnect() directly should not crash'); + +promise_test(async t => { + const observer1_changes = []; + const observer1 = new PressureObserver(change => { + observer1_changes.push(change); + }, {sampleRate: 1.0}); + t.add_cleanup(() => observer1.disconnect()); + // Ensure that observer1's schema gets registered before observer2 starts. + await observer1.observe('cpu'); + observer1.disconnect(); + + const observer2_changes = []; + await new Promise((resolve, reject) => { + const observer2 = new PressureObserver(change => { + observer2_changes.push(change); + resolve(); + }, {sampleRate: 1.0}); + t.add_cleanup(() => observer2.disconnect()); + observer2.observe('cpu').catch(reject); + }); + + assert_equals( + observer1_changes.length, 0, + 'disconnected observers should not receive callbacks'); + + assert_equals(observer2_changes.length, 1); + assert_equals(observer2_changes[0].length, 1); + assert_in_array( + observer2_changes[0][0].state, ['nominal', 'fair', 'serious', 'critical'], + 'cpu pressure state'); +}, 'Stopped PressureObserver do not receive changes'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect_idempotent.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect_idempotent.tentative.https.window.js new file mode 100644 index 0000000000..72021fd270 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect_idempotent.tentative.https.window.js @@ -0,0 +1,33 @@ +'use strict'; + +promise_test(async t => { + const observer1_changes = []; + const observer1 = new PressureObserver(changes => { + observer1_changes.push(changes); + }, {sampleRate: 1}); + t.add_cleanup(() => observer1.disconnect()); + // Ensure that observer1's schema gets registered before observer2 starts. + const promise = observer1.observe('cpu'); + observer1.disconnect(); + observer1.disconnect(); + await promise_rejects_dom(t, 'NotSupportedError', promise); + + const observer2_changes = []; + await new Promise((resolve, reject) => { + const observer2 = new PressureObserver(changes => { + observer2_changes.push(changes); + resolve(); + }, {sampleRate: 1}); + t.add_cleanup(() => observer2.disconnect()); + observer2.observe('cpu').catch(reject); + }); + + assert_equals( + observer1_changes.length, 0, + 'stopped observers should not receive callbacks'); + + assert_equals(observer2_changes.length, 1); + assert_in_array( + observer2_changes[0][0].state, ['nominal', 'fair', 'serious', 'critical'], + 'cpu pressure state'); +}, 'Stopped PressureObserver do not receive changes'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect_immediately.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect_immediately.tentative.https.window.js new file mode 100644 index 0000000000..1abe84d572 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_disconnect_immediately.tentative.https.window.js @@ -0,0 +1,63 @@ +'use strict'; + +promise_test(async t => { + const observer1_changes = []; + const observer1 = new PressureObserver(changes => { + observer1_changes.push(changes); + }, {sampleRate: 1.0}); + t.add_cleanup(() => observer1.disconnect()); + // Ensure that observer1's schema gets registered before observer2 starts. + const promise = observer1.observe('cpu'); + observer1.disconnect(); + await promise_rejects_dom(t, 'NotSupportedError', promise); + + const observer2_changes = []; + await new Promise((resolve, reject) => { + const observer2 = new PressureObserver(changes => { + observer2_changes.push(changes); + resolve(); + }, {sampleRate: 1.0}); + t.add_cleanup(() => observer2.disconnect()); + observer2.observe('cpu').catch(reject); + }); + + assert_equals( + observer1_changes.length, 0, + 'stopped observers should not receive callbacks'); + + assert_equals(observer2_changes.length, 1); + assert_equals(observer2_changes[0].length, 1); + assert_in_array( + observer2_changes[0][0].state, ['nominal', 'fair', 'serious', 'critical'], + 'cpu pressure state'); +}, 'Stopped PressureObserver do not receive changes'); + +promise_test(async t => { + const observer1_changes = []; + const observer1 = new PressureObserver(changes => { + observer1_changes.push(changes); + }, {sampleRate: 1}); + t.add_cleanup(() => observer1.disconnect()); + + const observer2_changes = []; + await new Promise(async resolve => { + const observer2 = new PressureObserver(changes => { + observer2_changes.push(changes); + resolve(); + }, {sampleRate: 1}); + t.add_cleanup(() => observer2.disconnect()); + const promise = observer1.observe('cpu'); + observer2.observe('cpu'); + observer1.disconnect(); + await promise_rejects_dom(t, 'NotSupportedError', promise); + }); + + assert_equals( + observer1_changes.length, 0, + 'stopped observers should not receive callbacks'); + + assert_equals(observer2_changes.length, 1); + assert_in_array( + observer2_changes[0][0].state, ['nominal', 'fair', 'serious', 'critical'], + 'cpu pressure state'); +}, 'Removing observer before observe() resolves does not affect other observers'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_duplicate_updates.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_duplicate_updates.tentative.https.window.js new file mode 100644 index 0000000000..3c312ca5b1 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_duplicate_updates.tentative.https.window.js @@ -0,0 +1,61 @@ +// META: script=/resources/test-only-api.js +// META: script=resources/pressure-helpers.js + +'use strict'; + +pressure_test(async (t, mockPressureService) => { + const pressureChanges = await new Promise(async resolve => { + const observer_changes = []; + let n = 0; + const observer = new PressureObserver(changes => { + observer_changes.push(changes); + if (++n === 2) + resolve(observer_changes); + }, {sampleRate: 5.0}); + observer.observe('cpu'); + const updatesDelivered = mockPressureService.updatesDelivered(); + mockPressureService.setPressureUpdate('critical'); + mockPressureService.startPlatformCollector(/*sampleRate*/ 5.0); + // Deliver 2 updates. + await t.step_wait( + () => mockPressureService.updatesDelivered() >= (updatesDelivered + 2), + 'Wait for more than one update to be delivered to the observer'); + mockPressureService.setPressureUpdate('nominal'); + // Deliver more updates, |resolve()| will be called when the new pressure + // state reaches PressureObserver and its callback is invoked + // for the second time. + }); + assert_equals(pressureChanges.length, 2); + assert_equals(pressureChanges[0][0].state, 'critical'); + assert_equals(pressureChanges[1][0].state, 'nominal'); +}, 'Changes that fail the "has change in data" test are discarded.'); + +pressure_test(async (t, mockPressureService) => { + const pressureChanges = await new Promise(async resolve => { + const observer_changes = []; + let n = 0; + const observer = new PressureObserver(changes => { + observer_changes.push(changes); + if (++n === 2) + resolve(observer_changes); + }, {sampleRate: 5.0}); + observer.observe('cpu'); + const updatesDelivered = mockPressureService.updatesDelivered(); + mockPressureService.setPressureUpdate('critical', ['thermal']); + mockPressureService.startPlatformCollector(/*sampleRate*/ 5.0); + + // Deliver 2 updates. + await t.step_wait( + () => mockPressureService.updatesDelivered() >= (updatesDelivered + 2), + 'Wait for more than one update to be delivered to the observer'); + mockPressureService.setPressureUpdate('critical', ['power-supply']); + // Deliver more updates, |resolve()| will be called when the new pressure + // state reaches PressureObserver and its callback is invoked + // for the second time. + }); + assert_equals(pressureChanges.length, 2); + assert_equals(pressureChanges[0][0].state, 'critical'); + assert_equals(pressureChanges[0][0].factors[0], 'thermal'); + assert_equals(pressureChanges[1][0].state, 'critical'); + assert_equals(pressureChanges[1][0].factors[0], 'power-supply'); +}, 'Factors that fail the "has change in data" test are discarded.'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_factors.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_factors.tentative.https.window.js new file mode 100644 index 0000000000..6d8d220888 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_factors.tentative.https.window.js @@ -0,0 +1,18 @@ +// META: script=/resources/test-only-api.js +// META: script=resources/pressure-helpers.js + +'use strict'; + +pressure_test(async (t, mockPressureService) => { + const changes = await new Promise(resolve => { + const observer = new PressureObserver(resolve, {sampleRate: 1.0}); + observer.observe('cpu'); + mockPressureService.setPressureUpdate('critical', ['thermal']); + mockPressureService.startPlatformCollector(/*sampleRate=*/ 1.0); + }); + assert_true(changes.length === 1); + assert_equals(changes[0].state, 'critical'); + assert_equals(changes[0].source, 'cpu'); + assert_equals(typeof changes[0].time, 'number'); + assert_equals(changes[0].factors[0], 'thermal'); +}, 'Basic factors functionality test'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_multiple.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_multiple.tentative.https.window.js new file mode 100644 index 0000000000..6015ae1f81 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_multiple.tentative.https.window.js @@ -0,0 +1,30 @@ +'use strict'; + +promise_test(async t => { + const changes1_promise = new Promise((resolve, reject) => { + const observer = new PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + observer.observe('cpu').catch(reject); + }); + + const changes2_promise = new Promise((resolve, reject) => { + const observer = new PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + observer.observe('cpu').catch(reject); + }); + + const changes3_promise = new Promise((resolve, reject) => { + const observer = new PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + observer.observe('cpu').catch(reject); + }); + + const [changes1, changes2, changes3] = + await Promise.all([changes1_promise, changes2_promise, changes3_promise]); + + for (const changes of [changes1, changes2, changes3]) { + assert_in_array( + changes[0].state, ['nominal', 'fair', 'serious', 'critical'], + 'cpu pressure state'); + } +}, 'Three PressureObserver instances receive changes'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_multiple_across_iframes.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_multiple_across_iframes.tentative.https.window.js new file mode 100644 index 0000000000..838b9a17a0 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_multiple_across_iframes.tentative.https.window.js @@ -0,0 +1,40 @@ +'use strict'; + +promise_test(async t => { + const changes1_promise = new Promise((resolve, reject) => { + const observer = new PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + observer.observe('cpu').catch(reject); + }); + + // iframe numbers are aligned with observer numbers. The first observer is + // in the main frame, so there is no iframe1. + const iframe2 = document.createElement('iframe'); + document.body.appendChild(iframe2); + + const changes2_promise = new Promise((resolve, reject) => { + const observer = + new iframe2.contentWindow.PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + observer.observe('cpu').catch(reject); + }); + + const iframe3 = document.createElement('iframe'); + document.body.appendChild(iframe3); + + const changes3_promise = new Promise((resolve, reject) => { + const observer = + new iframe3.contentWindow.PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + observer.observe('cpu').catch(reject); + }); + + const [changes1, changes2, changes3] = + await Promise.all([changes1_promise, changes2_promise, changes3_promise]); + + for (const changes of [changes1, changes2, changes3]) { + assert_in_array( + changes[0].state, ['nominal', 'fair', 'serious', 'critical'], + 'cpu pressure state'); + } +}, 'Three PressureObserver instances, in different iframes, receive changes'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_observe_idempotent.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_observe_idempotent.tentative.https.window.js new file mode 100644 index 0000000000..e60115fee8 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_observe_idempotent.tentative.https.window.js @@ -0,0 +1,16 @@ +'use strict'; + +promise_test(async t => { + const update = await new Promise((resolve, reject) => { + const observer = new PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + observer.observe('cpu').catch(reject); + observer.observe('cpu').catch(reject); + observer.observe('cpu').catch(reject); + }); + + assert_equals(typeof update[0].state, 'string'); + assert_in_array( + update[0].state, ['nominal', 'fair', 'serious', 'critical'], + 'cpu pressure state'); +}, 'PressureObserver.observe() is idempotent'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_observe_unobserve_failure.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_observe_unobserve_failure.tentative.https.window.js new file mode 100644 index 0000000000..c32649da5c --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_observe_unobserve_failure.tentative.https.window.js @@ -0,0 +1,17 @@ +'use strict'; + +promise_test(async t => { + const observer = new PressureObserver( + t.unreached_func('oops should not end up here'), {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + await promise_rejects_js(t, TypeError, observer.observe('random')); +}, 'PressureObserver.observe() requires a valid source'); + +test(t => { + const observer = new PressureObserver( + t.unreached_func('oops should not end up here'), {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + assert_throws_js(TypeError, () => { + observer.unobserve('random'); + }); +}, 'PressureObserver.unobserve() requires a valid source'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_options.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_options.tentative.https.window.js new file mode 100644 index 0000000000..d142ecc088 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_options.tentative.https.window.js @@ -0,0 +1,23 @@ +'use strict'; + +test(t => { + assert_throws_js(RangeError, () => { + new PressureObserver(() => {}, {sampleRate: 0}); + }); +}, 'PressureObserver constructor requires a non-zero sampleRate'); + +test(t => { + assert_throws_js(RangeError, () => { + new PressureObserver(() => {}, {sampleRate: -2}); + }); +}, 'PressureObserver constructor requires a positive sampleRate'); + +test(t => { + const observer = new PressureObserver(() => {}, {sampleRate: 0.5}); + assert_equals(typeof observer, 'object'); +}, 'PressureObserver constructor doesnt throw error on positive sampleRate'); + +test(t => { + const observer = new PressureObserver(() => {}, {}); + assert_equals(typeof observer, 'object'); +}, 'PressureObserver constructor succeeds on empty sampleRate'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_privacy_test.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_privacy_test.tentative.https.window.js new file mode 100644 index 0000000000..3a4198f547 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_privacy_test.tentative.https.window.js @@ -0,0 +1,130 @@ +// META: timeout=long +// META: script=/common/get-host-info.sub.js +// META: script=/common/media.js +// META: script=/mediacapture-streams/permission-helper.js +// META: script=/picture-in-picture/resources/picture-in-picture-helpers.js +// META: script=/resources/testdriver.js +// META: script=/resources/testdriver-vendor.js + +'use strict'; + +promise_test(async t => { + const video = await loadVideo(); + document.body.appendChild(video); + const pipWindow = await requestPictureInPictureWithTrustedClick(video); + assert_not_equals(pipWindow.width, 0); + assert_not_equals(pipWindow.height, 0); + + const iframe = document.createElement('iframe'); + document.body.appendChild(iframe); + // Focus on the iframe to make the main frame lose focus, so that + // PressureObserver in the main frame can't receive PressureRecord + // by default. However, if the main frame is the initiator of active + // Picture-in-Picture session, PressureObserver in the main frame can + // receive PressureRecord. + iframe.contentWindow.focus(); + + await new Promise(resolve => { + const observer = new PressureObserver(resolve); + t.add_cleanup(async () => { + observer.disconnect(); + iframe.remove(); + if (document.pictureInPictureElement) { + await document.exitPictureInPicture(); + } + video.remove(); + }); + observer.observe('cpu'); + }); +}, 'Observer should receive PressureRecord if associated document is the initiator of active Picture-in-Picture session'); + +promise_test(async t => { + await setMediaPermission(); + const stream = + await navigator.mediaDevices.getUserMedia({video: true, audio: true}); + assert_true(stream.active); + + const iframe = document.createElement('iframe'); + document.body.appendChild(iframe); + // Focus on the iframe to make the main frame lose focus, so that + // PressureObserver in the main frame can't receive PressureRecord + // by default. However, if the main frame's browsing context is capturing, + // PressureObserver in the main frame can receive PressureRecord. + iframe.contentWindow.focus(); + + await new Promise(resolve => { + const observer = new PressureObserver(resolve); + t.add_cleanup(async () => { + observer.disconnect(); + iframe.remove(); + stream.getTracks().forEach(track => track.stop()); + }); + observer.observe('cpu'); + }); +}, 'Observer should receive PressureRecord if browsing context is capturing'); + +promise_test(async t => { + const iframe = document.createElement('iframe'); + document.body.appendChild(iframe); + // Focus on the iframe to make the main frame lose focus, so that + // PressureObserver in the main frame can't receive PressureRecord + // by default. + iframe.contentWindow.focus(); + + const observer = new PressureObserver(() => { + assert_unreached('The observer callback should not be called'); + }); + t.add_cleanup(() => { + observer.disconnect(); + iframe.remove(); + }); + + return new Promise(resolve => t.step_timeout(resolve, 2000)); +}, 'Observer should not receive PressureRecord when top-level browsing context does not have system focus'); + +promise_test(async t => { + const iframe = document.createElement('iframe'); + document.body.appendChild(iframe); + // Focus on the main frame to make the iframe lose focus, so that + // PressureObserver in the iframe can't receive PressureRecord by default. + // However, if the iframe is same-origin with the main frame and the main + // frame has focus, PressureObserver in iframe can receive PressureRecord. + window.focus(); + + await new Promise(resolve => { + const observer = new iframe.contentWindow.PressureObserver(resolve); + t.add_cleanup(() => { + observer.disconnect(); + iframe.remove(); + }); + observer.observe('cpu'); + }); +}, 'Observer in iframe should receive PressureRecord when focused on same-origin main frame'); + +promise_test(async t => { + const iframe = document.createElement('iframe'); + iframe.src = get_host_info().HTTPS_REMOTE_ORIGIN + + '/compute-pressure/resources/support-iframe.html'; + iframe.allow = 'compute-pressure'; + const iframeLoadWatcher = new EventWatcher(t, iframe, 'load'); + document.body.appendChild(iframe); + await iframeLoadWatcher.wait_for('load'); + // Focus on the main frame to make the iframe lose focus, so that + // PressureObserver in the iframe can't receive PressureRecord by default. + // If the main frame has focus, but the iframe is cross-origin with the main + // frame, PressureObserver in the iframe still can't receive PressureRecord. + window.focus(); + + return new Promise((resolve, reject) => { + window.addEventListener('message', (e) => { + if (e.data.result === 'timeout') { + resolve(); + } else if (e.data.result === 'success') { + reject('Observer should not receive PressureRecord'); + } else { + reject('Got unexpected reply'); + } + }, {once: true}); + iframe.contentWindow.postMessage({command: 'start'}, '*'); + }); +}, 'Observer in iframe should not receive PressureRecord when focused on cross-origin main frame'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_supported_sources.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_supported_sources.tentative.https.window.js new file mode 100644 index 0000000000..2a69e731e7 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_supported_sources.tentative.https.window.js @@ -0,0 +1,19 @@ +'use strict'; + +test(() => { + // Compute Pressure should support at least "cpu" + const sources = PressureObserver.supportedSources; + assert_in_array('cpu', sources); +}, 'PressureObserver should support at least "cpu"'); + +test(() => { + // Compute Pressure should be frozen array + const sources = PressureObserver.supportedSources; + assert_equals(sources, PressureObserver.supportedSources); +}, 'PressureObserver must return always the same array'); + +test(() => { + // Compute Pressure should be frozen array + let sources = PressureObserver.supportedSources; + assert_equals(Object.isFrozen(), true); +}, 'PressureObserver must return a frozen array'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_take_records.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_take_records.tentative.https.window.js new file mode 100644 index 0000000000..d294a7e80f --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_take_records.tentative.https.window.js @@ -0,0 +1,29 @@ +// META: script=/resources/test-only-api.js +// META: script=resources/pressure-helpers.js + +'use strict'; + +test(t => { + const observer = new PressureObserver( + t.unreached_func('This callback should not have been called.'), + {sampleRate: 1.0}); + + const records = observer.takeRecords(); + assert_equals(records.length, 0, 'No record before observe'); +}, 'Calling takeRecords() before observe()'); + +promise_test(async t => { + let observer; + const changes = await new Promise(resolve => { + observer = new PressureObserver(resolve, {sampleRate: 1.0}); + t.add_cleanup(() => observer.disconnect()); + + observer.observe('cpu'); + }); + assert_in_array( + changes[0].state, ['nominal', 'fair', 'serious', 'critical'], + 'cpu presure state'); + + const records = observer.takeRecords(); + assert_equals(records.length, 0, 'No record available'); +}, 'takeRecords() returns empty record after callback invoke'); diff --git a/testing/web-platform/tests/compute-pressure/compute_pressure_timestamp.tentative.https.window.js b/testing/web-platform/tests/compute-pressure/compute_pressure_timestamp.tentative.https.window.js new file mode 100644 index 0000000000..b9b932e64f --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/compute_pressure_timestamp.tentative.https.window.js @@ -0,0 +1,77 @@ +// META: script=/resources/test-only-api.js +// META: script=resources/pressure-helpers.js + +'use strict'; + +pressure_test(async (t, mockPressureService) => { + const readings = ['nominal', 'fair', 'serious', 'critical']; + + const sampleRate = 4.0; + const pressureChanges = await new Promise(async resolve => { + const observerChanges = []; + const observer = new PressureObserver(changes => { + observerChanges.push(changes); + }, {sampleRate}); + observer.observe('cpu'); + + mockPressureService.startPlatformCollector(sampleRate * 2); + let i = 0; + // mockPressureService.updatesDelivered() does not necessarily match + // pressureChanges.length, as system load and browser optimizations can + // cause the actual timer used by mockPressureService to deliver readings + // to be a bit slower or faster than requested. + while (observerChanges.length < 4) { + mockPressureService.setPressureUpdate(readings[i++ % readings.length]); + await t.step_wait( + () => mockPressureService.updatesDelivered() >= i, + `At least ${i} readings have been delivered`); + } + observer.disconnect(); + resolve(observerChanges); + }); + + assert_equals(pressureChanges.length, 4); + assert_greater_than_equal( + pressureChanges[1][0].time - pressureChanges[0][0].time, + (1 / sampleRate * 1000)); + assert_greater_than_equal( + pressureChanges[2][0].time - pressureChanges[1][0].time, + (1 / sampleRate * 1000)); + assert_greater_than_equal( + pressureChanges[3][0].time - pressureChanges[2][0].time, + (1 / sampleRate * 1000)); +}, 'Faster collector: Timestamp difference between two changes should be higher or equal to the observer sample rate'); + +pressure_test(async (t, mockPressureService) => { + const pressureChanges = []; + const sampleRate = 1.0; + const observer = new PressureObserver(changes => { + pressureChanges.push(changes); + }, {sampleRate}); + + await new Promise(async resolve => { + observer.observe('cpu'); + mockPressureService.setPressureUpdate('critical'); + mockPressureService.startPlatformCollector(sampleRate); + await t.step_wait(() => pressureChanges.length == 1); + observer.disconnect(); + resolve(); + }); + + await new Promise(async resolve => { + observer.observe('cpu'); + mockPressureService.setPressureUpdate('serious'); + mockPressureService.startPlatformCollector(sampleRate * 4); + await t.step_wait(() => pressureChanges.length == 2); + observer.disconnect(); + resolve(); + }); + + assert_equals(pressureChanges.length, 2); + // When disconnect() is called, PressureRecord in [[LastRecordMap]] for cpu + // should be deleted. So the second PressureRecord is not discarded even + // though the time interval does not meet the requirement. + assert_less_than( + pressureChanges[1][0].time - pressureChanges[0][0].time, + (1 / sampleRate * 1000)); +}, 'disconnect() should update [[LastRecordMap]]'); diff --git a/testing/web-platform/tests/compute-pressure/idlharness.https.window.js b/testing/web-platform/tests/compute-pressure/idlharness.https.window.js new file mode 100644 index 0000000000..1cdfb59be0 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/idlharness.https.window.js @@ -0,0 +1,14 @@ +// META: script=/resources/WebIDLParser.js +// META: script=/resources/idlharness.js + +// https://wicg.github.io/compute-pressure/ + +'use strict'; + +idl_test(['compute-pressure'], ['dom', 'html'], async idl_array => { + idl_array.add_objects({ + PressureObserver: ['observer'], + }); + + self.observer = new PressureObserver(() => {}, {sampleRate: 1.0}); +}); diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy-attribute-redirect-on-load.https.html b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy-attribute-redirect-on-load.https.html new file mode 100644 index 0000000000..ec5b464461 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy-attribute-redirect-on-load.https.html @@ -0,0 +1,39 @@ + + + + + + + + diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy-attribute.https.html b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy-attribute.https.html new file mode 100644 index 0000000000..d6dfcfc191 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy-attribute.https.html @@ -0,0 +1,37 @@ + + + + + + + + diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy.https.html b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy.https.html new file mode 100644 index 0000000000..1651f72612 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy.https.html @@ -0,0 +1,55 @@ + + + + + + + + diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy.https.html.headers b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy.https.html.headers new file mode 100644 index 0000000000..76185cbb2d --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-by-permissions-policy.https.html.headers @@ -0,0 +1 @@ +Permissions-Policy: compute-pressure=* diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-on-self-origin-by-permissions-policy.https.html b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-on-self-origin-by-permissions-policy.https.html new file mode 100644 index 0000000000..98450b91a7 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-on-self-origin-by-permissions-policy.https.html @@ -0,0 +1,44 @@ + + + + + + + + diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-on-self-origin-by-permissions-policy.https.html.headers b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-on-self-origin-by-permissions-policy.https.html.headers new file mode 100644 index 0000000000..6852f871bb --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-allowed-on-self-origin-by-permissions-policy.https.html.headers @@ -0,0 +1 @@ +Permissions-Policy: compute-pressure=self diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-default-permissions-policy.https.html b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-default-permissions-policy.https.html new file mode 100644 index 0000000000..5a7c77264e --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-default-permissions-policy.https.html @@ -0,0 +1,34 @@ + + + + + + + + diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-disabled-by-permissions-policy.https.html b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-disabled-by-permissions-policy.https.html new file mode 100644 index 0000000000..58b044247c --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-disabled-by-permissions-policy.https.html @@ -0,0 +1,62 @@ + + + + + + + + diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-disabled-by-permissions-policy.https.html.headers b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-disabled-by-permissions-policy.https.html.headers new file mode 100644 index 0000000000..2e9f2ecce0 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-disabled-by-permissions-policy.https.html.headers @@ -0,0 +1 @@ +Permissions-Policy: compute-pressure=() diff --git a/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-supported-by-permissions-policy.html b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-supported-by-permissions-policy.html new file mode 100644 index 0000000000..931fcb66b4 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/permissions-policy/compute-pressure-supported-by-permissions-policy.html @@ -0,0 +1,11 @@ + +Test that compute-pressure is advertised in the feature list + + + + + diff --git a/testing/web-platform/tests/compute-pressure/resources/pressure-helpers.js b/testing/web-platform/tests/compute-pressure/resources/pressure-helpers.js new file mode 100644 index 0000000000..5234cf2d78 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/resources/pressure-helpers.js @@ -0,0 +1,35 @@ +'use strict'; + +// These tests rely on the User Agent providing an implementation of +// platform compute pressure backends. +// +// In Chromium-based browsers this implementation is provided by a polyfill +// in order to reduce the amount of test-only code shipped to users. To enable +// these tests the browser must be run with these options: +// +// --enable-blink-features=MojoJS,MojoJSTest + +let mockPressureService = undefined; + +function pressure_test(func, name, properties) { + promise_test(async t => { + if (mockPressureService === undefined) { + if (isChromiumBased) { + const mocks = + await import('/resources/chromium/mock-pressure-service.js'); + mockPressureService = mocks.mockPressureService; + } + } + assert_implements( + mockPressureService, + 'missing mockPressureService after initialization'); + + mockPressureService.start(); + + t.add_cleanup(() => { + mockPressureService.reset(); + return mockPressureService.stop(); + }); + return func(t, mockPressureService); + }, name, properties); +} diff --git a/testing/web-platform/tests/compute-pressure/resources/support-iframe.html b/testing/web-platform/tests/compute-pressure/resources/support-iframe.html new file mode 100644 index 0000000000..57e18b77f6 --- /dev/null +++ b/testing/web-platform/tests/compute-pressure/resources/support-iframe.html @@ -0,0 +1,30 @@ + + +compute pressure iframe tester + + + -- cgit v1.2.3