dom/tests/browser/browser_ConsoleAPITests.js

Thu, 22 Jan 2015 13:21:57 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Thu, 22 Jan 2015 13:21:57 +0100
branch
TOR_BUG_9701
changeset 15
b8a032363ba2
permissions
-rw-r--r--

Incorporate requested changes from Mozilla in review:
https://bugzilla.mozilla.org/show_bug.cgi?id=1123480#c6

     1 /* vim:set ts=2 sw=2 sts=2 et: */
     2 /* This Source Code Form is subject to the terms of the Mozilla Public
     3  * License, v. 2.0. If a copy of the MPL was not distributed with this
     4  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
     6 const TEST_URI = "http://example.com/browser/dom/tests/browser/test-console-api.html";
     8 var gWindow, gLevel, gArgs, gTestDriver, gStyle;
    10 function test() {
    11   waitForExplicitFinish();
    13   var tab = gBrowser.addTab(TEST_URI);
    14   gBrowser.selectedTab = tab;
    15   var browser = gBrowser.selectedBrowser;
    17   registerCleanupFunction(function () {
    18     gWindow = gLevel = gArgs = gTestDriver = null;
    19     gBrowser.removeTab(tab);
    20   });
    22   ConsoleObserver.init();
    24   browser.addEventListener("DOMContentLoaded", function onLoad(event) {
    25     browser.removeEventListener("DOMContentLoaded", onLoad, false);
    26     executeSoon(function test_executeSoon() {
    27       gWindow = browser.contentWindow;
    28       consoleAPISanityTest();
    29       gTestDriver = observeConsoleTest();
    30       gTestDriver.next();
    31     });
    33   }, false);
    34 }
    36 function testConsoleData(aMessageObject) {
    37   let messageWindow = Services.wm.getOuterWindowWithId(aMessageObject.ID);
    38   is(messageWindow, gWindow, "found correct window by window ID");
    40   is(aMessageObject.level, gLevel, "expected level received");
    41   ok(aMessageObject.arguments, "we have arguments");
    43   switch (gLevel) {
    44     case "trace": {
    45       is(aMessageObject.arguments.length, 0, "arguments.length matches");
    46       is(aMessageObject.stacktrace.toSource(), gArgs.toSource(),
    47          "stack trace is correct");
    48       break
    49     }
    50     case "count": {
    51       is(aMessageObject.counter.label, gArgs[0].label, "label matches");
    52       is(aMessageObject.counter.count, gArgs[0].count, "count matches");
    53       break;
    54     }
    55     default: {
    56       is(aMessageObject.arguments.length, gArgs.length, "arguments.length matches");
    57       gArgs.forEach(function (a, i) {
    58         // Waive Xray so that we don't get messed up by Xray ToString.
    59         //
    60         // It'd be nice to just use XPCNativeWrapper.unwrap here, but there are
    61         // a number of dumb reasons we can't. See bug 868675.
    62         var arg = aMessageObject.arguments[i];
    63         if (Components.utils.isXrayWrapper(arg))
    64           arg = arg.wrappedJSObject;
    65         is(arg, a, "correct arg " + i);
    66       });
    68       if (gStyle) {
    69         is(aMessageObject.styles.length, gStyle.length, "styles.length matches");
    70         is(aMessageObject.styles + "", gStyle + "", "styles match");
    71       } else {
    72         ok(!aMessageObject.styles || aMessageObject.styles.length === 0,
    73            "styles match");
    74       }
    75     }
    76   }
    78   gTestDriver.next();
    79 }
    81 function testLocationData(aMessageObject) {
    82   let messageWindow = Services.wm.getOuterWindowWithId(aMessageObject.ID);
    83   is(messageWindow, gWindow, "found correct window by window ID");
    85   is(aMessageObject.level, gLevel, "expected level received");
    86   ok(aMessageObject.arguments, "we have arguments");
    88   is(aMessageObject.filename, gArgs[0].filename, "filename matches");
    89   is(aMessageObject.lineNumber, gArgs[0].lineNumber, "lineNumber matches");
    90   is(aMessageObject.functionName, gArgs[0].functionName, "functionName matches");
    91   is(aMessageObject.arguments.length, gArgs[0].arguments.length, "arguments.length matches");
    92   gArgs[0].arguments.forEach(function (a, i) {
    93     is(aMessageObject.arguments[i], a, "correct arg " + i);
    94   });
    96   startNativeCallbackTest();
    97 }
    99 function startNativeCallbackTest() {
   100   // Reset the observer function to cope with the fabricated test data.
   101   ConsoleObserver.observe = function CO_observe(aSubject, aTopic, aData) {
   102     try {
   103       testNativeCallback(aSubject.wrappedJSObject);
   104     } catch (ex) {
   105       // XXX Bug 906593 - Exceptions in this function currently aren't
   106       // reported, because of some XPConnect weirdness, so report them manually
   107       ok(false, "Exception thrown in CO_observe: " + ex);
   108     }
   109   };
   111   let button = gWindow.document.getElementById("test-nativeCallback");
   112   ok(button, "found #test-nativeCallback button");
   113   EventUtils.synthesizeMouseAtCenter(button, {}, gWindow);
   114 }
   116 function testNativeCallback(aMessageObject) {
   117   is(aMessageObject.level, "log", "expected level received");
   118   is(aMessageObject.filename, "", "filename matches");
   119   is(aMessageObject.lineNumber, 0, "lineNumber matches");
   120   is(aMessageObject.functionName, "", "functionName matches");
   122   startGroupTest();
   123 }
   125 function startGroupTest() {
   126   // Reset the observer function to cope with the fabricated test data.
   127   ConsoleObserver.observe = function CO_observe(aSubject, aTopic, aData) {
   128     try {
   129       testConsoleGroup(aSubject.wrappedJSObject);
   130     } catch (ex) {
   131       // XXX Bug 906593 - Exceptions in this function currently aren't
   132       // reported, because of some XPConnect weirdness, so report them manually
   133       ok(false, "Exception thrown in CO_observe: " + ex);
   134     }
   135   };
   136   let button = gWindow.document.getElementById("test-groups");
   137   ok(button, "found #test-groups button");
   138   EventUtils.synthesizeMouseAtCenter(button, {}, gWindow);
   139 }
   141 function testConsoleGroup(aMessageObject) {
   142   let messageWindow = Services.wm.getOuterWindowWithId(aMessageObject.ID);
   143   is(messageWindow, gWindow, "found correct window by window ID");
   145   ok(aMessageObject.level == "group" ||
   146      aMessageObject.level == "groupCollapsed" ||
   147      aMessageObject.level == "groupEnd",
   148      "expected level received");
   150   is(aMessageObject.functionName, "testGroups", "functionName matches");
   151   ok(aMessageObject.lineNumber >= 46 && aMessageObject.lineNumber <= 50,
   152      "lineNumber matches");
   153   if (aMessageObject.level == "groupCollapsed") {
   154     is(aMessageObject.groupName, "a group", "groupCollapsed groupName matches");
   155     is(aMessageObject.arguments[0], "a", "groupCollapsed arguments[0] matches");
   156     is(aMessageObject.arguments[1], "group", "groupCollapsed arguments[0] matches");
   157   }
   158   else if (aMessageObject.level == "group") {
   159     is(aMessageObject.groupName, "b group", "group groupName matches");
   160     is(aMessageObject.arguments[0], "b", "group arguments[0] matches");
   161     is(aMessageObject.arguments[1], "group", "group arguments[1] matches");
   162   }
   163   else if (aMessageObject.level == "groupEnd") {
   164     let groupName = Array.prototype.join.call(aMessageObject.arguments, " ");
   165     is(groupName,"b group", "groupEnd arguments matches");
   166     is(aMessageObject.groupName, "b group", "groupEnd groupName matches");
   167   }
   169   if (aMessageObject.level == "groupEnd") {
   170     startTimeTest();
   171   }
   172 }
   174 function startTraceTest() {
   175   gLevel = "trace";
   176   gArgs = [
   177     {filename: TEST_URI, functionName: "window.foobar585956c", language: 2, lineNumber: 6},
   178     {filename: TEST_URI, functionName: "foobar585956b", language: 2, lineNumber: 11},
   179     {filename: TEST_URI, functionName: "foobar585956a", language: 2, lineNumber: 15},
   180     {filename: TEST_URI, functionName: "onclick", language: 2, lineNumber: 1}
   181   ];
   183   let button = gWindow.document.getElementById("test-trace");
   184   ok(button, "found #test-trace button");
   185   EventUtils.synthesizeMouseAtCenter(button, {}, gWindow);
   186 }
   188 function startLocationTest() {
   189   // Reset the observer function to cope with the fabricated test data.
   190   ConsoleObserver.observe = function CO_observe(aSubject, aTopic, aData) {
   191     try {
   192       testLocationData(aSubject.wrappedJSObject);
   193     } catch (ex) {
   194       // XXX Bug 906593 - Exceptions in this function currently aren't
   195       // reported, because of some XPConnect weirdness, so report them manually
   196       ok(false, "Exception thrown in CO_observe: " + ex);
   197     }
   198   };
   199   gLevel = "log";
   200   gArgs = [
   201     {filename: TEST_URI, functionName: "foobar646025", arguments: ["omg", "o", "d"], lineNumber: 19}
   202   ];
   204   let button = gWindow.document.getElementById("test-location");
   205   ok(button, "found #test-location button");
   206   EventUtils.synthesizeMouseAtCenter(button, {}, gWindow);
   207 }
   209 function expect(level) {
   210   gLevel = level;
   211   gArgs = Array.slice(arguments, 1);
   212 }
   214 function observeConsoleTest() {
   215   let win = XPCNativeWrapper.unwrap(gWindow);
   216   expect("log", "arg");
   217   win.console.log("arg");
   218   yield undefined;
   220   expect("info", "arg", "extra arg");
   221   win.console.info("arg", "extra arg");
   222   yield undefined;
   224   expect("warn", "Lesson 1: PI is approximately equal to 3");
   225   win.console.warn("Lesson %d: %s is approximately equal to %1.0f",
   226                    1,
   227                    "PI",
   228                    3.14159);
   229   yield undefined;
   231   expect("warn", "Lesson 1: PI is approximately equal to 3.14");
   232   win.console.warn("Lesson %d: %s is approximately equal to %1.2f",
   233                    1,
   234                    "PI",
   235                    3.14159);
   236   yield undefined;
   238   expect("warn", "Lesson 1: PI is approximately equal to 3.141590");
   239   win.console.warn("Lesson %d: %s is approximately equal to %f",
   240                    1,
   241                    "PI",
   242                    3.14159);
   243   yield undefined;
   245   expect("warn", "Lesson 1: PI is approximately equal to 3.1415900");
   246   win.console.warn("Lesson %d: %s is approximately equal to %0.7f",
   247                    1,
   248                    "PI",
   249                    3.14159);
   250   yield undefined;
   252   expect("log", "%d, %s, %l");
   253   win.console.log("%d, %s, %l");
   254   yield undefined;
   256   expect("log", "%a %b %g");
   257   win.console.log("%a %b %g");
   258   yield undefined;
   260   expect("log", "%a %b %g", "a", "b");
   261   win.console.log("%a %b %g", "a", "b");
   262   yield undefined;
   264   expect("log", "2, a, %l", 3);
   265   win.console.log("%d, %s, %l", 2, "a", 3);
   266   yield undefined;
   268   // Bug #692550 handle null and undefined.
   269   expect("log", "null, undefined");
   270   win.console.log("%s, %s", null, undefined);
   271   yield undefined;
   273   // Bug #696288 handle object as first argument.
   274   let obj = { a: 1 };
   275   expect("log", obj, "a");
   276   win.console.log(obj, "a");
   277   yield undefined;
   279   expect("dir", win.toString());
   280   win.console.dir(win);
   281   yield undefined;
   283   expect("error", "arg");
   284   win.console.error("arg");
   285   yield undefined;
   287   expect("exception", "arg");
   288   win.console.exception("arg");
   289   yield undefined;
   291   expect("log", "foobar");
   292   gStyle = ["color:red;foobar;;"];
   293   win.console.log("%cfoobar", gStyle[0]);
   294   yield undefined;
   296   let obj4 = { d: 4 };
   297   expect("warn", "foobar", obj4, "test", "bazbazstr", "last");
   298   gStyle = [null, null, null, "color:blue;", "color:red"];
   299   win.console.warn("foobar%Otest%cbazbaz%s%clast", obj4, gStyle[3], "str", gStyle[4]);
   300   yield undefined;
   302   let obj3 = { c: 3 };
   303   expect("info", "foobar", "bazbaz", obj3, "%comg", "color:yellow");
   304   gStyle = [null, "color:pink;"];
   305   win.console.info("foobar%cbazbaz", gStyle[1], obj3, "%comg", "color:yellow");
   306   yield undefined;
   308   gStyle = null;
   309   let obj2 = { b: 2 };
   310   expect("log", "omg ", obj, " foo ", 4, obj2);
   311   win.console.log("omg %o foo %o", obj, 4, obj2);
   312   yield undefined;
   314   expect("assert", "message");
   315   win.console.assert(false, "message");
   316   yield undefined;
   318   expect("count", { label: "label a", count: 1 })
   319   win.console.count("label a");
   320   yield undefined;
   322   expect("count", { label: "label b", count: 1 })
   323   win.console.count("label b");
   324   yield undefined;
   326   expect("count", { label: "label a", count: 2 })
   327   win.console.count("label a");
   328   yield undefined;
   330   expect("count", { label: "label b", count: 2 })
   331   win.console.count("label b");
   332   yield undefined;
   334   startTraceTest();
   335   yield undefined;
   337   startLocationTest();
   338   yield undefined;
   339 }
   341 function consoleAPISanityTest() {
   342   let win = XPCNativeWrapper.unwrap(gWindow);
   343   ok(win.console, "we have a console attached");
   344   ok(win.console, "we have a console attached, 2nd attempt");
   346   ok(win.console.log, "console.log is here");
   347   ok(win.console.info, "console.info is here");
   348   ok(win.console.warn, "console.warn is here");
   349   ok(win.console.error, "console.error is here");
   350   ok(win.console.exception, "console.exception is here");
   351   ok(win.console.trace, "console.trace is here");
   352   ok(win.console.dir, "console.dir is here");
   353   ok(win.console.group, "console.group is here");
   354   ok(win.console.groupCollapsed, "console.groupCollapsed is here");
   355   ok(win.console.groupEnd, "console.groupEnd is here");
   356   ok(win.console.time, "console.time is here");
   357   ok(win.console.timeEnd, "console.timeEnd is here");
   358   ok(win.console.assert, "console.assert is here");
   359   ok(win.console.count, "console.count is here");
   360 }
   362 function startTimeTest() {
   363   // Reset the observer function to cope with the fabricated test data.
   364   ConsoleObserver.observe = function CO_observe(aSubject, aTopic, aData) {
   365     try {
   366       testConsoleTime(aSubject.wrappedJSObject);
   367     } catch (ex) {
   368       // XXX Bug 906593 - Exceptions in this function currently aren't
   369       // reported, because of some XPConnect weirdness, so report them manually
   370       ok(false, "Exception thrown in CO_observe: " + ex);
   371     }
   372   };
   373   gLevel = "time";
   374   gArgs = [
   375     {filename: TEST_URI, lineNumber: 23, functionName: "startTimer",
   376      arguments: ["foo"],
   377      timer: { name: "foo" },
   378     }
   379   ];
   381   let button = gWindow.document.getElementById("test-time");
   382   ok(button, "found #test-time button");
   383   EventUtils.synthesizeMouseAtCenter(button, {}, gWindow);
   384 }
   386 function testConsoleTime(aMessageObject) {
   387   let messageWindow = Services.wm.getOuterWindowWithId(aMessageObject.ID);
   388   is(messageWindow, gWindow, "found correct window by window ID");
   390   is(aMessageObject.level, gLevel, "expected level received");
   392   is(aMessageObject.filename, gArgs[0].filename, "filename matches");
   393   is(aMessageObject.lineNumber, gArgs[0].lineNumber, "lineNumber matches");
   394   is(aMessageObject.functionName, gArgs[0].functionName, "functionName matches");
   395   is(aMessageObject.timer.name, gArgs[0].timer.name, "timer.name matches");
   396   ok(aMessageObject.timer.started, "timer.started exists");
   398   gArgs[0].arguments.forEach(function (a, i) {
   399     is(aMessageObject.arguments[i], a, "correct arg " + i);
   400   });
   402   startTimeEndTest();
   403 }
   405 function startTimeEndTest() {
   406   // Reset the observer function to cope with the fabricated test data.
   407   ConsoleObserver.observe = function CO_observe(aSubject, aTopic, aData) {
   408     try {
   409       testConsoleTimeEnd(aSubject.wrappedJSObject);
   410     } catch (ex) {
   411       // XXX Bug 906593 - Exceptions in this function currently aren't
   412       // reported, because of some XPConnect weirdness, so report them manually
   413       ok(false, "Exception thrown in CO_observe: " + ex);
   414     }
   415   };
   416   gLevel = "timeEnd";
   417   gArgs = [
   418     {filename: TEST_URI, lineNumber: 27, functionName: "stopTimer",
   419      arguments: ["foo"],
   420      timer: { name: "foo" },
   421     },
   422   ];
   424   let button = gWindow.document.getElementById("test-timeEnd");
   425   ok(button, "found #test-timeEnd button");
   426   EventUtils.synthesizeMouseAtCenter(button, {}, gWindow);
   427 }
   429 function testConsoleTimeEnd(aMessageObject) {
   430   let messageWindow = Services.wm.getOuterWindowWithId(aMessageObject.ID);
   431   is(messageWindow, gWindow, "found correct window by window ID");
   433   is(aMessageObject.level, gLevel, "expected level received");
   434   ok(aMessageObject.arguments, "we have arguments");
   436   is(aMessageObject.filename, gArgs[0].filename, "filename matches");
   437   is(aMessageObject.lineNumber, gArgs[0].lineNumber, "lineNumber matches");
   438   is(aMessageObject.functionName, gArgs[0].functionName, "functionName matches");
   439   is(aMessageObject.arguments.length, gArgs[0].arguments.length, "arguments.length matches");
   440   is(aMessageObject.timer.name, gArgs[0].timer.name, "timer name matches");
   441   is(typeof aMessageObject.timer.duration, "number", "timer duration is a number");
   442   info("timer duration: " + aMessageObject.timer.duration);
   443   ok(aMessageObject.timer.duration >= 0, "timer duration is positive");
   445   gArgs[0].arguments.forEach(function (a, i) {
   446     is(aMessageObject.arguments[i], a, "correct arg " + i);
   447   });
   449   startEmptyTimerTest();
   450 }
   452 function startEmptyTimerTest() {
   453   // Reset the observer function to cope with the fabricated test data.
   454   ConsoleObserver.observe = function CO_observe(aSubject, aTopic, aData) {
   455     try {
   456       testEmptyTimer(aSubject.wrappedJSObject);
   457     } catch (ex) {
   458       // XXX Bug 906593 - Exceptions in this function currently aren't
   459       // reported, because of some XPConnect weirdness, so report them manually
   460       ok(false, "Exception thrown in CO_observe: " + ex);
   461     }
   462   };
   464   let button = gWindow.document.getElementById("test-namelessTimer");
   465   ok(button, "found #test-namelessTimer button");
   466   EventUtils.synthesizeMouseAtCenter(button, {}, gWindow);
   467 }
   469 function testEmptyTimer(aMessageObject) {
   470   let messageWindow = Services.wm.getOuterWindowWithId(aMessageObject.ID);
   471   is(messageWindow, gWindow, "found correct window by window ID");
   473   ok(aMessageObject.level == "time" || aMessageObject.level == "timeEnd",
   474      "expected level received");
   475   is(aMessageObject.arguments.length, 0, "we don't have arguments");
   476   ok(!aMessageObject.timer, "we don't have a timer");
   478   is(aMessageObject.functionName, "namelessTimer", "functionName matches");
   479   ok(aMessageObject.lineNumber == 31 || aMessageObject.lineNumber == 32,
   480      "lineNumber matches");
   481   // Test finished
   482   ConsoleObserver.destroy();
   483   finish();
   484 }
   486 var ConsoleObserver = {
   487   QueryInterface: XPCOMUtils.generateQI([Ci.nsIObserver]),
   489   init: function CO_init() {
   490     Services.obs.addObserver(this, "console-api-log-event", false);
   491   },
   493   destroy: function CO_destroy() {
   494     Services.obs.removeObserver(this, "console-api-log-event");
   495   },
   497   observe: function CO_observe(aSubject, aTopic, aData) {
   498     try {
   499       testConsoleData(aSubject.wrappedJSObject);
   500     } catch (ex) {
   501       // XXX Bug 906593 - Exceptions in this function currently aren't
   502       // reported, because of some XPConnect weirdness, so report them manually
   503       ok(false, "Exception thrown in CO_observe: " + ex);
   504     }
   505   }
   506 };
   508 function getWindowId(aWindow)
   509 {
   510   return aWindow.QueryInterface(Ci.nsIInterfaceRequestor)
   511                 .getInterface(Ci.nsIDOMWindowUtils)
   512                 .outerWindowID;
   513 }

mercurial