--- a/devtools/client/netmonitor/test/browser.ini
+++ b/devtools/client/netmonitor/test/browser.ini
@@ -1,14 +1,15 @@
[DEFAULT]
tags = devtools
subsuite = devtools
support-files =
dropmarker.svg
head.js
+ shared-head.js
html_cause-test-page.html
html_content-type-without-cache-test-page.html
html_brotli-test-page.html
html_image-tooltip-test-page.html
html_cors-test-page.html
html_custom-get-page.html
html_cyrillic-test-page.html
html_frame-test-page.html
--- a/devtools/client/netmonitor/test/browser_net_autoscroll.js
+++ b/devtools/client/netmonitor/test/browser_net_autoscroll.js
@@ -5,17 +5,17 @@
/**
* Bug 863102 - Automatically scroll down upon new network requests.
* edited to account for changes made to fix Bug 1360457
*/
add_task(function* () {
requestLongerTimeout(4);
- let { monitor } = yield initNetMonitor(INFINITE_GET_URL, true);
+ let { tab, monitor } = yield initNetMonitor(INFINITE_GET_URL, true);
let { document, windowRequire, store } = monitor.panelWin;
let Actions = windowRequire("devtools/client/netmonitor/src/actions/index");
store.dispatch(Actions.batchEnable(false));
// Wait until the first request makes the empty notice disappear
yield waitForRequestListToAppear();
@@ -52,16 +52,21 @@ add_task(function* () {
// from just below the headers.
store.dispatch(Actions.selectRequestByIndex(0));
yield waitForNetworkEvents(monitor, 8);
yield waitSomeTime();
let requestsContainerHeaders = requestsContainer.firstChild;
let headersHeight = requestsContainerHeaders.offsetHeight;
is(requestsContainer.scrollTop, headersHeight, "Did not scroll.");
+ // Stop doing requests.
+ yield ContentTask.spawn(tab.linkedBrowser, {}, function () {
+ content.wrappedJSObject.stopRequests();
+ });
+
// Done: clean up.
return teardown(monitor);
function waitForRequestListToAppear() {
info("Waiting until the empty notice disappears and is replaced with the list");
return waitUntil(() => !!document.querySelector(".requests-list-contents"));
}
--- a/devtools/client/netmonitor/test/browser_net_brotli.js
+++ b/devtools/client/netmonitor/test/browser_net_brotli.js
@@ -46,21 +46,23 @@ add_task(function* () {
type: "plain",
fullMimeType: "text/plain",
transferred: L10N.getFormatStrWithNumbers("networkMenu.sizeB", 60),
size: L10N.getFormatStrWithNumbers("networkMenu.sizeB", 64),
time: true
});
wait = waitForDOM(document, ".CodeMirror-code");
+ let onResponseContent = monitor.panelWin.once(EVENTS.RECEIVED_RESPONSE_CONTENT);
EventUtils.sendMouseEvent({ type: "click" },
document.querySelector(".network-details-panel-toggle"));
EventUtils.sendMouseEvent({ type: "click" },
document.querySelector("#response-tab"));
yield wait;
+ yield onResponseContent;
yield testResponse("br");
yield teardown(monitor);
function* testResponse(type) {
switch (type) {
case "br": {
is(document.querySelector(".CodeMirror-line").textContent, "X".repeat(64),
"The text shown in the source editor is incorrect for the brotli request.");
--- a/devtools/client/netmonitor/test/browser_net_clear.js
+++ b/devtools/client/netmonitor/test/browser_net_clear.js
@@ -8,40 +8,39 @@
*/
add_task(function* () {
let { tab, monitor } = yield initNetMonitor(SIMPLE_URL);
info("Starting test... ");
let { document, store, windowRequire } = monitor.panelWin;
let Actions = windowRequire("devtools/client/netmonitor/src/actions/index");
- let { EVENTS } = windowRequire("devtools/client/netmonitor/src/constants");
let detailsPanelToggleButton = document.querySelector(".network-details-panel-toggle");
let clearButton = document.querySelector(".requests-list-clear-button");
store.dispatch(Actions.batchEnable(false));
// Make sure we start in a sane state
assertNoRequestState();
// Load one request and assert it shows up in the list
- let networkEvent = monitor.panelWin.once(EVENTS.NETWORK_EVENT);
+ let onMonitorUpdated = waitForAllRequestsFinished(monitor);
tab.linkedBrowser.reload();
- yield networkEvent;
+ yield onMonitorUpdated;
assertSingleRequestState();
// Click clear and make sure the requests are gone
EventUtils.sendMouseEvent({ type: "click" }, clearButton);
assertNoRequestState();
// Load a second request and make sure they still show up
- networkEvent = monitor.panelWin.once(EVENTS.NETWORK_EVENT);
+ onMonitorUpdated = waitForAllRequestsFinished(monitor);
tab.linkedBrowser.reload();
- yield networkEvent;
+ yield onMonitorUpdated;
assertSingleRequestState();
// Make sure we can now open the network details panel
EventUtils.sendMouseEvent({ type: "click" }, detailsPanelToggleButton);
ok(document.querySelector(".network-details-panel") &&
!detailsPanelToggleButton.classList.contains("pane-collapsed"),
--- a/devtools/client/netmonitor/test/browser_net_content-type.js
+++ b/devtools/client/netmonitor/test/browser_net_content-type.js
@@ -17,17 +17,17 @@ add_task(function* () {
let {
getDisplayedRequests,
getSortedRequests,
} = windowRequire("devtools/client/netmonitor/src/selectors/index");
store.dispatch(Actions.batchEnable(false));
let wait = waitForNetworkEvents(monitor, CONTENT_TYPE_WITHOUT_CACHE_REQUESTS);
- yield ContentTask.spawn(tab.linkedBrowser, {}, function* () {
+ yield ContentTask.spawn(tab.linkedBrowser, {}, function () {
content.wrappedJSObject.performRequests();
});
yield wait;
for (let requestItem of document.querySelectorAll(".request-list-item")) {
let requestsListStatus = requestItem.querySelector(".requests-list-status");
requestItem.scrollIntoView();
EventUtils.sendMouseEvent({ type: "mouseover" }, requestsListStatus);
@@ -137,35 +137,35 @@ add_task(function* () {
type: "plain",
fullMimeType: "text/plain",
transferred: L10N.getFormatStrWithNumbers("networkMenu.sizeB", 324),
size: L10N.getFormatStrWithNumbers("networkMenu.sizeKB", 10.73),
time: true
}
);
- yield selectIndexAndWaitForSourceEditor(0);
+ yield selectIndexAndWaitForSourceEditor(monitor, 0);
yield testResponseTab("xml");
- yield selectIndexAndWaitForSourceEditor(1);
+ yield selectIndexAndWaitForSourceEditor(monitor, 1);
yield testResponseTab("css");
- yield selectIndexAndWaitForSourceEditor(2);
+ yield selectIndexAndWaitForSourceEditor(monitor, 2);
yield testResponseTab("js");
yield selectIndexAndWaitForJSONView(3);
yield testResponseTab("json");
- yield selectIndexAndWaitForSourceEditor(4);
+ yield selectIndexAndWaitForSourceEditor(monitor, 4);
yield testResponseTab("html");
yield selectIndexAndWaitForImageView(5);
yield testResponseTab("png");
- yield selectIndexAndWaitForSourceEditor(6);
+ yield selectIndexAndWaitForSourceEditor(monitor, 6);
yield testResponseTab("gzip");
yield teardown(monitor);
function* testResponseTab(type) {
let tabpanel = document.querySelector("#response-panel");
function checkVisibility(box) {
@@ -265,37 +265,31 @@ add_task(function* () {
is(text, new Array(1000).join("Hello gzip!"),
"The text shown in the source editor is incorrect for the gzip request.");
break;
}
}
}
- function* selectIndexAndWaitForSourceEditor(index) {
- let editor = document.querySelector("#response-panel .CodeMirror-code");
- if (!editor) {
- let waitDOM = waitForDOM(document, "#response-panel .CodeMirror-code");
- EventUtils.sendMouseEvent({ type: "mousedown" },
- document.querySelectorAll(".request-list-item")[index]);
- document.querySelector("#response-tab").click();
- yield waitDOM;
- } else {
- EventUtils.sendMouseEvent({ type: "mousedown" },
- document.querySelectorAll(".request-list-item")[index]);
- }
- }
-
function* selectIndexAndWaitForJSONView(index) {
+ let onResponseContent = monitor.panelWin.once(EVENTS.RECEIVED_RESPONSE_CONTENT);
let tabpanel = document.querySelector("#response-panel");
let waitDOM = waitForDOM(tabpanel, ".treeTable");
store.dispatch(Actions.selectRequestByIndex(index));
yield waitDOM;
+ yield onResponseContent;
+
+ // Waiting for RECEIVED_RESPONSE_CONTENT isn't enough.
+ // DOM may not be fully updated yet and checkVisibility(json) may still fail.
+ yield waitForTick();
}
function* selectIndexAndWaitForImageView(index) {
+ let onResponseContent = monitor.panelWin.once(EVENTS.RECEIVED_RESPONSE_CONTENT);
let tabpanel = document.querySelector("#response-panel");
let waitDOM = waitForDOM(tabpanel, ".response-image");
store.dispatch(Actions.selectRequestByIndex(index));
let [imageNode] = yield waitDOM;
yield once(imageNode, "load");
+ yield onResponseContent;
}
});
--- a/devtools/client/netmonitor/test/browser_net_headers-alignment.js
+++ b/devtools/client/netmonitor/test/browser_net_headers-alignment.js
@@ -5,17 +5,17 @@
/**
* Bug 1360457 - Mis-alignment between headers and columns on overflow
*/
add_task(function* () {
requestLongerTimeout(4);
- let { monitor } = yield initNetMonitor(INFINITE_GET_URL, true);
+ let { tab, monitor } = yield initNetMonitor(INFINITE_GET_URL, true);
let { document, windowRequire, store } = monitor.panelWin;
let Actions = windowRequire("devtools/client/netmonitor/src/actions/index");
store.dispatch(Actions.batchEnable(false));
// Wait until the first request makes the empty notice disappear
yield waitForRequestListToAppear();
@@ -35,16 +35,21 @@ add_task(function* () {
let aHeaderColumn = headers.childNodes[columnNumber];
let aRequestColumn = firstRequestLine.childNodes[columnNumber];
is(aHeaderColumn.getBoundingClientRect().left,
aRequestColumn.getBoundingClientRect().left,
"Headers for columns number " + columnNumber + " are aligned."
);
}
+ // Stop doing requests.
+ yield ContentTask.spawn(tab.linkedBrowser, {}, function* () {
+ content.wrappedJSObject.stopRequests();
+ });
+
// Done: clean up.
return teardown(monitor);
function waitForRequestListToAppear() {
info("Waiting until the empty notice disappears and is replaced with the list");
return waitUntil(() => !!document.querySelector(".requests-list-contents"));
}
--- a/devtools/client/netmonitor/test/browser_net_resend_cors.js
+++ b/devtools/client/netmonitor/test/browser_net_resend_cors.js
@@ -51,25 +51,29 @@ add_task(function* () {
info("Sending the cloned request (without change)");
store.dispatch(Actions.sendCustomRequest(connector));
});
info("Waiting for both resent requests");
yield onRequests;
// Check the resent requests
- ITEMS.forEach((item, i) => {
+ for (let i = 0; i < ITEMS.length; i++) {
+ let item = ITEMS[i];
is(item.method, METHODS[i], `The ${item.method} request has the right method`);
is(item.url, requestUrl, `The ${item.method} request has the right URL`);
is(item.status, 200, `The ${item.method} response has the right status`);
if (item.method === "POST") {
+ // Force fetching response content
+ let responseContent = yield connector.requestData(item.id, "responseContent");
+
is(item.requestPostData.postData.text, "post-data",
"The POST request has the right POST data");
// eslint-disable-next-line mozilla/no-cpows-in-tests
- is(item.responseContent.content.text, "Access-Control-Allow-Origin: *",
+ is(responseContent.content.text, "Access-Control-Allow-Origin: *",
"The POST response has the right content");
}
- });
+ }
info("Finishing the test");
return teardown(monitor);
});
--- a/devtools/client/netmonitor/test/browser_net_security-error.js
+++ b/devtools/client/netmonitor/test/browser_net_security-error.js
@@ -42,19 +42,16 @@ add_task(function* () {
* completed.
*/
function waitForSecurityBrokenNetworkEvent() {
let awaitedEvents = [
"UPDATING_REQUEST_HEADERS",
"RECEIVED_REQUEST_HEADERS",
"UPDATING_REQUEST_COOKIES",
"RECEIVED_REQUEST_COOKIES",
- "STARTED_RECEIVING_RESPONSE",
- "UPDATING_RESPONSE_CONTENT",
- "RECEIVED_RESPONSE_CONTENT",
"UPDATING_EVENT_TIMINGS",
"RECEIVED_EVENT_TIMINGS",
"UPDATING_SECURITY_INFO",
"RECEIVED_SECURITY_INFO",
];
let promises = awaitedEvents.map((event) => {
return monitor.panelWin.once(EVENTS[event]);
--- a/devtools/client/netmonitor/test/browser_net_security-state.js
+++ b/devtools/client/netmonitor/test/browser_net_security-state.js
@@ -75,49 +75,40 @@ add_task(function* () {
yield executeRequests(1, "http://test1.example.com" + CORS_SJS_PATH);
yield done;
done = waitForNetworkEvents(monitor, 1);
info("Requesting a resource over HTTPS.");
yield executeRequests(1, "https://example.com" + CORS_SJS_PATH);
yield done;
- done = waitForSecurityBrokenNetworkEvent(true);
+ done = waitForSecurityBrokenNetworkEvent();
info("Requesting a resource over HTTP to localhost.");
yield executeRequests(1, "http://localhost" + CORS_SJS_PATH);
yield done;
const expectedCount = Object.keys(EXPECTED_SECURITY_STATES).length;
is(store.getState().requests.requests.size,
expectedCount,
expectedCount + " events logged.");
}
/**
* Returns a promise that's resolved once a request with security issues is
* completed.
*/
- function waitForSecurityBrokenNetworkEvent(networkError) {
+ function waitForSecurityBrokenNetworkEvent() {
let awaitedEvents = [
"UPDATING_REQUEST_HEADERS",
"RECEIVED_REQUEST_HEADERS",
"UPDATING_REQUEST_COOKIES",
"RECEIVED_REQUEST_COOKIES",
- "STARTED_RECEIVING_RESPONSE",
- "UPDATING_RESPONSE_CONTENT",
- "RECEIVED_RESPONSE_CONTENT",
"UPDATING_EVENT_TIMINGS",
"RECEIVED_EVENT_TIMINGS",
];
- // If the reason for breakage is a network error, then the
- // STARTED_RECEIVING_RESPONSE event does not fire.
- if (networkError) {
- awaitedEvents = awaitedEvents.filter(e => e !== "STARTED_RECEIVING_RESPONSE");
- }
-
let promises = awaitedEvents.map((event) => {
return monitor.panelWin.once(EVENTS[event]);
});
return Promise.all(promises);
}
});
--- a/devtools/client/netmonitor/test/browser_net_security-tab-visibility.js
+++ b/devtools/client/netmonitor/test/browser_net_security-tab-visibility.js
@@ -93,19 +93,16 @@ add_task(function* () {
* completed.
*/
function waitForSecurityBrokenNetworkEvent() {
let awaitedEvents = [
"UPDATING_REQUEST_HEADERS",
"RECEIVED_REQUEST_HEADERS",
"UPDATING_REQUEST_COOKIES",
"RECEIVED_REQUEST_COOKIES",
- "STARTED_RECEIVING_RESPONSE",
- "UPDATING_RESPONSE_CONTENT",
- "RECEIVED_RESPONSE_CONTENT",
"UPDATING_EVENT_TIMINGS",
"RECEIVED_EVENT_TIMINGS",
];
let promises = awaitedEvents.map((event) => {
return monitor.panelWin.once(EVENTS[event]);
});
--- a/devtools/client/netmonitor/test/browser_net_simple-request-data.js
+++ b/devtools/client/netmonitor/test/browser_net_simple-request-data.js
@@ -245,50 +245,34 @@ function test() {
SIMPLE_SJS,
{
status: "200",
statusText: "Och Aye"
}
);
});
- expectEvent(EVENTS.RECEIVED_RESPONSE_CONTENT, async () => {
+ expectEvent(EVENTS.PAYLOAD_READY, async () => {
await waitUntil(() => {
let requestItem = getSortedRequests(store.getState()).get(0);
return requestItem &&
requestItem.transferredSize &&
requestItem.contentSize &&
- requestItem.mimeType &&
- requestItem.responseContent;
+ requestItem.mimeType;
});
let requestItem = getSortedRequests(store.getState()).get(0);
is(requestItem.transferredSize, "342",
"The transferredSize data has an incorrect value.");
is(requestItem.contentSize, "12",
"The contentSize data has an incorrect value.");
is(requestItem.mimeType, "text/plain; charset=utf-8",
"The mimeType data has an incorrect value.");
- ok(requestItem.responseContent,
- "There should be a responseContent data available.");
- // eslint-disable-next-line mozilla/no-cpows-in-tests
- is(requestItem.responseContent.content.mimeType,
- "text/plain; charset=utf-8",
- "The responseContent data has an incorrect |content.mimeType| property.");
- // eslint-disable-next-line mozilla/no-cpows-in-tests
- is(requestItem.responseContent.content.text,
- "Hello world!",
- "The responseContent data has an incorrect |content.text| property.");
- // eslint-disable-next-line mozilla/no-cpows-in-tests
- is(requestItem.responseContent.content.size,
- 12,
- "The responseContent data has an incorrect |content.size| property.");
-
verifyRequestItemTarget(
document,
getDisplayedRequests(store.getState()),
requestItem,
"GET",
SIMPLE_SJS,
{
type: "plain",
--- a/devtools/client/netmonitor/test/browser_net_streaming-response.js
+++ b/devtools/client/netmonitor/test/browser_net_streaming-response.js
@@ -60,37 +60,23 @@ add_task(function* () {
EventUtils.sendMouseEvent({ type: "click" },
document.querySelector(".network-details-panel-toggle"));
EventUtils.sendMouseEvent({ type: "click" },
document.querySelector("#response-tab"));
yield wait;
store.dispatch(Actions.selectRequest(null));
- yield selectIndexAndWaitForSourceEditor(0);
+ yield selectIndexAndWaitForSourceEditor(monitor, 0);
// the hls-m3u8 part
testEditorContent(REQUESTS[0]);
- yield selectIndexAndWaitForSourceEditor(1);
+ yield selectIndexAndWaitForSourceEditor(monitor, 1);
// the mpeg-dash part
testEditorContent(REQUESTS[1]);
return teardown(monitor);
- function* selectIndexAndWaitForSourceEditor(index) {
- let editor = document.querySelector("#response-panel .CodeMirror-code");
- if (!editor) {
- let waitDOM = waitForDOM(document, "#response-panel .CodeMirror-code");
- EventUtils.sendMouseEvent({ type: "mousedown" },
- document.querySelectorAll(".request-list-item")[index]);
- document.querySelector("#response-tab").click();
- yield waitDOM;
- } else {
- EventUtils.sendMouseEvent({ type: "mousedown" },
- document.querySelectorAll(".request-list-item")[index]);
- }
- }
-
function testEditorContent([ fmt, textRe ]) {
ok(document.querySelector(".CodeMirror-line").textContent.match(textRe),
"The text shown in the source editor for " + fmt + " is correct.");
}
});
--- a/devtools/client/netmonitor/test/head.js
+++ b/devtools/client/netmonitor/test/head.js
@@ -1,24 +1,28 @@
/* Any copyright is dedicated to the Public Domain.
http://creativecommons.org/publicdomain/zero/1.0/ */
/* import-globals-from ../../framework/test/shared-head.js */
+/* import-globals-from shared-head.js */
/* exported Toolbox, restartNetMonitor, teardown, waitForExplicitFinish,
verifyRequestItemTarget, waitFor, testFilterButtons, loadCommonFrameScript,
- performRequestsInContent, waitForNetworkEvents */
+ performRequestsInContent, waitForNetworkEvents, selectIndexAndWaitForSourceEditor */
"use strict";
// shared-head.js handles imports, constants, and utility functions
Services.scriptloader.loadSubScript(
"chrome://mochitests/content/browser/devtools/client/framework/test/shared-head.js",
this);
-const { EVENTS } = require("devtools/client/netmonitor/src/constants");
+Services.scriptloader.loadSubScript(
+ "chrome://mochitests/content/browser/devtools/client/netmonitor/test/shared-head.js",
+ this);
+
const {
getFormattedIPAndPort,
getFormattedTime,
} = require("devtools/client/netmonitor/src/utils/format-utils");
const {
decodeUnicodeUrl,
getFormattedProtocol,
getUrlBaseName,
@@ -276,16 +280,22 @@ function restartNetMonitor(monitor, newU
}
function teardown(monitor) {
info("Destroying the specified network monitor.");
return Task.spawn(function* () {
let tab = monitor.toolbox.target.tab;
+ // Ensure that there is no pending RDP requests related to payload request
+ // done from FirefoxDataProvider.
+ info("Wait for completion of all pending RDP requests...");
+ yield waitForExistingRequests(monitor);
+ info("All pending requests finished.");
+
let onDestroyed = monitor.once("destroyed");
yield removeTab(tab);
yield onDestroyed;
});
}
function waitForNetworkEvents(monitor, getRequests, postRequests = 0) {
return new Promise((resolve) => {
@@ -301,23 +311,24 @@ function waitForNetworkEvents(monitor, g
["UPDATING_REQUEST_COOKIES", onGenericEvent],
["RECEIVED_REQUEST_COOKIES", onGenericEvent],
["UPDATING_REQUEST_POST_DATA", onPostEvent],
["RECEIVED_REQUEST_POST_DATA", onPostEvent],
["UPDATING_RESPONSE_HEADERS", onGenericEvent],
["RECEIVED_RESPONSE_HEADERS", onGenericEvent],
["UPDATING_RESPONSE_COOKIES", onGenericEvent],
["RECEIVED_RESPONSE_COOKIES", onGenericEvent],
- ["STARTED_RECEIVING_RESPONSE", onGenericEvent],
- ["UPDATING_RESPONSE_CONTENT", onGenericEvent],
- ["RECEIVED_RESPONSE_CONTENT", onGenericEvent],
["UPDATING_EVENT_TIMINGS", onGenericEvent],
["RECEIVED_EVENT_TIMINGS", onGenericEvent],
["PAYLOAD_READY", onPayloadReady]
];
+ let expectedGenericEvents = awaitedEventsToListeners
+ .filter(([, listener]) => listener == onGenericEvent).length;
+ let expectedPostEvents = awaitedEventsToListeners
+ .filter(([, listener]) => listener == onPostEvent).length;
function initProgressForURL(url) {
if (progress[url]) {
return;
}
progress[url] = {};
awaitedEventsToListeners.forEach(function ([e]) {
progress[url][e] = 0;
@@ -360,32 +371,34 @@ function waitForNetworkEvents(monitor, g
}
payloadReady++;
maybeResolve(event, actor, networkInfo);
}
function maybeResolve(event, actor, networkInfo) {
info("> Network events progress: " +
- genericEvents + "/" + ((getRequests + postRequests) * 13) + ", " +
- postEvents + "/" + (postRequests * 2) + ", " +
+ "Payload: " + payloadReady + "/" + (getRequests + postRequests) + ", " +
+ "Generic: " + genericEvents + "/" +
+ ((getRequests + postRequests) * expectedGenericEvents) + ", " +
+ "Post: " + postEvents + "/" + (postRequests * expectedPostEvents) + ", " +
"got " + event + " for " + actor);
let url = networkInfo.request.url;
updateProgressForURL(url, event);
// Uncomment this to get a detailed progress logging (when debugging a test)
// info("> Current state: " + JSON.stringify(progress, null, 2));
- // There are 15 updates which need to be fired for a request to be
- // considered finished. The "requestPostData" packet isn't fired for
- // non-POST requests.
+ // There are `expectedGenericEvents` updates which need to be fired for a request
+ // to be considered finished. The "requestPostData" packet isn't fired for non-POST
+ // requests.
if (payloadReady >= (getRequests + postRequests) &&
- genericEvents >= (getRequests + postRequests) * 13 &&
- postEvents >= postRequests * 2) {
+ genericEvents >= (getRequests + postRequests) * expectedGenericEvents &&
+ postEvents >= postRequests * expectedPostEvents) {
awaitedEventsToListeners.forEach(([e, l]) => panel.off(EVENTS[e], l));
executeSoon(resolve);
}
}
awaitedEventsToListeners.forEach(([e, l]) => panel.on(EVENTS[e], l));
});
}
@@ -679,8 +692,30 @@ function waitForContentMessage(name) {
return new Promise((resolve) => {
mm.addMessageListener(name, function onMessage(msg) {
mm.removeMessageListener(name, onMessage);
resolve(msg);
});
});
}
+
+/**
+ * Select a request and switch to its response panel.
+ *
+ * @param {Number} index The request index to be selected
+ */
+async function selectIndexAndWaitForSourceEditor(monitor, index) {
+ let document = monitor.panelWin.document;
+ let onResponseContent = monitor.panelWin.once(EVENTS.RECEIVED_RESPONSE_CONTENT);
+ // Select the request first, as it may try to fetch whatever is the current request's
+ // responseContent if we select the ResponseTab first.
+ EventUtils.sendMouseEvent({ type: "mousedown" },
+ document.querySelectorAll(".request-list-item")[index]);
+ // We may already be on the ResponseTab, so only select it if needed.
+ let editor = document.querySelector("#response-panel .CodeMirror-code");
+ if (!editor) {
+ let waitDOM = waitForDOM(document, "#response-panel .CodeMirror-code");
+ document.querySelector("#response-tab").click();
+ await waitDOM;
+ }
+ await onResponseContent;
+}
--- a/devtools/client/netmonitor/test/html_infinite-get-page.html
+++ b/devtools/client/netmonitor/test/html_infinite-get-page.html
@@ -26,18 +26,24 @@
callback();
}
};
xhr.send(null);
}
// Use a count parameter to defeat caching.
let count = 0;
+ let doRequests = true;
+ function stopRequests() { // eslint-disable-line no-unused-vars
+ doRequests = false;
+ }
(function performRequests() {
get("request_" + (count++), function () {
- setTimeout(performRequests, 50);
+ if (doRequests) {
+ setTimeout(performRequests, 50);
+ }
});
})();
</script>
</body>
</html>
new file mode 100644
--- /dev/null
+++ b/devtools/client/netmonitor/test/shared-head.js
@@ -0,0 +1,43 @@
+/* Any copyright is dedicated to the Public Domain.
+ http://creativecommons.org/publicdomain/zero/1.0/ */
+
+/* exported EVENTS, waitForExistingRequests */
+
+"use strict";
+
+const { EVENTS } = require("devtools/client/netmonitor/src/constants");
+
+async function waitForExistingRequests(monitor) {
+ let { store } = monitor.panelWin;
+ function getRequests() {
+ return store.getState().requests.requests;
+ }
+ function areAllRequestsFullyLoaded() {
+ let requests = getRequests().valueSeq();
+ for (let request of requests) {
+ // Ignore cloned request as we don't lazily fetch data for them
+ // and have arbitrary number of field set.
+ if (request.id.includes("-clone")) {
+ continue;
+ }
+ // Do same check than FirefoxDataProvider.isRequestPayloadReady,
+ // in order to ensure there is no more pending payload requests to be done.
+ if (!request.requestHeaders || !request.requestCookies ||
+ !request.eventTimings ||
+ (!request.securityInfo && !request.fromServiceWorker) ||
+ ((!request.responseHeaders || !request.responseCookies) &&
+ request.securityState != "broken" &&
+ (!request.responseContentAvailable || request.status))) {
+ return false;
+ }
+ }
+ return true;
+ }
+ // If there is no request, we are good to go.
+ if (getRequests().size == 0) {
+ return;
+ }
+ while (!areAllRequestsFullyLoaded()) {
+ await monitor.panelWin.once(EVENTS.PAYLOAD_READY);
+ }
+}
--- a/devtools/client/styleeditor/test/browser.ini
+++ b/devtools/client/styleeditor/test/browser.ini
@@ -53,16 +53,17 @@ support-files =
doc_xulpage.xul
sync.html
utf-16.css
!/devtools/client/commandline/test/helpers.js
!/devtools/client/framework/test/shared-head.js
!/devtools/client/inspector/shared/test/head.js
!/devtools/client/inspector/test/head.js
!/devtools/client/inspector/test/shared-head.js
+ !/devtools/client/netmonitor/test/shared-head.js
!/devtools/client/responsive.html/test/browser/devices.json
!/devtools/client/shared/test/test-actor-registry.js
!/devtools/client/shared/test/test-actor.js
[browser_styleeditor_add_stylesheet.js]
[browser_styleeditor_autocomplete.js]
[browser_styleeditor_autocomplete-disabled.js]
[browser_styleeditor_bom.js]
--- a/devtools/client/styleeditor/test/browser_styleeditor_fetch-from-cache.js
+++ b/devtools/client/styleeditor/test/browser_styleeditor_fetch-from-cache.js
@@ -1,16 +1,21 @@
/* vim: set ts=2 et sw=2 tw=80: */
/* Any copyright is dedicated to the Public Domain.
http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
+/* import-globals-from ../../netmonitor/test/shared-head.js */
+
// A test to ensure Style Editor doesn't bybass cache when loading style sheet
// contents (bug 978688).
+Services.scriptloader.loadSubScript(
+ "chrome://mochitests/content/browser/devtools/client/netmonitor/test/shared-head.js", this);
+
const TEST_URL = TEST_BASE_HTTP + "doc_uncached.html";
add_task(function* () {
// Disable rcwn to make cache behavior deterministic.
yield pushPref("network.http.rcwn.enabled", false);
info("Opening netmonitor");
let tab = yield addTab("about:blank");
@@ -29,16 +34,18 @@ add_task(function* () {
yield navigateTo(TEST_URL);
info("Opening Style Editor");
let styleeditor = yield toolbox.selectTool("styleeditor");
info("Waiting for the source to be loaded.");
yield styleeditor.UI.editors[0].getSourceEditor();
+ yield waitForExistingRequests(monitor);
+
info("Checking Netmonitor contents.");
let items = [];
for (let item of getSortedRequests(store.getState())) {
if (item.url.endsWith("doc_uncached.css")) {
items.push(item);
}
}
--- a/devtools/client/webconsole/new-console-output/test/mochitest/browser_netmonitor_shows_reqs_in_webconsole.js
+++ b/devtools/client/webconsole/new-console-output/test/mochitest/browser_netmonitor_shows_reqs_in_webconsole.js
@@ -59,9 +59,11 @@ async function testNetmonitor(toolbox) {
await waitUntil(() => store.getState().requests.requests.size > 0);
is(store.getState().requests.requests.size, 1,
"Network request appears in the network panel");
let item = getSortedRequests(store.getState()).get(0);
is(item.method, "GET", "The attached method is correct.");
is(item.url, TEST_PATH, "The attached url is correct.");
+
+ await waitForExistingRequests(monitor);
}
--- a/devtools/client/webconsole/new-console-output/test/mochitest/browser_webconsole_network_attach.js
+++ b/devtools/client/webconsole/new-console-output/test/mochitest/browser_webconsole_network_attach.js
@@ -44,16 +44,18 @@ add_task(async function task() {
// Expand network log
urlNode.click();
await consoleReady;
info("network-request-payload-ready received");
await testNetworkMessage(messageNode);
+
+ await waitForExistingRequests(monitor);
});
async function testNetworkMessage(messageNode) {
let headersTab = messageNode.querySelector("#headers-tab");
ok(headersTab, "Headers tab is available");
// Headers tab should be selected by default, so just check its content.
--- a/devtools/client/webconsole/new-console-output/test/mochitest/browser_webconsole_network_messages_openinnet.js
+++ b/devtools/client/webconsole/new-console-output/test/mochitest/browser_webconsole_network_messages_openinnet.js
@@ -70,9 +70,12 @@ async function testNetmonitorLink(toolbo
store.dispatch(actions.batchEnable(false));
await waitUntil(() => {
const selected = getSelectedRequest(store.getState());
return selected && selected.url === url;
});
ok(true, "The attached url is correct.");
+
+ let monitor = toolbox.getCurrentPanel();
+ await waitForExistingRequests(monitor);
}
--- a/devtools/client/webconsole/new-console-output/test/mochitest/head.js
+++ b/devtools/client/webconsole/new-console-output/test/mochitest/head.js
@@ -1,26 +1,30 @@
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
/* vim: set ft=javascript ts=2 et sw=2 tw=80: */
/* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/ */
/* import-globals-from ../../../../framework/test/shared-head.js */
+/* import-globals-from ../../../../netmonitor/test/shared-head.js */
/* exported WCUL10n, openNewTabAndConsole, waitForMessages, waitForMessage, waitFor,
findMessage, openContextMenu, hideContextMenu, loadDocument, hasFocus,
waitForNodeMutation, testOpenInDebugger, checkClickOnNode, jstermSetValueAndComplete,
openDebugger, openConsole */
"use strict";
// shared-head.js handles imports, constants, and utility functions
// Load the shared-head file first.
Services.scriptloader.loadSubScript(
"chrome://mochitests/content/browser/devtools/client/framework/test/shared-head.js",
this);
+Services.scriptloader.loadSubScript(
+ "chrome://mochitests/content/browser/devtools/client/netmonitor/test/shared-head.js", this);
+
var {HUDService} = require("devtools/client/webconsole/hudservice");
var WCUL10n = require("devtools/client/webconsole/webconsole-l10n");
Services.prefs.setBoolPref("devtools.webconsole.new-frontend-enabled", true);
registerCleanupFunction(function* () {
Services.prefs.clearUserPref("devtools.webconsole.new-frontend-enabled");
Services.prefs.clearUserPref("devtools.webconsole.ui.filterbar");
--- a/devtools/client/webconsole/test/browser_netmonitor_shows_reqs_in_webconsole.js
+++ b/devtools/client/webconsole/test/browser_netmonitor_shows_reqs_in_webconsole.js
@@ -1,15 +1,18 @@
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
/* vim: set ft=javascript ts=2 et sw=2 tw=80: */
/* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/ */
"use strict";
+Services.scriptloader.loadSubScript(
+ "chrome://mochitests/content/browser/devtools/client/netmonitor/test/shared-head.js", this);
+
const TEST_URI = "data:text/html;charset=utf8,Test that the netmonitor " +
"displays requests that have been recorded in the " +
"web console, even if the netmonitor hadn't opened yet.";
const TEST_FILE = "test-network-request.html";
const TEST_PATH = "http://example.com/browser/devtools/client/webconsole/" +
"test/" + TEST_FILE;
@@ -71,9 +74,11 @@ function* testNetmonitor(toolbox) {
yield waitUntil(() => store.getState().requests.requests.size > 0);
is(store.getState().requests.requests.size, 1, "Network request appears in the network panel");
let item = getSortedRequests(store.getState()).get(0);
is(item.method, "GET", "The attached method is correct.");
is(item.url, TEST_PATH, "The attached url is correct.");
+
+ yield waitForExistingRequests(monitor);
}
--- a/devtools/client/webconsole/test/browser_webconsole_netlogging_panel.js
+++ b/devtools/client/webconsole/test/browser_webconsole_netlogging_panel.js
@@ -1,34 +1,41 @@
/* vim:set ts=2 sw=2 sts=2 et: */
/* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/ */
+/* import-globals-from ../../netmonitor/test/shared-head.js */
+
// Tests that network log messages bring up the network panel.
"use strict";
const TEST_NETWORK_REQUEST_URI =
"http://example.com/browser/devtools/client/webconsole/test/" +
"test-network-request.html";
+Services.scriptloader.loadSubScript(
+ "chrome://mochitests/content/browser/devtools/client/netmonitor/test/shared-head.js", this);
+
add_task(function* () {
let finishedRequest = waitForFinishedRequest(({ request }) => {
return request.url.endsWith("test-network-request.html");
});
const hud = yield loadPageAndGetHud(TEST_NETWORK_REQUEST_URI);
let request = yield finishedRequest;
yield hud.ui.openNetworkPanel(request.actor);
let toolbox = gDevTools.getToolbox(hud.target);
is(toolbox.currentToolId, "netmonitor", "Network panel was opened");
- let panel = toolbox.getCurrentPanel();
+ let monitor = toolbox.getCurrentPanel();
- let { store, windowRequire } = panel.panelWin;
+ let { store, windowRequire } = monitor.panelWin;
let { getSelectedRequest } = windowRequire("devtools/client/netmonitor/src/selectors/index");
let selected = getSelectedRequest(store.getState());
is(selected.method, request.request.method,
"The correct request is selected");
is(selected.url, request.request.url,
"The correct request is definitely selected");
+
+ yield waitForExistingRequests(monitor);
});
--- a/devtools/client/webconsole/test/browser_webconsole_netlogging_reset_filter.js
+++ b/devtools/client/webconsole/test/browser_webconsole_netlogging_reset_filter.js
@@ -1,23 +1,28 @@
/* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
/* vim: set ft=javascript ts=2 et sw=2 tw=80: */
/* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/ */
+/* import-globals-from ../../netmonitor/test/shared-head.js */
+
// Tests that network log messages bring up the network panel and select the
// right request even if it was previously filtered off.
"use strict";
const TEST_FILE_URI =
"http://example.com/browser/devtools/client/webconsole/test/" +
"test-network.html";
const TEST_URI = "data:text/html;charset=utf8,<p>test file URI";
+Services.scriptloader.loadSubScript(
+ "chrome://mochitests/content/browser/devtools/client/netmonitor/test/shared-head.js", this);
+
var hud;
add_task(function* () {
let requests = [];
let { browser } = yield loadTab(TEST_URI);
yield pushPrefEnv();
hud = yield openConsole();
@@ -32,18 +37,18 @@ add_task(function* () {
yield testMessages();
let htmlRequest = requests.find(e => e.request.url.endsWith("html"));
ok(htmlRequest, "htmlRequest was a html");
yield hud.ui.openNetworkPanel(htmlRequest.actor);
let toolbox = gDevTools.getToolbox(hud.target);
is(toolbox.currentToolId, "netmonitor", "Network panel was opened");
- let panel = toolbox.getCurrentPanel();
- let { store, windowRequire } = panel.panelWin;
+ let monitor = toolbox.getCurrentPanel();
+ let { store, windowRequire } = monitor.panelWin;
let Actions = windowRequire("devtools/client/netmonitor/src/actions/index");
let { getSelectedRequest } = windowRequire("devtools/client/netmonitor/src/selectors/index");
let selected = getSelectedRequest(store.getState());
is(selected.method, htmlRequest.request.method,
"The correct request is selected");
is(selected.url, htmlRequest.request.url,
"The correct request is definitely selected");
@@ -59,16 +64,18 @@ add_task(function* () {
is(selected.method, htmlRequest.request.method,
"The correct request is selected");
is(selected.url, htmlRequest.request.url,
"The correct request is definitely selected");
// All tests are done. Shutdown.
HUDService.lastFinishedRequest.callback = null;
htmlRequest = browser = requests = hud = null;
+
+ yield waitForExistingRequests(monitor);
});
function testMessages() {
return waitForMessages({
webconsole: hud,
messages: [{
text: "running network console logging tests",
category: CATEGORY_WEBDEV,