Files
sousa-gecko/testing/web-platform/tests/resource-timing/render-blocking-status-link.html
T
Barry Pollard 08ca4b05b4 Bug 1998493 [wpt PR 55871] - Allow upgrade of renderBlockingStatus in Resource Timing for preloaded resources., a=testonly
Automatic update from web-platform-tests
Allow upgrade of renderBlockingStatus in Resource Timing for preloaded resources.

Note this only happens if the Resource Timing entry has not been emitted yet and makes the Resource Timing entry reflect Chrome's internal understanding of whether this is render blocking or not. Previously this was just stuck at the initial status.

Spec discussion: https://github.com/w3c/resource-timing/issues/420

Bug: 457303652
Change-Id: I208d30d3fa0f673a27b5e7dc9489e0452f5d1489
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/7112285
Reviewed-by: Yoav Weiss (@Shopify) <yoavweiss@chromium.org>
Reviewed-by: Noam Rosenthal <nrosenthal@google.com>
Commit-Queue: Barry Pollard <barrypollard@chromium.org>
Cr-Commit-Position: refs/heads/main@{#1540547}

--

wpt-commits: c480f28fdbd966fccd72d7d7a430df5a95d62b61
wpt-pr: 55871
2025-11-10 09:59:33 +00:00

239 lines
10 KiB
HTML

<!DOCTYPE html>
<head>
<meta charset="utf-8" />
<title>This test validates the render blocking status of resources.</title>
<link rel="help" href="https://www.w3.org/TR/resource-timing-2/#sec-performanceresourcetiming"/>
<script src="/resources/testharness.js"></script>
<script src="/resources/testharnessreport.js"></script>
<!-- Start of test cases -->
<script>
// Dynamic style using document.write in head
document.write(`
<link rel=stylesheet
href='resources/empty_style.css?stylesheet-head-dynamic-docWrite'>
`);
document.write(`
<link rel=stylesheet
href='resources/empty_style.css?stylesheet-head-dynamic-docWrite-print'
media=print>
`);
</script>
<link rel=stylesheet href="resources/empty_style.css?stylesheet-head">
<link rel=stylesheet href="resources/empty_style.css?stylesheet-head-media-print"
media=print>
<link rel="alternate stylesheet"
href="resources/empty_style.css?stylesheet-head-alternate">
<link rel=preload as=style href="resources/empty_style.css?link-style-head-preload">
<link rel=preload as=style href="resources/empty_style.css?link-style-preload-used">
<link rel=preload as=style href="resources/empty_style.css?link-style-preload-used-immediately">
<link rel=stylesheet href="resources/empty_style.css?link-style-preload-used-immediately">
<link rel=preload as=style href="resources/empty_style.css?link-style-preload-used-immediately-then-preloaded-again">
<link rel=stylesheet href="resources/empty_style.css?link-style-preload-used-immediately-then-preloaded-again">
<link rel=preload as=style href="resources/empty_style.css?link-style-preload-used-immediately-then-preloaded-again">
<link rel=stylesheet href="resources/importer.css?stylesheet-importer-head">
<link rel=stylesheet id="link-head-remove-attr" blocking="render"
href="resources/empty_style.css?stylesheet-head-blocking-render-remove-attr">
<link rel=modulepreload href="resources/empty_script.js?link-head-modulepreload">
<link rel=preload as="script" href="resources/empty_script.js?link-script-preload-used-immediately">
<script src="resources/empty_script.js?link-script-preload-used-immediately"></script>
<link rel=preload as="script" href="resources/empty_script.js?link-script-preload-defer-used-immediately">
<script defer src="resources/empty_script.js?link-script-preload-defer-used-immediately"></script>
<style>@import url(resources/empty_style.css?stylesheet-inline-imported);</style>
<style media=print>
@import url(resources/empty_style.css?stylesheet-inline-imported-print);
</style>
</head>
<body>
<link rel=stylesheet href="resources/empty_style.css?stylesheet-body">
<link rel=stylesheet href="resources/importer.css?stylesheet-importer-body">
<link rel=stylesheet href="resources/empty_style.css?stylesheet-body-media-print"
media=print>
<link rel=stylesheet blocking="render"
href="resources/empty_style.css?stylesheet-body-blocking-render">
<img src="resources/blue.png?link-image-preload-used-immediately">
<!-- https://html.spec.whatwg.org/multipage/urls-and-fetching.html#blocking-attributes
mentions that an element is potentially render-blocking if its blocking
tokens set contains "render", or if it is implicitly potentially
render-blocking. By default, an element is not implicitly potentially
render-blocking.
https://html.spec.whatwg.org/multipage/links.html#link-type-stylesheet
specifies that a link element of type stylesheet is implicitly potentially
render-blocking only if the element was created by its node document's parser. -->
<script>
// Dynamic style using document.write in body
document.write(`
<link rel=stylesheet
href='resources/empty_style.css?stylesheet-body-dynamic-docWrite'>
`);
document.write(`
<link rel=stylesheet
href='resources/empty_style.css?stylesheet-body-dynamic-docWrite-print'
media=print>
`);
// Dynamic style using innerHTML
document.head.innerHTML += `
<link rel=stylesheet
href='resources/empty_style.css?stylesheet-head-dynamic-innerHTML'>
`;
document.head.innerHTML += `
<link rel=stylesheet
href='resources/empty_style.css?stylesheet-head-dynamic-innerHTML-print'
media=print>
`;
document.head.innerHTML += `
<link rel=stylesheet blocking=render
href='resources/empty_style.css?stylesheet-head-blocking-render-dynamic-innerHTML'>
`;
// Dynamic style using DOM API
var link = document.createElement("link");
link.href = "resources/empty_style.css?stylesheet-head-dynamic-dom";
link.rel = "stylesheet";
document.head.appendChild(link);
// Add a dynamic render-blocking style with DOM API
link = document.createElement("link");
link.href = "resources/empty_style.css?stylesheet-head-blocking-render-dynamic-dom";
link.rel = "stylesheet";
link.blocking = "render";
document.head.appendChild(link);
// Dynamic style preload using DOM API
link = document.createElement("link");
link.href = "resources/empty_style.css?link-style-head-preload-dynamic-dom";
link.rel = "preload";
link.as = "style";
document.head.appendChild(link);
// Dynamic module via modulepreload using DOM API
link = document.createElement("link");
link.href = "resources/empty_script.js?link-head-modulepreload-dynamic-dom";
link.rel = "modulepreload";
document.head.appendChild(link);
// Add a style preload with DOM API to be used later
link = document.createElement("link");
link.href = "resources/empty_style.css?link-style-preload-used-dynamic";
link.rel = "preload";
link.as = "style";
document.head.appendChild(link);
// Use the preload
link = document.createElement("link");
link.href = "resources/empty_style.css?link-style-preload-used-dynamic";
link.rel = "stylesheet";
document.head.appendChild(link);
// Dynamic inline CSS
// Add an inline CSS importer
document.write(`
<style>
@import url('resources/empty_style.css?stylesheet-inline-imported-dynamic-docwrite')
</style>
`);
document.write(`
<style media=print>
@import url('resources/empty_style.css?stylesheet-inline-imported-dynamic-docwrite-print')
</style>
`);
// Add a dynamic inline CSS importer using DOM API
let style = document.createElement("style");
style.textContent = "@import url('resources/empty_style.css?stylesheet-inline-imported-dynamic-dom')";
document.head.appendChild(style);
// Add a dynamic render-blocking inline CSS importer
style = document.createElement("style");
style.textContent = "@import url('resources/empty_style.css?stylesheet-inline-imported-blocking-render-dynamic-dom')";
style.blocking = "render";
document.head.appendChild(style);
// Dynamic CSS importer
document.write(`
<link rel=stylesheet href='resources/importer_dynamic.css'>
`);
document.write(`
<link rel=stylesheet href='resources/importer_print.css' media=print>
`);
// Removing blocking render attribute after request is made
const sheet = document.getElementById("link-head-remove-attr");
sheet.blocking = "";
</script>
<link rel=stylesheet href="resources/empty_style.css?link-style-preload-used">
<script>
const wait_for_onload = () => {
return new Promise(resolve => {
window.addEventListener("load", resolve);
})};
promise_test(
async () => {
const expectedRenderBlockingStatus = {
'stylesheet-head-dynamic-docWrite' : 'blocking',
'stylesheet-head-dynamic-docWrite-print' : 'non-blocking',
'stylesheet-head' : 'blocking',
'stylesheet-head-media-print' : 'non-blocking',
'stylesheet-head-alternate' : 'non-blocking',
'link-style-head-preload' : 'non-blocking',
'stylesheet-importer-head' : 'blocking',
'stylesheet-head-blocking-render-remove-attr' : 'blocking',
'link-head-modulepreload' : 'non-blocking',
'stylesheet-inline-imported' : 'blocking',
'stylesheet-inline-imported-print' : 'non-blocking',
'stylesheet-body': 'non-blocking',
'stylesheet-importer-body' : 'non-blocking',
'stylesheet-body-media-print' : 'non-blocking',
'stylesheet-body-blocking-render' : 'non-blocking',
'stylesheet-body-dynamic-docWrite' : 'non-blocking',
'stylesheet-body-dynamic-docWrite-print': 'non-blocking',
'stylesheet-head-dynamic-innerHTML' : 'non-blocking',
'stylesheet-head-dynamic-innerHTML-print' : 'non-blocking',
'stylesheet-head-blocking-render-dynamic-innerHTML' : 'blocking',
'stylesheet-head-dynamic-dom' : 'non-blocking',
'stylesheet-head-blocking-render-dynamic-dom' : 'blocking',
'link-style-head-preload-dynamic-dom' : 'non-blocking',
'link-head-modulepreload-dynamic-dom' : 'non-blocking',
'link-style-preload-used' : 'non-blocking',
'link-style-preload-used-dynamic' : 'non-blocking',
'link-style-preload-used-immediately' : 'blocking',
'link-style-preload-used-immediately-then-preloaded-again' : 'blocking',
'stylesheet-inline-imported-dynamic-docwrite' : 'blocking',
'stylesheet-inline-imported-dynamic-docwrite-print' : 'non-blocking',
'stylesheet-inline-imported-dynamic-dom' : 'non-blocking',
'stylesheet-inline-imported-blocking-render-dynamic-dom' : 'blocking',
'stylesheet-imported' : 'blocking',
'stylesheet-imported-print' : 'non-blocking',
'stylesheet-imported-dynamic' : 'non-blocking',
'link-image-preload-used-immediately' : 'non-blocking',
'link-script-preload-used-immediately' : 'blocking',
'link-script-preload-defer-used-immediately' : 'non-blocking'
};
await wait_for_onload();
const entry_list = performance.getEntriesByType("resource");
for (entry of entry_list) {
if (entry.name.includes("empty_style.css") ||
entry.name.includes("importer.css") ||
entry.name.includes("empty_script.js") ||
entry.name.includes("blue.png")) {
key = entry.name.split("?").pop();
expectedStatus = expectedRenderBlockingStatus[key];
assert_equals(entry.renderBlockingStatus, expectedStatus,
`render blocking status for ${entry.name} should be ${expectedStatus}`);
}
}
}, "Validate render blocking status of link resources in PerformanceResourceTiming");
</script>