Bug 843004 - Part 4: Tests for pretty output of objects; r=nfitzgerald

--HG--
rename : browser/devtools/webconsole/test/browser_webconsole_bug_598357_jsterm_output.js => browser/devtools/webconsole/test/browser_webconsole_output_01.js
This commit is contained in:
Mihai Sucan 2013-12-19 23:07:54 +02:00
parent 7b4599def0
commit a2344897e5
39 changed files with 1094 additions and 345 deletions

View File

@ -77,13 +77,13 @@ function test() {
.getAttribute("value"), "getName",
"Should have the right property name for 'getName' in person.");
is(personNode.get("getName").target.querySelector(".value")
.getAttribute("value"), "Function",
.getAttribute("value"), "_pfactory/<.getName()",
"'getName' in person should have the right value.");
is(personNode.get("getFoo").target.querySelector(".name")
.getAttribute("value"), "getFoo",
"Should have the right property name for 'getFoo' in person.");
is(personNode.get("getFoo").target.querySelector(".value")
.getAttribute("value"), "Function",
.getAttribute("value"), "_pfactory/<.getFoo()",
"'getFoo' in person should have the right value.");
// Expand the function nodes. This causes their properties to be

View File

@ -58,7 +58,7 @@ function testPauseOnExceptionsDisabled() {
is(innerNodes[0].querySelector(".name").getAttribute("value"), "this",
"Should have the right property name for 'this'.");
is(innerNodes[0].querySelector(".value").getAttribute("value"), "HTMLButtonElement",
is(innerNodes[0].querySelector(".value").getAttribute("value"), "<button>",
"Should have the right property value for 'this'.");
let finished = waitForDebuggerEvents(gPanel, gDebugger.EVENTS.AFTER_FRAMES_CLEARED).then(() => {
@ -124,7 +124,7 @@ function testPauseOnExceptionsEnabled() {
is(innerNodes[0].querySelector(".name").getAttribute("value"), "this",
"Should have the right property name for 'this'.");
is(innerNodes[0].querySelector(".value").getAttribute("value"), "HTMLButtonElement",
is(innerNodes[0].querySelector(".value").getAttribute("value"), "<button>",
"Should have the right property value for 'this'.");
let finished = waitForDebuggerEvents(gPanel, gDebugger.EVENTS.AFTER_FRAMES_CLEARED).then(() => {

View File

@ -79,7 +79,7 @@ function testPauseOnExceptionsAfterReload() {
is(innerNodes[0].querySelector(".name").getAttribute("value"), "this",
"Should have the right property name for 'this'.");
is(innerNodes[0].querySelector(".value").getAttribute("value"), "HTMLButtonElement",
is(innerNodes[0].querySelector(".value").getAttribute("value"), "<button>",
"Should have the right property value for 'this'.");
let finished = waitForDebuggerEvents(gPanel, gDebugger.EVENTS.AFTER_FRAMES_CLEARED).then(() => {

View File

@ -22,16 +22,16 @@ function test() {
.then(() => initialChecks())
.then(() => testModification("a", "1"))
.then(() => testModification("{ a: 1 }", "Object"))
.then(() => testModification("[a]", "Array"))
.then(() => testModification("[a]", "Array[1]"))
.then(() => testModification("b", "Object"))
.then(() => testModification("b.a", "1"))
.then(() => testModification("c.a", "1"))
.then(() => testModification("Infinity", "Infinity"))
.then(() => testModification("NaN", "NaN"))
.then(() => testModification("new Function", "Function"))
.then(() => testModification("new Function", "anonymous()"))
.then(() => testModification("+0", "0"))
.then(() => testModification("-0", "-0"))
.then(() => testModification("Object.keys({})", "Array"))
.then(() => testModification("Object.keys({})", "Array[0]"))
.then(() => testModification("document.title", '"Debugger test page"'))
.then(() => resumeDebuggerThenCloseAndFinish(gPanel))
.then(null, aError => {

View File

@ -89,14 +89,16 @@ function testExpandVariables() {
waitForDebuggerEvents(gPanel, gDebugger.EVENTS.FETCHED_PROPERTIES, 3).then(() => {
is(thisVar.get("window").target.querySelector(".name").getAttribute("value"), "window",
"Should have the right property name for 'window'.");
is(thisVar.get("window").target.querySelector(".value").getAttribute("value"), "Window",
is(thisVar.get("window").target.querySelector(".value").getAttribute("value"),
"Window \u2192 doc_frame-parameters.html",
"Should have the right property value for 'window'.");
ok(thisVar.get("window").target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'window'.");
is(thisVar.get("document").target.querySelector(".name").getAttribute("value"), "document",
"Should have the right property name for 'document'.");
is(thisVar.get("document").target.querySelector(".value").getAttribute("value"), "HTMLDocument",
is(thisVar.get("document").target.querySelector(".value").getAttribute("value"),
"HTMLDocument \u2192 doc_frame-parameters.html",
"Should have the right property value for 'document'.");
ok(thisVar.get("document").target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'document'.");

View File

@ -56,7 +56,8 @@ function testScopeVariables() {
is(localEnums[0].querySelector(".name").getAttribute("value"), "this",
"Should have the right property name for 'this'.");
is(localEnums[0].querySelector(".value").getAttribute("value"), "Window",
is(localEnums[0].querySelector(".value").getAttribute("value"),
"Window \u2192 doc_frame-parameters.html",
"Should have the right property value for 'this'.");
ok(localEnums[0].querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'this'.");
@ -192,7 +193,8 @@ function testArgumentsProperties() {
is(argsNonEnums[0].querySelector(".name").getAttribute("value"), "callee",
"Should have the right property name for 'callee'.");
is(argsNonEnums[0].querySelector(".value").getAttribute("value"), "Function",
is(argsNonEnums[0].querySelector(".value").getAttribute("value"),
"test(aArg,bArg,cArg,dArg,eArg,fArg)",
"Should have the right property name for 'callee'.");
ok(argsNonEnums[0].querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'callee'.");
@ -518,14 +520,16 @@ function testGetterSetterObject() {
is(propNonEnums[0].querySelector(".name").getAttribute("value"), "get",
"Should have the right property name for 'get'.");
is(propNonEnums[0].querySelector(".value").getAttribute("value"), "Function",
is(propNonEnums[0].querySelector(".value").getAttribute("value"),
"test/myVar.prop()",
"Should have the right property value for 'get'.");
ok(propNonEnums[0].querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'get'.");
is(propNonEnums[1].querySelector(".name").getAttribute("value"), "set",
"Should have the right property name for 'set'.");
is(propNonEnums[1].querySelector(".value").getAttribute("value"), "Function",
is(propNonEnums[1].querySelector(".value").getAttribute("value"),
"test/myVar.prop(val)",
"Should have the right property value for 'set'.");
ok(propNonEnums[1].querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'set'.");

View File

@ -71,12 +71,14 @@ function testGlobalScope() {
is(globalScope.get("window").target.querySelector(".name").getAttribute("value"), "window",
"Should have the right property name for 'window'.");
is(globalScope.get("window").target.querySelector(".value").getAttribute("value"), "Window",
is(globalScope.get("window").target.querySelector(".value").getAttribute("value"),
"Window \u2192 doc_frame-parameters.html",
"Should have the right property value for 'window'.");
is(globalScope.get("document").target.querySelector(".name").getAttribute("value"), "document",
"Should have the right property name for 'document'.");
is(globalScope.get("document").target.querySelector(".value").getAttribute("value"), "HTMLDocument",
is(globalScope.get("document").target.querySelector(".value").getAttribute("value"),
"HTMLDocument \u2192 doc_frame-parameters.html",
"Should have the right property value for 'document'.");
is(globalScope.get("undefined").target.querySelector(".name").getAttribute("value"), "undefined",
@ -123,12 +125,14 @@ function testWindowVariable() {
is(windowVar.get("window").target.querySelector(".name").getAttribute("value"), "window",
"Should have the right property name for 'window'.");
is(windowVar.get("window").target.querySelector(".value").getAttribute("value"), "Window",
is(windowVar.get("window").target.querySelector(".value").getAttribute("value"),
"Window \u2192 doc_frame-parameters.html",
"Should have the right property value for 'window'.");
is(windowVar.get("document").target.querySelector(".name").getAttribute("value"), "document",
"Should have the right property name for 'document'.");
is(windowVar.get("document").target.querySelector(".value").getAttribute("value"), "HTMLDocument",
is(windowVar.get("document").target.querySelector(".value").getAttribute("value"),
"HTMLDocument \u2192 doc_frame-parameters.html",
"Should have the right property value for 'document'.");
is(windowVar.get("undefined").target.querySelector(".name").getAttribute("value"), "undefined",

View File

@ -57,7 +57,8 @@ function testFirstWithScope() {
is(withEnums[0].querySelector(".name").getAttribute("value"), "this",
"Should have the right property name for 'this'.");
is(withEnums[0].querySelector(".value").getAttribute("value"), "Window",
is(withEnums[0].querySelector(".value").getAttribute("value"),
"Window \u2192 doc_with-frame.html",
"Should have the right property value for 'this'.");
ok(withEnums[0].querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'this'.");
@ -131,7 +132,7 @@ function testSecondWithScope() {
is(secondWithScope.get("random").target.querySelector(".name").getAttribute("value"), "random",
"Should have the right property name for 'random'.");
is(secondWithScope.get("random").target.querySelector(".value").getAttribute("value"), "Function",
is(secondWithScope.get("random").target.querySelector(".value").getAttribute("value"), "random()",
"Should have the right property value for 'random'.");
ok(secondWithScope.get("random").target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'random'.");

View File

@ -54,7 +54,7 @@ function initialChecks() {
is(arrayVar.target.querySelector(".name").getAttribute("value"), "largeArray",
"Should have the right property name for 'largeArray'.");
is(arrayVar.target.querySelector(".value").getAttribute("value"), "Int8Array",
is(arrayVar.target.querySelector(".value").getAttribute("value"), "Int8Array[10000]",
"Should have the right property value for 'largeArray'.");
ok(arrayVar.target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'largeArray'.");

View File

@ -62,7 +62,7 @@ function performTest() {
is(buttonVar.target.querySelector(".name").getAttribute("value"), "button",
"Should have the right property name for 'button'.");
is(buttonVar.target.querySelector(".value").getAttribute("value"), "HTMLButtonElement",
is(buttonVar.target.querySelector(".value").getAttribute("value"), "<button>",
"Should have the right property value for 'button'.");
ok(buttonVar.target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'button'.");
@ -76,7 +76,8 @@ function performTest() {
is(documentVar.target.querySelector(".name").getAttribute("value"), "document",
"Should have the right property name for 'document'.");
is(documentVar.target.querySelector(".value").getAttribute("value"), "HTMLDocument",
is(documentVar.target.querySelector(".value").getAttribute("value"),
"HTMLDocument \u2192 doc_frame-parameters.html",
"Should have the right property value for 'document'.");
ok(documentVar.target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'document'.");
@ -98,14 +99,14 @@ function performTest() {
is(buttonVar.get("childNodes").target.querySelector(".name").getAttribute("value"), "childNodes",
"Should have the right property name for 'childNodes'.");
is(buttonVar.get("childNodes").target.querySelector(".value").getAttribute("value"), "NodeList",
is(buttonVar.get("childNodes").target.querySelector(".value").getAttribute("value"), "NodeList[1]",
"Should have the right property value for 'childNodes'.");
ok(buttonVar.get("childNodes").target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'childNodes'.");
is(buttonVar.get("onclick").target.querySelector(".name").getAttribute("value"), "onclick",
"Should have the right property name for 'onclick'.");
is(buttonVar.get("onclick").target.querySelector(".value").getAttribute("value"), "Function",
is(buttonVar.get("onclick").target.querySelector(".value").getAttribute("value"), "onclick(event)",
"Should have the right property value for 'onclick'.");
ok(buttonVar.get("onclick").target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'onclick'.");
@ -119,7 +120,7 @@ function performTest() {
is(documentVar.get("childNodes").target.querySelector(".name").getAttribute("value"), "childNodes",
"Should have the right property name for 'childNodes'.");
is(documentVar.get("childNodes").target.querySelector(".value").getAttribute("value"), "NodeList",
is(documentVar.get("childNodes").target.querySelector(".value").getAttribute("value"), "NodeList[3]",
"Should have the right property value for 'childNodes'.");
ok(documentVar.get("childNodes").target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'childNodes'.");
@ -144,7 +145,7 @@ function performTest() {
is(buttonAsProtoProtoVar.target.querySelector(".name").getAttribute("value"), "__proto__",
"Should have the right property name for '__proto__'.");
is(buttonAsProtoProtoVar.target.querySelector(".value").getAttribute("value"), "HTMLButtonElement",
is(buttonAsProtoProtoVar.target.querySelector(".value").getAttribute("value"), "<button>",
"Should have the right property value for '__proto__'.");
ok(buttonAsProtoProtoVar.target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for '__proto__'.");
@ -173,14 +174,14 @@ function performTest() {
is(buttonAsProtoProtoVar.get("childNodes").target.querySelector(".name").getAttribute("value"), "childNodes",
"Should have the right property name for 'childNodes'.");
is(buttonAsProtoProtoVar.get("childNodes").target.querySelector(".value").getAttribute("value"), "NodeList",
is(buttonAsProtoProtoVar.get("childNodes").target.querySelector(".value").getAttribute("value"), "NodeList[1]",
"Should have the right property value for 'childNodes'.");
ok(buttonAsProtoProtoVar.get("childNodes").target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'childNodes'.");
is(buttonAsProtoProtoVar.get("onclick").target.querySelector(".name").getAttribute("value"), "onclick",
"Should have the right property name for 'onclick'.");
is(buttonAsProtoProtoVar.get("onclick").target.querySelector(".value").getAttribute("value"), "Function",
is(buttonAsProtoProtoVar.get("onclick").target.querySelector(".value").getAttribute("value"), "onclick(event)",
"Should have the right property value for 'onclick'.");
ok(buttonAsProtoProtoVar.get("onclick").target.querySelector(".value").className.contains("token-other"),
"Should have the right token class for 'onclick'.");

View File

@ -64,6 +64,10 @@ support-files =
test-console-extras.html
test-console-replaced-api.html
test-console.html
test-console-output-02.html
test-console-output-03.html
test-console-output-04.html
test-console-output-events.html
test-consoleiframes.html
test-data.json
test-data.json^headers^
@ -167,7 +171,6 @@ support-files =
[browser_webconsole_bug_597136_network_requests_from_chrome.js]
[browser_webconsole_bug_597460_filter_scroll.js]
[browser_webconsole_bug_597756_reopen_closed_tab.js]
[browser_webconsole_bug_598357_jsterm_output.js]
[browser_webconsole_bug_599725_response_headers.js]
[browser_webconsole_bug_600183_charset.js]
[browser_webconsole_bug_601177_log_levels.js]
@ -248,3 +251,8 @@ run-if = os == "mac"
[browser_webconsole_expandable_timestamps.js]
[browser_webconsole_autocomplete_in_debugger_stackframe.js]
[browser_webconsole_autocomplete_popup_close_on_tab_switch.js]
[browser_webconsole_output_01.js]
[browser_webconsole_output_02.js]
[browser_webconsole_output_03.js]
[browser_webconsole_output_04.js]
[browser_webconsole_output_events.js]

View File

@ -36,7 +36,8 @@ function onExecuteFooObj(msg)
let anchor = msg.querySelector("a");
ok(anchor, "object anchor");
isnot(anchor.textContent.indexOf("[object Object]"), -1, "message text check");
isnot(anchor.textContent.indexOf('testProp: "testValue"'), -1,
"message text check");
gJSTerm.once("variablesview-fetched", onFooObjFetch);
EventUtils.synthesizeMouse(anchor, 2, 2, {}, gWebConsole.iframeWindow)
@ -76,7 +77,8 @@ function onExecuteWindow(msg)
ok(msg, "output message found");
let anchor = msg.querySelector("a");
ok(anchor, "object anchor");
isnot(anchor.textContent.indexOf("[object Window]"), -1, "message text check");
isnot(anchor.textContent.indexOf("Window \u2192 http://example.com/browser/"), -1,
"message text check");
gJSTerm.once("variablesview-fetched", onWindowFetch);
EventUtils.synthesizeMouse(anchor, 2, 2, {}, gWebConsole.iframeWindow)

View File

@ -46,7 +46,7 @@ function onConsoleMessage(aResults)
{
let clickable = aResults[0].clickableElements[0];
ok(clickable, "clickable object found");
isnot(clickable.textContent.indexOf("[object Object]"), -1,
isnot(clickable.textContent.indexOf('{hello: "world!",'), -1,
"message text check");
gJSTerm.once("variablesview-fetched", onObjFetch);

View File

@ -71,7 +71,7 @@ function test()
},
{
name: "console.error output",
text: /\bbug851231-error\b.+\[object Object\]/,
text: /\bbug851231-error\b.+\{bug851231prop:\s"bug851231value"\}/,
category: CATEGORY_WEBDEV,
severity: SEVERITY_ERROR,
objects: true,
@ -91,7 +91,7 @@ function test()
},
{
name: "console.dir output",
consoleDir: "[object XULDocument]",
consoleDir: "XULDocument {",
},
{
name: "console.time output",

View File

@ -34,7 +34,7 @@ function performTest(hud)
}).then(([result]) => {
let clickable = result.clickableElements[0];
ok(clickable, "the console.log() object anchor was found");
isnot(clickable.textContent.indexOf("Object"), -1,
isnot(clickable.textContent.indexOf('{abba: "omgBug676722"}'), -1,
"clickable node content is correct");
hud.jsterm.once("variablesview-fetched",

View File

@ -30,7 +30,7 @@ function consoleOpened(hud)
waitForMessages({
webconsole: hud,
messages: [{
text: "[object HTMLDocument]",
text: "HTMLDocument \u2192 data:text/html;charset=utf8",
category: CATEGORY_OUTPUT,
objects: true,
}],
@ -90,7 +90,7 @@ function testParagraphs()
waitForMessages({
webconsole: gWebConsole,
messages: [{
text: "[object NodeList]",
text: "NodeList [",
category: CATEGORY_OUTPUT,
objects: true,
}],

View File

@ -28,7 +28,8 @@ function consoleOpened(hud)
function onExecuteFooObj(msg)
{
ok(msg, "output message found");
isnot(msg.textContent.indexOf("[object Object]"), -1, "message text check");
isnot(msg.textContent.indexOf('{testProp: "testValue"}'), -1,
"message text check");
let anchor = msg.querySelector("a");
ok(anchor, "object link found");

View File

@ -62,7 +62,8 @@ function onFramesAdded()
function onExecuteFooObj(msg)
{
ok(msg, "output message found");
isnot(msg.textContent.indexOf("[object Object]"), -1, "message text check");
isnot(msg.textContent.indexOf('{testProp2: "testValue2"}'), -1,
"message text check");
let anchor = msg.querySelector("a");
ok(anchor, "object link found");

View File

@ -57,7 +57,8 @@ function onFramesAdded()
function onExecuteFooObj(msg)
{
ok(msg, "output message found");
isnot(msg.textContent.indexOf("[object Object]"), -1, "message text check");
isnot(msg.textContent.indexOf('{testProp2: "testValue2"}'), -1,
"message text check");
let anchor = msg.querySelector("a");
ok(anchor, "object link found");

View File

@ -29,7 +29,7 @@ function test()
findVariableViewProperties(aVar, [
{ name: "testProp", value: "testValue" },
{ name: "document", value: "HTMLDocument" },
{ name: "document", value: /HTMLDocument \u2192 data:/ },
], { webconsole: hud }).then(finishTest);
}
}

View File

@ -28,10 +28,10 @@ function performTest(hud)
ok(!hud.outputNode.querySelector("#foobar"), "no #foobar element found");
ok(msg, "eval output node found");
is(msg.textContent.indexOf("HTMLDivElement"), -1,
"HTMLDivElement string is not displayed");
isnot(msg.textContent.indexOf("HTMLParagraphElement"), -1,
"HTMLParagraphElement string is displayed");
is(msg.textContent.indexOf("<div>"), -1,
"<div> string is not displayed");
isnot(msg.textContent.indexOf("<p>"), -1,
"<p> string is displayed");
EventUtils.synthesizeMouseAtCenter(msg, {type: "mousemove"});
ok(!gBrowser._bug772506, "no content variable");

View File

@ -80,9 +80,8 @@ function tab2Loaded(aEvent) {
function testEnd() {
ok(noErrors, "there were no errors");
Array.forEach(win1.gBrowser.tabs, function(aTab) {
win1.gBrowser.removeTab(aTab);
});
win1.gBrowser.removeTab(tab1);
Array.forEach(win2.gBrowser.tabs, function(aTab) {
win2.gBrowser.removeTab(aTab);
});

View File

@ -1,267 +0,0 @@
/* vim:set ts=2 sw=2 sts=2 et: */
/* ***** BEGIN LICENSE BLOCK *****
* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/
*
* Contributor(s):
* Mihai Șucan <mihai.sucan@gmail.com>
*
* ***** END LICENSE BLOCK ***** */
const TEST_URI = "http://example.com/browser/browser/devtools/webconsole/test/test-console.html";
let testEnded = false;
let pos = -1;
let dateNow = Date.now();
let tempScope = {};
Cu.import("resource://gre/modules/devtools/dbg-server.jsm", tempScope);
let longString = (new Array(tempScope.DebuggerServer.LONG_STRING_LENGTH + 4)).join("a");
let initialString = longString.substring(0,
tempScope.DebuggerServer.LONG_STRING_INITIAL_LENGTH);
let inputValues = [
// [showsVariablesView?, input value, expected output format,
// print() output, console API output, optional console API test]
// 0
[false, "'hello \\nfrom \\rthe \\\"string world!'",
'"hello \nfrom \rthe "string world!"',
"hello \nfrom \rthe \"string world!"],
// 1
[false, "'\xFA\u1E47\u0129\xE7\xF6d\xEA \u021B\u0115\u0219\u0165'",
"\"\xFA\u1E47\u0129\xE7\xF6d\xEA \u021B\u0115\u0219\u0165\"",
"\xFA\u1E47\u0129\xE7\xF6d\xEA \u021B\u0115\u0219\u0165"],
// 2
[false, "window.location.href", '"' + TEST_URI + '"', TEST_URI],
// 3
[false, "0", "0"],
// 4
[false, "'0'", '"0"', "0"],
// 5
[false, "42", "42"],
// 6
[false, "'42'", '"42"', "42"],
// 7
[true, "/foobar/", "[object RegExp]", '"/foobar/"', "[object RegExp]"],
// 8
[false, "null", "null"],
// 9
[false, "undefined", "undefined"],
// 10
[false, "true", "true"],
// 11
[true, "document.getElementById", "[object Function]",
"function getElementById() {\n [native code]\n}",
"[object Function]"],
// 12
[true, "(function() { return 42; })", "[object Function]",
"function () { return 42; }", "[object Function]"],
// 13
[true, "new Date(" + dateNow + ")", "[object Date]", (new Date(dateNow)).toString(), "[object Date]"],
// 14
[true, "document.body", "[object HTMLBodyElement]"],
// 15
[true, "window.location", "[object Location]", TEST_URI, "[object Location]"],
// 16
[true, "[1,2,3,'a','b','c','4','5']", '[object Array]',
'1,2,3,a,b,c,4,5',
"[object Array]"],
// 17
[true, "({a:'b', c:'d', e:1, f:'2'})", "[object Object]"],
// 18
[false, "'" + longString + "'",
'"' + initialString + "\"[\u2026]", initialString],
];
longString = null;
initialString = null;
tempScope = null;
let eventHandlers = [];
let popupShown = [];
let HUD;
let testDriver;
function tabLoad(aEvent) {
browser.removeEventListener(aEvent.type, tabLoad, true);
waitForFocus(function () {
openConsole(null, function(aHud) {
HUD = aHud;
testNext();
});
}, content);
}
function subtestNext() {
testDriver.next();
}
function testNext() {
pos++;
if (pos == inputValues.length) {
testEnd();
return;
}
testDriver = testGen();
testDriver.next();
}
function testGen() {
let cpos = pos;
let showsVariablesView = inputValues[cpos][0];
let inputValue = inputValues[cpos][1];
let expectedOutput = inputValues[cpos][2];
let printOutput = inputValues[cpos].length >= 4 ?
inputValues[cpos][3] : expectedOutput;
let consoleOutput = inputValues[cpos].length >= 5 ?
inputValues[cpos][4] : printOutput;
let consoleTest = inputValues[cpos][5] || inputValue;
HUD.jsterm.clearOutput();
// Test the console.log() output.
let outputItem;
function onExecute(msg) {
outputItem = msg;
subtestNext();
}
HUD.jsterm.execute("console.log(" + consoleTest + ")");
waitForMessages({
webconsole: HUD,
messages: [{
name: "console API output is correct for inputValues[" + cpos + "]",
text: consoleOutput,
category: CATEGORY_WEBDEV,
severity: SEVERITY_LOG,
}],
}).then(subtestNext);
yield undefined;
HUD.jsterm.clearOutput();
// Test jsterm print() output.
HUD.jsterm.setInputValue("print(" + inputValue + ")");
HUD.jsterm.execute(null, onExecute);
yield undefined;
ok(outputItem,
"found the jsterm print() output line for inputValues[" + cpos + "]");
ok(outputItem.textContent.indexOf(printOutput) > -1,
"jsterm print() output is correct for inputValues[" + cpos + "]");
// Test jsterm execution output.
HUD.jsterm.clearOutput();
HUD.jsterm.setInputValue(inputValue);
HUD.jsterm.execute(null, onExecute);
yield undefined;
ok(outputItem, "found the jsterm output line for inputValues[" + cpos + "]");
ok(outputItem.textContent.indexOf(expectedOutput) > -1,
"jsterm output is correct for inputValues[" + cpos + "]");
let messageBody = outputItem.querySelector(".body a") ||
outputItem.querySelector(".body");
ok(messageBody, "we have the message body for inputValues[" + cpos + "]");
// Test click on output.
let eventHandlerID = eventHandlers.length + 1;
let variablesViewShown = function(aEvent, aView, aOptions) {
if (aOptions.label.indexOf(expectedOutput) == -1) {
return;
}
HUD.jsterm.off("variablesview-open", variablesViewShown);
eventHandlers[eventHandlerID] = null;
ok(showsVariablesView,
"the variables view shown for inputValues[" + cpos + "]");
popupShown[cpos] = true;
if (showsVariablesView) {
executeSoon(subtestNext);
}
};
HUD.jsterm.on("variablesview-open", variablesViewShown);
eventHandlers.push(variablesViewShown);
EventUtils.synthesizeMouse(messageBody, 2, 2, {}, HUD.iframeWindow);
if (showsVariablesView) {
info("messageBody tagName '" + messageBody.tagName + "' className '" + messageBody.className + "'");
yield undefined; // wait for the panel to open if we need to.
}
testNext();
yield undefined;
}
function testEnd() {
if (testEnded) {
return;
}
testEnded = true;
for (let i = 0; i < eventHandlers.length; i++) {
if (eventHandlers[i]) {
HUD.jsterm.off("variablesview-open", eventHandlers[i]);
}
}
for (let i = 0; i < inputValues.length; i++) {
if (inputValues[i][0] && !popupShown[i]) {
ok(false, "the variables view failed to show for inputValues[" + i + "]");
}
}
HUD = inputValues = testDriver = null;
executeSoon(finishTest);
}
function test() {
requestLongerTimeout(2);
addTab(TEST_URI);
browser.addEventListener("load", tabLoad, true);
}

View File

@ -57,20 +57,16 @@ function autocompletePopupHidden()
popup._panel.removeEventListener("popuphidden", autocompletePopupHidden, false);
ok(!popup.isOpen, "popup is not open");
jsterm.once("autocomplete-updated", function() {
is(completeNode.value, testStr + "dy", "autocomplete shows document.body");
testPropertyPanel();
});
let inputStr = "document.b";
jsterm.setInputValue(inputStr);
EventUtils.synthesizeKey("o", {});
let testStr = inputStr.replace(/./g, " ") + " ";
waitForSuccess({
name: "autocomplete shows document.body",
validatorFn: function()
{
return completeNode.value == testStr + "dy";
},
successFn: testPropertyPanel,
failureFn: finishTest,
});
}
function testPropertyPanel()
@ -87,7 +83,6 @@ function testPropertyPanel()
function onVariablesViewReady(aEvent, aView)
{
findVariableViewProperties(aView, [
{ name: "body", value: "HTMLBodyElement" },
{ name: "body", value: "<body>" },
], { webconsole: gHUD }).then(finishTest);
}

View File

@ -88,8 +88,7 @@ function performWebConsoleTests(hud)
function onNodeOutput(node)
{
isnot(node.textContent.indexOf("[object HTMLHeadingElement"), -1,
"correct output for $0");
isnot(node.textContent.indexOf("<h1>"), -1, "correct output for $0");
jsterm.clearOutput();
jsterm.execute("$0.textContent = 'bug653531'", onNodeUpdate);

View File

@ -22,8 +22,8 @@ function consoleOpened(hud) {
function testConsoleDir(hud, ev, view) {
findVariableViewProperties(view, [
{ name: "__proto__.__proto__.querySelectorAll", value: "Function" },
{ name: "location", value: "Location" },
{ name: "__proto__.write", value: "Function" },
{ name: "__proto__.__proto__.querySelectorAll", value: "querySelectorAll()" },
{ name: "location", value: /Location \u2192 data:Web/ },
{ name: "__proto__.write", value: "write()" },
], { webconsole: hud }).then(finishTest);
}

View File

@ -54,7 +54,7 @@ function consoleOpened(hud)
waitForMessages({
webconsole: gWebConsole,
messages: [{
text: "[object Function]",
text: "function _pfactory/<.getName()",
category: CATEGORY_OUTPUT,
objects: true,
}],

View File

@ -118,7 +118,7 @@ function testJSTerm(hud)
jsterm.clearOutput();
jsterm.execute("pprint({b:2, a:1})");
checkResult('" b: 2\n a: 1"', "pprint()");
checkResult("\" b: 2\\n a: 1\"", "pprint()");
yield undefined;
// check instanceof correctness, bug 599940
@ -154,7 +154,7 @@ function testJSTerm(hud)
// bug 614561
jsterm.clearOutput();
jsterm.execute("pprint('hi')");
checkResult('" 0: "h"\n 1: "i""', "pprint('hi')");
checkResult("\" 0: \\\"h\\\"\\n 1: \\\"i\\\"\"", "pprint('hi')");
yield undefined;
// check that pprint(function) shows function source, bug 618344

View File

@ -0,0 +1,146 @@
/*
* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/
*/
// Test the webconsole output for various types of objects.
const TEST_URI = "data:text/html;charset=utf8,test for console output - 01";
let dateNow = Date.now();
let {DebuggerServer} = Cu.import("resource://gre/modules/devtools/dbg-server.jsm", {});
let LONG_STRING_LENGTH = DebuggerServer.LONG_STRING_LENGTH;
let LONG_STRING_INITIAL_LENGTH = DebuggerServer.LONG_STRING_INITIAL_LENGTH;
DebuggerServer.LONG_STRING_LENGTH = 100;
DebuggerServer.LONG_STRING_INITIAL_LENGTH = 50;
let longString = (new Array(DebuggerServer.LONG_STRING_LENGTH + 4)).join("a");
let initialString = longString.substring(0, DebuggerServer.LONG_STRING_INITIAL_LENGTH);
let inputTests = [
// 0
{
input: "'hello \\nfrom \\rthe \\\"string world!'",
output: "\"hello \\nfrom \\rthe \\\"string world!\"",
},
// 1
{
// unicode test
input: "'\xFA\u1E47\u0129\xE7\xF6d\xEA \u021B\u0115\u0219\u0165'",
output: "\"\\xFA\\u1E47\\u0129\\xE7\\xF6d\\xEA \\u021B\\u0115\\u0219\\u0165\"",
},
// 2
{
input: "'" + longString + "'",
output: '"' + initialString + "\"[\u2026]",
printOutput: initialString,
},
// 3
{
input: "''",
output: '""',
printOutput: '""',
},
// 4
{
input: "0",
output: "0",
},
// 5
{
input: "'0'",
output: '"0"',
},
// 6
{
input: "42",
output: "42",
},
// 7
{
input: "'42'",
output: '"42"',
},
// 8
{
input: "/foobar/",
output: "/foobar/",
inspectable: true,
},
// 9
{
input: "/foo?b*\\s\"ar/igym",
output: "/foo?b*\\s\"ar/gimy",
printOutput: "/foo?b*\\\\s\\\"ar/gimy",
inspectable: true,
},
// 10
{
input: "null",
output: "null",
},
// 11
{
input: "undefined",
output: "undefined",
},
// 12
{
input: "true",
output: "true",
},
// 13
{
input: "false",
output: "false",
},
// 14
{
input: "new Date(" + dateNow + ")",
output: "Date " + (new Date(dateNow)).toISOString(),
printOutput: (new Date(dateNow)).toString(),
inspectable: true,
},
// 15
{
input: "new Date('test')",
output: "Invalid Date",
printOutput: "Invalid Date",
inspectable: true,
variablesViewLabel: "Invalid Date",
},
];
longString = initialString = null;
function test() {
registerCleanupFunction(() => {
DebuggerServer.LONG_STRING_LENGTH = LONG_STRING_LENGTH;
DebuggerServer.LONG_STRING_INITIAL_LENGTH = LONG_STRING_INITIAL_LENGTH;
});
addTab(TEST_URI);
browser.addEventListener("load", function onLoad() {
browser.removeEventListener("load", onLoad, true);
openConsole().then((hud) => {
return checkOutputForInputs(hud, inputTests);
}).then(finishTest);
}, true);
}

View File

@ -0,0 +1,161 @@
/*
* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/
*/
// Test the webconsole output for various types of objects.
const TEST_URI = "http://example.com/browser/browser/devtools/webconsole/test/test-console-output-02.html";
let inputTests = [
// 0 - native named function
{
input: "document.getElementById",
output: "function getElementById()",
printOutput: "function getElementById() {\\n [native code]\\n}",
inspectable: true,
variablesViewLabel: "getElementById()",
},
// 1 - anonymous function
{
input: "(function() { return 42; })",
output: "function ()",
printOutput: "function () { return 42; }",
inspectable: true,
},
// 2 - named function
{
input: "window.testfn1",
output: "function testfn1()",
printOutput: "function testfn1() { return 42; }",
inspectable: true,
variablesViewLabel: "testfn1()",
},
// 3 - anonymous function, but spidermonkey gives us an inferred name.
{
input: "testobj1.testfn2",
output: "function testobj1.testfn2()",
printOutput: "function () { return 42; }",
inspectable: true,
variablesViewLabel: "testobj1.testfn2()",
},
// 4 - named function with custom display name
{
input: "window.testfn3",
output: "function testfn3DisplayName()",
printOutput: "function testfn3() { return 42; }",
inspectable: true,
variablesViewLabel: "testfn3DisplayName()",
},
// 5 - basic array
{
input: "window.array1",
output: '[1, 2, 3, "a", "b", "c", "4", "5"]',
printOutput: "1,2,3,a,b,c,4,5",
inspectable: true,
variablesViewLabel: "Array[8]",
},
// 6 - array with objects
{
input: "window.array2",
output: '["a", HTMLDocument \u2192 test-console-output-02.html, <body>, ' +
"DOMStringMap[0], DOMTokenList[0]]",
printOutput: '"a,[object HTMLDocument],[object HTMLBodyElement],' +
'[object DOMStringMap],"',
inspectable: true,
variablesViewLabel: "Array[5]",
},
// 7 - array with more than 10 elements
{
input: "window.array3",
output: '[1, Window \u2192 test-console-output-02.html, null, "a", "b", ' +
'undefined, false, "", -Infinity, testfn3DisplayName(), 3 more\u2026]',
printOutput: '"1,[object Window],,a,b,,false,,-Infinity,' +
'function testfn3() { return 42; },[object Object],foo,bar"',
inspectable: true,
variablesViewLabel: "Array[13]",
},
// 8 - array with holes and a cyclic reference
{
input: "window.array4",
output: '[,,,,, "test", Array[7]]',
printOutput: '",,,,,test,"',
inspectable: true,
variablesViewLabel: "Array[7]",
},
// 9
{
input: "window.typedarray1",
output: 'Int32Array [1, 287, 8651, 40983, 8754]',
printOutput: "[object Int32Array]",
inspectable: true,
variablesViewLabel: "Int32Array[5]",
},
// 10 - Set with cyclic reference
{
input: "window.set1",
output: 'Set [1, 2, null, Array[13], "a", "b", undefined, <head>, Set[9]]',
printOutput: "[object Set]",
inspectable: true,
variablesViewLabel: "Set[9]",
},
// 11 - Object with cyclic reference and a getter
{
input: "window.testobj2",
output: '{a: "b", c: "d", e: 1, f: "2", foo: Object, bar: Object, ' +
"getterTest: Getter}",
printOutput: "[object Object]",
inspectable: true,
variablesViewLabel: "Object",
},
// 12 - Object with more than 10 properties
{
input: "window.testobj3",
output: '{a: "b", c: "d", e: 1, f: "2", g: true, h: null, i: undefined, ' +
'j: "", k: StyleSheetList[0], l: NodeList[5], 2 more\u2026}',
printOutput: "[object Object]",
inspectable: true,
variablesViewLabel: "Object",
},
// 13 - Object with a non-enumerable property that we do not show
{
input: "window.testobj4",
output: '{a: "b", c: "d", 1 more\u2026}',
printOutput: "[object Object]",
inspectable: true,
variablesViewLabel: "Object",
},
// 14 - Map with cyclic references
{
input: "window.map1",
output: 'Map {a: "b", HTMLCollection[2]: Object, Map[3]: Set[9]}',
printOutput: "[object Map]",
inspectable: true,
variablesViewLabel: "Map[3]",
},
];
function test() {
addTab(TEST_URI);
browser.addEventListener("load", function onLoad() {
browser.removeEventListener("load", onLoad, true);
openConsole().then((hud) => {
return checkOutputForInputs(hud, inputTests);
}).then(finishTest);
}, true);
}

View File

@ -0,0 +1,164 @@
/*
* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/
*/
// Test the webconsole output for various types of objects.
const TEST_URI = "http://example.com/browser/browser/devtools/webconsole/test/test-console-output-03.html";
let inputTests = [
// 0
{
input: "document",
output: "HTMLDocument \u2192 " + TEST_URI,
printOutput: "[object HTMLDocument]",
inspectable: true,
noClick: true,
},
// 1
{
input: "window",
output: "Window \u2192 " + TEST_URI,
printOutput: "[object Window",
inspectable: true,
noClick: true,
},
// 2
{
input: "document.body",
output: "<body>",
printOutput: "[object HTMLBodyElement]",
inspectable: true,
noClick: true,
},
// 3
{
input: "document.body.dataset",
output: "DOMStringMap {}",
printOutput: "[object DOMStringMap]",
inspectable: true,
variablesViewLabel: "DOMStringMap[0]",
},
// 4
{
input: "document.body.classList",
output: "DOMTokenList []",
printOutput: '""',
inspectable: true,
variablesViewLabel: "DOMTokenList[0]",
},
// 5
{
input: "window.location.href",
output: '"' + TEST_URI + '"',
},
// 6
{
input: "window.location",
output: "Location \u2192 " + TEST_URI,
printOutput: TEST_URI,
inspectable: true,
variablesViewLabel: "Location \u2192 test-console-output-03.html",
},
// 7
{
input: "document.body.attributes",
output: "MozNamedAttrMap []",
printOutput: "[object MozNamedAttrMap]",
inspectable: true,
variablesViewLabel: "MozNamedAttrMap[0]",
},
// 8
{
input: "document.styleSheets",
output: "StyleSheetList []",
printOutput: "[object StyleSheetList",
inspectable: true,
variablesViewLabel: "StyleSheetList[0]",
},
// 9
{
input: "testBodyClassName()",
output: '<body class="test1 tezt2">',
printOutput: "[object HTMLBodyElement]",
inspectable: true,
noClick: true,
},
// 10
{
input: "testBodyID()",
output: '<body class="test1 tezt2" id="foobarid">',
printOutput: "[object HTMLBodyElement]",
inspectable: true,
noClick: true,
},
// 11
{
input: "document.body.classList",
output: 'DOMTokenList ["test1", "tezt2"]',
printOutput: '"test1 tezt2"',
inspectable: true,
variablesViewLabel: "DOMTokenList[2]",
},
// 12
{
input: "testBodyDataset()",
output: '<body class="test1 tezt2" id="foobarid"' +
' data-preview="zuzu&quot;&lt;a&gt;foo">',
printOutput: "[object HTMLBodyElement]",
inspectable: true,
noClick: true,
},
// 13
{
input: "document.body.dataset",
output: 'DOMStringMap {preview: "zuzu\\"<a>foo"}',
printOutput: "[object DOMStringMap]",
inspectable: true,
variablesViewLabel: "DOMStringMap[1]",
},
// 14
{
input: "document.body.attributes",
output: 'MozNamedAttrMap [class="test1 tezt2", id="foobarid", ' +
'data-preview="zuzu&quot;&lt;a&gt;foo"]',
printOutput: "[object MozNamedAttrMap]",
inspectable: true,
variablesViewLabel: "MozNamedAttrMap[3]",
},
// 15
{
input: "document.body.attributes[0]",
output: 'class="test1 tezt2"',
printOutput: "[object Attr]",
inspectable: true,
variablesViewLabel: 'class="test1 tezt2"',
},
];
function test() {
addTab(TEST_URI);
browser.addEventListener("load", function onLoad() {
browser.removeEventListener("load", onLoad, true);
openConsole().then((hud) => {
return checkOutputForInputs(hud, inputTests);
}).then(finishTest);
}, true);
}

View File

@ -0,0 +1,120 @@
/*
* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/
*/
// Test the webconsole output for various types of objects.
const TEST_URI = "http://example.com/browser/browser/devtools/webconsole/test/test-console-output-04.html";
let inputTests = [
// 0
{
input: "testTextNode()",
output: '#text "hello world!"',
printOutput: "[object Text]",
inspectable: true,
noClick: true,
},
// 1
{
input: "testCommentNode()",
output: "<!--\n - Any copyright ",
printOutput: "[object Comment]",
inspectable: true,
noClick: true,
},
// 2
{
input: "testDocumentFragment()",
output: 'DocumentFragment [<div id="foo1" class="bar">, <div id="foo3">]',
printOutput: "[object DocumentFragment]",
inspectable: true,
variablesViewLabel: "DocumentFragment[2]",
},
// 3
{
input: "testError()",
output: "TypeError: window.foobar is not a function\n" +
"Stack trace:\n" +
"testError@" + TEST_URI + ":44",
printOutput: '"TypeError: window.foobar is not a function"',
inspectable: true,
variablesViewLabel: "TypeError",
},
// 4
{
input: "testDOMException()",
output: 'DOMException [SyntaxError: "An invalid or illegal string was specified"',
printOutput: '[Exception... \\"An invalid or illegal string was specified\\"',
inspectable: true,
variablesViewLabel: "SyntaxError",
},
// 5
{
input: "testCSSStyleDeclaration()",
output: 'CSS2Properties {color: "green", font-size: "2em"}',
printOutput: "[object CSS2Properties]",
inspectable: true,
noClick: true,
},
// 6
{
input: "testStyleSheetList()",
output: "StyleSheetList [CSSStyleSheet]",
printOutput: "[object StyleSheetList",
inspectable: true,
variablesViewLabel: "StyleSheetList[1]",
},
// 7
{
input: "document.styleSheets[0]",
output: "CSSStyleSheet",
printOutput: "[object CSSStyleSheet]",
inspectable: true,
},
// 8
{
input: "document.styleSheets[0].cssRules",
output: "CSSRuleList [CSSStyleRule, CSSMediaRule]",
printOutput: "[object CSSRuleList",
inspectable: true,
variablesViewLabel: "CSSRuleList[2]",
},
// 9
{
input: "document.styleSheets[0].cssRules[0]",
output: 'CSSStyleRule "p, div"',
printOutput: "[object CSSStyleRule",
inspectable: true,
variablesViewLabel: "CSSStyleRule",
},
// 10
{
input: "document.styleSheets[0].cssRules[1]",
output: 'CSSMediaRule "print"',
printOutput: "[object CSSMediaRule",
inspectable: true,
variablesViewLabel: "CSSMediaRule",
},
];
function test() {
addTab(TEST_URI);
browser.addEventListener("load", function onLoad() {
browser.removeEventListener("load", onLoad, true);
openConsole().then((hud) => {
return checkOutputForInputs(hud, inputTests);
}).then(finishTest);
}, true);
}

View File

@ -0,0 +1,60 @@
/*
* Any copyright is dedicated to the Public Domain.
* http://creativecommons.org/publicdomain/zero/1.0/
*/
// Test the webconsole output for DOM events.
const TEST_URI = "http://example.com/browser/browser/devtools/webconsole/test/test-console-output-events.html";
function test() {
addTab(TEST_URI);
browser.addEventListener("load", function onLoad() {
browser.removeEventListener("load", onLoad, true);
Task.spawn(runner);
}, true);
function* runner()
{
let hud = yield openConsole();
hud.jsterm.clearOutput();
hud.jsterm.execute("testDOMEvents()");
yield waitForMessages({
webconsole: hud,
messages: [{
name: "testDOMEvents() output",
text: "undefined",
category: CATEGORY_OUTPUT,
}],
});
EventUtils.synthesizeMouse(content.document.body, 2, 2, {type: "mousemove"}, content);
yield waitForMessages({
webconsole: hud,
messages: [{
name: "console.log() output for mousemove",
text: /"eventLogger" mousemove {target: .+, buttons: 1, clientX: \d+, clientY: \d+, layerX: \d+, layerY: \d+}/,
category: CATEGORY_WEBDEV,
severity: SEVERITY_LOG,
}],
});
content.focus();
EventUtils.synthesizeKey("a", {shiftKey: true}, content);
yield waitForMessages({
webconsole: hud,
messages: [{
name: "console.log() output for keypress",
text: /"eventLogger" keypress Shift {target: .+, key: .+, charCode: \d+, keyCode: \d+}/,
category: CATEGORY_WEBDEV,
severity: SEVERITY_LOG,
}],
});
finishTest();
}
}

View File

@ -3,18 +3,18 @@
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
let WebConsoleUtils, gDevTools, TargetFactory, console, promise, require;
let WebConsoleUtils, TargetFactory, require;
let {gDevTools} = Cu.import("resource:///modules/devtools/gDevTools.jsm", {});
let {console} = Cu.import("resource://gre/modules/devtools/Console.jsm", {});
let {Promise: promise} = Cu.import("resource://gre/modules/commonjs/sdk/core/promise.js", {});
let {Task} = Cu.import("resource://gre/modules/Task.jsm", {});
(() => {
gDevTools = Cu.import("resource:///modules/devtools/gDevTools.jsm", {}).gDevTools;
console = Cu.import("resource://gre/modules/devtools/Console.jsm", {}).console;
promise = Cu.import("resource://gre/modules/commonjs/sdk/core/promise.js", {}).Promise;
let tools = Cu.import("resource://gre/modules/devtools/Loader.jsm", {}).devtools;
let utils = tools.require("devtools/toolkit/webconsole/utils");
TargetFactory = tools.TargetFactory;
let {devtools} = Cu.import("resource://gre/modules/devtools/Loader.jsm", {});
let utils = devtools.require("devtools/toolkit/webconsole/utils");
TargetFactory = devtools.TargetFactory;
WebConsoleUtils = utils.Utils;
require = tools.require;
require = devtools.require;
})();
// promise._reportErrors = true; // please never leave me.
@ -152,15 +152,20 @@ function findLogEntry(aString)
* @param function [aCallback]
* Optional function to invoke after the Web Console completes
* initialization (web-console-created).
* @return object
* A promise that is resolved once the web console is open.
*/
function openConsole(aTab, aCallback = function() { })
{
let deferred = promise.defer();
let target = TargetFactory.forTab(aTab || tab);
gDevTools.showToolbox(target, "webconsole").then(function(toolbox) {
let hud = toolbox.getCurrentPanel().hud;
hud.jsterm._lazyVariablesView = false;
aCallback(hud);
deferred.resolve(hud);
});
return deferred.promise;
}
/**
@ -1259,3 +1264,153 @@ function whenDelayedStartupFinished(aWindow, aCallback)
}
}, "browser-delayed-startup-finished", false);
}
/**
* Check the web console output for the given inputs. Each input is checked for
* the expected JS eval result, the result of calling print(), the result of
* console.log(). The JS eval result is also checked if it opens the variables
* view on click.
*
* @param object hud
* The web console instance to work with.
* @param array inputTests
* An array of input tests. An input test element is an object. Each
* object has the following properties:
* - input: string, JS input value to execute.
*
* - output: string|RegExp, expected JS eval result.
*
* - inspectable: boolean, when true, the test runner expects the JS eval
* result is an object that can be clicked for inspection.
*
* - noClick: boolean, when true, the test runner does not click the JS
* eval result. Some objects, like |window|, have a lot of properties and
* opening vview for them is very slow (they can cause timeouts in debug
* builds).
*
* - printOutput: string|RegExp, optional, expected output for
* |print(input)|. If this is not provided, printOutput = output.
*
* - variablesViewLabel: string|RegExp, optional, the expected variables
* view label when the object is inspected. If this is not provided, then
* |output| is used.
*/
function checkOutputForInputs(hud, inputTests)
{
let eventHandlers = new Set();
function* runner()
{
for (let [i, entry] of inputTests.entries()) {
info("checkInput(" + i + "): " + entry.input);
yield checkInput(entry);
}
for (let fn of eventHandlers) {
hud.jsterm.off("variablesview-open", fn);
}
}
function* checkInput(entry)
{
yield checkConsoleLog(entry);
yield checkPrintOutput(entry);
yield checkJSEval(entry);
}
function checkConsoleLog(entry)
{
hud.jsterm.clearOutput();
hud.jsterm.execute("console.log(" + entry.input + ")");
return waitForMessages({
webconsole: hud,
messages: [{
name: "console.log() output: " + entry.output,
text: entry.output,
category: CATEGORY_WEBDEV,
severity: SEVERITY_LOG,
}],
});
}
function checkPrintOutput(entry)
{
hud.jsterm.clearOutput();
hud.jsterm.execute("print(" + entry.input + ")");
let printOutput = entry.printOutput || entry.output;
return waitForMessages({
webconsole: hud,
messages: [{
name: "print() output: " + printOutput,
text: printOutput,
category: CATEGORY_OUTPUT,
}],
});
}
function* checkJSEval(entry)
{
hud.jsterm.clearOutput();
hud.jsterm.execute(entry.input);
let [result] = yield waitForMessages({
webconsole: hud,
messages: [{
name: "JS eval output: " + entry.output,
text: entry.output,
category: CATEGORY_OUTPUT,
}],
});
if (!entry.noClick) {
let msg = [...result.matched][0];
yield checkObjectClick(entry, msg);
}
}
function checkObjectClick(entry, msg)
{
let body = msg.querySelector(".body a") || msg.querySelector(".body");
ok(body, "the message body");
let deferred = promise.defer();
entry._onVariablesViewOpen = onVariablesViewOpen.bind(null, entry, deferred);
hud.jsterm.on("variablesview-open", entry._onVariablesViewOpen);
eventHandlers.add(entry._onVariablesViewOpen);
body.scrollIntoView();
EventUtils.synthesizeMouse(body, 2, 2, {}, hud.iframeWindow);
if (entry.inspectable) {
info("message body tagName '" + body.tagName + "' className '" + body.className + "'");
return deferred.promise; // wait for the panel to open if we need to.
}
return promise.resolve(null);
}
function onVariablesViewOpen(entry, deferred, event, view, options)
{
let label = entry.variablesViewLabel || entry.output;
if (typeof label == "string" && options.label != label) {
return;
}
if (label instanceof RegExp && !label.test(options.label)) {
return;
}
hud.jsterm.off("variablesview-open", entry._onVariablesViewOpen);
eventHandlers.delete(entry._onVariablesViewOpen);
entry._onVariablesViewOpen = null;
ok(entry.inspectable, "variables view was shown");
deferred.resolve(null);
}
return Task.spawn(runner);
}

View File

@ -0,0 +1,61 @@
<!DOCTYPE HTML>
<html dir="ltr" lang="en-US">
<head>
<meta charset="utf-8">
<title>Test the web console output - 02</title>
<!--
- Any copyright is dedicated to the Public Domain.
- http://creativecommons.org/publicdomain/zero/1.0/
-->
</head>
<body>
<p>hello world!</p>
<script type="text/javascript">
function testfn1() { return 42; }
var testobj1 = {
testfn2: function() { return 42; },
};
function testfn3() { return 42; }
testfn3.displayName = "testfn3DisplayName";
var array1 = [1, 2, 3, "a", "b", "c", "4", "5"];
var array2 = ["a", document, document.body, document.body.dataset,
document.body.classList];
var array3 = [1, window, null, "a", "b", undefined, false, "", -Infinity, testfn3, testobj1, "foo", "bar"];
var array4 = new Array(5);
array4.push("test");
array4.push(array4);
var typedarray1 = new Int32Array([1, 287, 8651, 40983, 8754]);
var set1 = new Set([1, 2, null, array3, "a", "b", undefined, document.head]);
set1.add(set1);
var testobj2 = {a: "b", c: "d", e: 1, f: "2"};
testobj2.foo = testobj1;
testobj2.bar = testobj2;
Object.defineProperty(testobj2, "getterTest", {
enumerable: true,
get: function() {
return 42;
},
});
var testobj3 = {a: "b", c: "d", e: 1, f: "2", g: true, h: null, i: undefined,
j: "", k: document.styleSheets, l: document.body.childNodes,
o: new Array(125), m: document.head};
var testobj4 = {a: "b", c: "d"};
Object.defineProperty(testobj4, "nonEnumerable", { value: "hello world" });
var map1 = new Map([["a", "b"], [document.body.children, testobj2]]);
map1.set(map1, set1);
</script>
</body>
</html>

View File

@ -0,0 +1,30 @@
<!DOCTYPE HTML>
<html dir="ltr" lang="en-US">
<head>
<meta charset="utf-8">
<title>Test the web console output - 03</title>
<!--
- Any copyright is dedicated to the Public Domain.
- http://creativecommons.org/publicdomain/zero/1.0/
-->
</head>
<body>
<p>hello world!</p>
<script type="text/javascript">
function testBodyClassName() {
document.body.className = "test1 tezt2";
return document.body;
}
function testBodyID() {
document.body.id = 'foobarid';
return document.body;
}
function testBodyDataset() {
document.body.dataset.preview = 'zuzu"<a>foo';
return document.body;
}
</script>
</body>
</html>

View File

@ -0,0 +1,77 @@
<!DOCTYPE HTML>
<html dir="ltr" lang="en-US">
<head>
<meta charset="utf-8">
<title>Test the web console output - 04</title>
<!--
- Any copyright is dedicated to the Public Domain.
- http://creativecommons.org/publicdomain/zero/1.0/
-->
</head>
<body>
<p>hello world!</p>
<script type="text/javascript">
function testTextNode() {
return document.querySelector("p").childNodes[0];
}
function testCommentNode() {
return document.head.childNodes[5];
}
function testDocumentFragment() {
var frag = document.createDocumentFragment();
var div = document.createElement("div");
div.id = "foo1";
div.className = "bar";
frag.appendChild(div);
var span = document.createElement("span");
span.id = "foo2";
span.textContent = "hello world";
div.appendChild(span);
var div2 = document.createElement("div");
div2.id = "foo3";
frag.appendChild(div2);
return frag;
}
function testError() {
try {
window.foobar("a");
} catch (ex) {
return ex;
}
return null;
}
function testDOMException() {
try {
var foo = document.querySelector("foo;()bar!");
} catch (ex) {
return ex;
}
return null;
}
function testCSSStyleDeclaration() {
document.body.style = 'color: green; font-size: 2em';
return document.body.style;
}
function testStyleSheetList() {
var style = document.querySelector("style");
if (!style) {
style = document.createElement("style");
style.textContent = "p, div { color: blue; font-weight: bold }\n" +
"@media print { p { background-color: yellow } }";
document.head.appendChild(style);
}
return document.styleSheets;
}
</script>
</body>
</html>

View File

@ -0,0 +1,23 @@
<!DOCTYPE HTML>
<html dir="ltr" lang="en-US">
<head>
<meta charset="utf-8">
<title>Test the web console output for DOM events</title>
<!--
- Any copyright is dedicated to the Public Domain.
- http://creativecommons.org/publicdomain/zero/1.0/
-->
</head>
<body>
<p>hello world!</p>
<script type="text/javascript">
function testDOMEvents() {
function eventLogger(ev) {
console.log("eventLogger", ev);
}
document.addEventListener("mousemove", eventLogger);
document.addEventListener("keypress", eventLogger);
}
</script>
</body>
</html>

View File

@ -4261,6 +4261,7 @@ JSTerm.prototype = {
popup.selectNextItem();
}
this.emit("autocomplete-updated");
aCallback && aCallback(this);
},