commit 1622a301a4ccc294b8608dcd9782fc22eee2d01f
parent 0a93ac3791e484044b9ea2ee099857f45f75e54c
Author: Julian Descottes <jdescottes@mozilla.com>
Date: Wed, 15 Oct 2025 12:13:24 +0000
Bug 1986704 - [devtools] Reduce markupview timeout to wait for selector on navigation to 1000ms r=devtools-reviewers,nchevobbe
Arbitrarily reducing the timeout to 1000ms, which seems more reasonable. The helper is only used in reload scenarios to reselect nodes/restore highlighters, so I think having a relatively short timeout is fine.
Test is expanded to cover this.
Differential Revision: https://phabricator.services.mozilla.com/D268685
Diffstat:
2 files changed, 59 insertions(+), 15 deletions(-)
diff --git a/devtools/client/inspector/test/browser_inspector_reload_iframe.js b/devtools/client/inspector/test/browser_inspector_reload_iframe.js
@@ -9,25 +9,31 @@
// We're loading an image that would take a few second to load so the iframe won't have
// its readyState to "complete" (it should be "interactive").
// That was causing some issue, see Bug 1733539.
-const IMG_URL = URL_ROOT_COM_SSL + "sjs_slow-loading-image.sjs";
-const FRAME_URI =
- "data:text/html;charset=utf-8," +
- encodeURI(`
- <div id="in-frame">div in the iframe</div>
- <img src="${IMG_URL}"></img>
- `);
-const HTML = `
- <iframe src="${FRAME_URI}"></iframe>
-`;
-
-const TEST_URI = "data:text/html;charset=utf-8," + encodeURI(HTML);
+
+function getTestURI(delay) {
+ const IMG_URL = `${URL_ROOT_COM_SSL}sjs_slow-loading-image.sjs?delay=${delay}`;
+ const FRAME_URI =
+ "data:text/html;charset=utf-8," +
+ encodeURI(`
+ <div id="in-frame">div in the iframe</div>
+ <img src="${IMG_URL}"></img>
+ `);
+ const HTML = `
+ <iframe src="${FRAME_URI}"></iframe>
+ `;
+
+ return "data:text/html;charset=utf-8," + encodeURI(HTML);
+}
+
+const TEST_URI = getTestURI(100);
+const SLOW_TEST_URI = getTestURI(5000);
add_task(async function () {
const { inspector } = await openInspectorForURL(TEST_URI);
await selectNodeInFrames(["iframe", "#in-frame"], inspector);
- const markupLoaded = inspector.once("markuploaded");
+ let markupLoaded = inspector.once("markuploaded");
info("Reloading page.");
await navigateTo(TEST_URI);
@@ -45,4 +51,42 @@ add_task(async function () {
reloadedNodeFront,
"#in-frame selected after reload."
);
+
+ info("Check that markup view is not blocked for a page with a slow iframe");
+ await navigateTo(SLOW_TEST_URI);
+ await selectNodeInFrames(["iframe", "#in-frame"], inspector);
+
+ markupLoaded = inspector.once("markuploaded");
+
+ info("Reloading page.");
+ const onNavigate = navigateTo(SLOW_TEST_URI);
+
+ info("Waiting for markupview to load after reload.");
+ await markupLoaded;
+
+ info("Check that the navigation is not done yet");
+ ok(
+ !(await hasPromiseResolved(onNavigate)),
+ "Navigation to page with slow iframe is not done yet"
+ );
+
+ const bodyNodeFront = await getNodeFrontInFrames(["body"], inspector);
+ is(
+ inspector.selection.nodeFront,
+ bodyNodeFront,
+ "Iframe was too slow to load, the markup view selected body as fallback"
+ );
+
+ await onNavigate;
});
+
+async function hasPromiseResolved(promise) {
+ let resolved = false;
+
+ // Note that the catch() is only here to avoid leaking promise rejections.
+ // In all cases the resolved flag should be successfully flipped in finally().
+ promise.finally(() => (resolved = true)).catch(() => {});
+ // Make sure microtasks have time to run.
+ await new Promise(resolve => Services.tm.dispatchToMainThread(resolve));
+ return resolved;
+}
diff --git a/devtools/shared/commands/inspector/inspector-command.js b/devtools/shared/commands/inspector/inspector-command.js
@@ -176,14 +176,14 @@ class InspectorCommand {
* Several selectors can be needed if the element is nested in frames
* and not directly in the root document.
* @param {Integer} timeoutInMs
- * The maximum number of ms the function should run (defaults to 5000).
+ * The maximum number of ms the function should run (defaults to 1000).
* If it exceeds this, the returned promise will resolve with `null`.
* @return {Promise<NodeFront|null>} a promise that resolves when the node front is found
* for selection using inspector tools. It resolves with the deepest frame document
* that could be retrieved when the "final" nodeFront couldn't be found in the page.
* It resolves with `null` when the function runs for more than timeoutInMs.
*/
- async findNodeFrontFromSelectors(nodeSelectors, timeoutInMs = 5000) {
+ async findNodeFrontFromSelectors(nodeSelectors, timeoutInMs = 1000) {
if (
!nodeSelectors ||
!Array.isArray(nodeSelectors) ||