blob: 28272ae355be4f8927fca40513bee704bb31bc9b [file] [edit]
<!DOCTYPE html>
<html>
<head>
<script src="../../http/tests/inspector/resources/inspector-test.js"></script>
<script>function inlineScriptOne() { return 1; }</script>
<script>
function inlineScriptTwo() {
return 2;
}
//# sourceURL=inline-script-two.js
</script>
<script>
function triggerResourceWithNormalScript() {
loadNormalScript();
}
function loadNormalScript() {
return new Promise((resolve, reject) => {
let script = document.createElement("script");
script.src = "resources/relationship-normal.js";
script.addEventListener("load", resolve, {once: true});
script.addEventListener("error", reject, {once: true});
document.body.appendChild(script);
});
}
async function triggerRepeatedResourcesWithNormalScripts() {
await loadNormalScript();
await loadNormalScript();
}
function triggerResourceWithNamedScript() {
let script = document.createElement("script");
script.src = "resources/relationship-named.js";
document.body.appendChild(script);
}
function triggerScriptWithoutResource() {
eval("//# sourceURL=script-only.js\n1+1");
}
function triggerScriptElement() {
let script = document.createElement("script");
script.text = "//# sourceURL=dynamically-added-script-element.js\n1+1";
document.body.appendChild(script);
}
function test()
{
let suite = InspectorTest.createAsyncSuite("WI.Script and WI.Resource relationship");
function validateNormalRelationship(resource, script) {
InspectorTest.expectThat(resource.url === script.url, "Resource and Script have the same URL.");
InspectorTest.expectThat(resource.scripts.length === 1, "Resource should be related to one script.");
InspectorTest.expectThat(resource.scripts[0] === script, "Resource should be related to the newly added script.");
InspectorTest.expectThat(script.resource === resource, "Script should be related to the resource.");
}
suite.addTestCase({
name: "ScriptWithResource",
description: "Normal relationship between a script and a resource.",
test(resolve, reject) {
let script = null;
let resource = null;
WI.debuggerManager.addEventListener(WI.DebuggerManager.Event.ScriptAdded, scriptListener);
WI.Frame.awaitEvent(WI.Frame.Event.ResourceWasAdded)
.then((event) => {
resource = event.data.resource;
validateRelationship();
});
function scriptListener(event) {
if (!event.data.script.url)
return;
InspectorTest.expectThat(!script, "Only one Script should be added.");
script = event.data.script;
validateRelationship();
}
function validateRelationship() {
if (!resource || !script)
return;
validateNormalRelationship(resource, script);
InspectorTest.expectThat(!script.sourceURL, "Script should not have a sourceURL.");
WI.debuggerManager.removeEventListener(WI.DebuggerManager.Event.ScriptAdded, scriptListener, null);
resolve();
}
InspectorTest.evaluateInPage("triggerResourceWithNormalScript()");
}
});
suite.addTestCase({
name: "NamedScriptWithResource",
description: "Normal relationship between a named script and a resource.",
test(resolve, reject) {
let script = null;
let resource = null;
WI.debuggerManager.addEventListener(WI.DebuggerManager.Event.ScriptAdded, scriptListener);
WI.Frame.awaitEvent(WI.Frame.Event.ResourceWasAdded)
.then((event) => {
resource = event.data.resource;
validateRelationship();
});
function scriptListener(event) {
if (!event.data.script.url)
return;
InspectorTest.expectThat(!script, "Only one Script should be added.");
script = event.data.script;
validateRelationship();
}
function validateRelationship() {
if (!resource || !script)
return;
validateNormalRelationship(resource, script);
InspectorTest.expectThat(script.sourceURL === "foo.js", "Script should have a sourceURL.");
WI.debuggerManager.removeEventListener(WI.DebuggerManager.Event.ScriptAdded, scriptListener, null);
resolve();
}
InspectorTest.evaluateInPage("triggerResourceWithNamedScript()");
}
});
suite.addTestCase({
name: "RepeatedScriptsWithResources",
description: "Repeated loads of the same JavaScript URL should each associate with the only unassociated Resource.",
async test() {
await NetworkAgent.setResourceCachingDisabled(true);
let scripts = [];
let resourceChangedPromises = [];
let scriptsAddedPromise = new Promise((resolve) => {
function handleScriptAdded(event) {
let script = event.data.script;
if (!script.url?.endsWith("/relationship-normal.js"))
return;
scripts.push(script);
if (!script.resource)
resourceChangedPromises.push(script.awaitEvent(WI.Script.Event.ResourceChanged));
if (scripts.length !== 2)
return;
WI.debuggerManager.removeEventListener(WI.DebuggerManager.Event.ScriptAdded, handleScriptAdded);
resolve();
}
WI.debuggerManager.addEventListener(WI.DebuggerManager.Event.ScriptAdded, handleScriptAdded);
});
InspectorTest.evaluateInPage("triggerRepeatedResourcesWithNormalScripts()");
await scriptsAddedPromise;
await Promise.all(resourceChangedPromises);
let resources = scripts.map((script) => script.resource);
InspectorTest.expectEqual(scripts.length, 2, "Should add two JavaScript scripts.");
InspectorTest.expectTrue(resources.every((resource) => resource instanceof WI.Resource), "Each JavaScript script should associate with a Resource.");
InspectorTest.expectEqual(new Set(resources).size, 2, "Each JavaScript script should associate with a distinct Resource.");
InspectorTest.expectTrue(resources.every((resource, index) => resource.scripts.includes(scripts[index])), "Each Resource should associate with its JavaScript script.");
await NetworkAgent.setResourceCachingDisabled(false);
}
});
suite.addTestCase({
name: "ScriptWithoutResource",
description: "A named eval does not have a resource.",
test(resolve, reject) {
WI.debuggerManager.addEventListener(WI.DebuggerManager.Event.ScriptAdded, scriptListener);
let resourceListener = WI.Frame.singleFireEventListener(WI.Frame.Event.ResourceWasAdded, (event) => {
InspectorTest.fail("Resource should not be added.");
reject();
});
function scriptListener(event) {
if (!event.data.script.sourceURL)
return;
InspectorTest.pass("Script was added.");
let script = event.data.script;
InspectorTest.expectThat(script.resource === null, "Script should not be associated with a Resource.");
InspectorTest.expectThat(script.sourceURL === "script-only.js", "Script should have a sourceURL.");
WI.Frame.removeEventListener(WI.Frame.Event.ResourceWasAdded, resourceListener, null);
WI.debuggerManager.removeEventListener(WI.DebuggerManager.Event.ScriptAdded, scriptListener, null);
resolve();
}
InspectorTest.evaluateInPage("triggerScriptWithoutResource()");
}
});
suite.addTestCase({
name: "DynamicallyAddedScriptElementNoResource",
description: "A dynamically added script element has no resource.",
test(resolve, reject) {
WI.debuggerManager.addEventListener(WI.DebuggerManager.Event.ScriptAdded, scriptListener);
function scriptListener(event) {
if (event.data.script.sourceURL !== "dynamically-added-script-element.js")
return;
InspectorTest.pass("Script was added.");
let script = event.data.script;
InspectorTest.expectThat(script.dynamicallyAddedScriptElement, "Script should identify as a dynamically added script element.");
InspectorTest.expectThat(script.resource === null, "Script should not be associated when a resource.");
WI.debuggerManager.removeEventListener(WI.DebuggerManager.Event.ScriptAdded, scriptListener, null);
resolve();
}
InspectorTest.evaluateInPage("triggerScriptElement()");
}
});
suite.addTestCase({
name: "DocumentWithInlineScripts",
description: "A document resource may be associated with multiple inline scripts.",
async test() {
let mainResource = WI.networkManager.mainFrame.mainResource;
while (mainResource.scripts.length < 4)
await mainResource.awaitEvent(WI.Resource.Event.ScriptAssociated);
let scripts = mainResource.scripts.slice().sort((a, b) => a.range.startLine - b.range.startLine);
// Scripts are:
// 1. <script> with inlineScriptOne()
// 2. <script> with inlineScriptTwo()
// 3. This <script> with test()
// 4. The <body onload> inline script event listener
InspectorTest.expectThat(scripts.length === 4, "Main Resource should have 4 scripts.");
InspectorTest.expectThat(!scripts[0].sourceURL, "Inline script 1 does not have a sourceURL.");
InspectorTest.expectThat(scripts[1].sourceURL === "inline-script-two.js", "Inline script 2 has a sourceURL.");
InspectorTest.expectThat(!scripts[2].sourceURL, "Inline script 3 does not have a sourceURL.");
InspectorTest.expectThat(!scripts[3].sourceURL, "Inline script 4 does not have a sourceURL.");
InspectorTest.expectThat(scripts[0].range.startLine < 15, "Inline script 1 should have a low start line.");
InspectorTest.expectThat(scripts[1].range.startLine < 15, "Inline script 2 should have a low start line.");
InspectorTest.expectThat(scripts[2].range.startLine < 15, "Inline script 3 should have a low start line.");
InspectorTest.expectThat(scripts[3].range.startLine > 100, "Inline script 4 should have a high start line.");
}
});
suite.runTestCasesAndFinish();
}
</script>
</head>
<body onload="runTest()">
<p>WI.Script and WI.Resource relationship.</p>
</body>
</html>