browser_console_variables_view.js 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204
  1. /* -*- indent-tabs-mode: nil; js-indent-level: 2 -*- */
  2. /* Any copyright is dedicated to the Public Domain.
  3. * http://creativecommons.org/publicdomain/zero/1.0/ */
  4. // Check that variables view works as expected in the web console.
  5. "use strict";
  6. const TEST_URI = "http://example.com/browser/devtools/client/webconsole/" +
  7. "test/test-eval-in-stackframe.html";
  8. var hud, gVariablesView;
  9. registerCleanupFunction(function () {
  10. hud = gVariablesView = null;
  11. });
  12. add_task(function* () {
  13. yield loadTab(TEST_URI);
  14. hud = yield openConsole();
  15. let msg = yield hud.jsterm.execute("(function foo(){})");
  16. ok(msg, "output message found");
  17. ok(msg.textContent.includes("function foo()"),
  18. "message text check");
  19. executeSoon(() => {
  20. EventUtils.synthesizeMouse(msg.querySelector("a"), 2, 2, {}, hud.iframeWindow);
  21. });
  22. let varView = yield hud.jsterm.once("variablesview-fetched");
  23. ok(varView, "object inspector opened on click");
  24. yield findVariableViewProperties(varView, [{
  25. name: "name",
  26. value: "foo",
  27. }], { webconsole: hud });
  28. });
  29. add_task(function* () {
  30. let msg = yield hud.jsterm.execute("fooObj");
  31. ok(msg, "output message found");
  32. ok(msg.textContent.includes('{ testProp: "testValue" }'),
  33. "message text check");
  34. let anchor = msg.querySelector("a");
  35. ok(anchor, "object link found");
  36. let fetched = hud.jsterm.once("variablesview-fetched");
  37. // executeSoon
  38. EventUtils.synthesizeMouse(anchor, 2, 2, {}, hud.iframeWindow);
  39. let view = yield fetched;
  40. let results = yield onFooObjFetch(view);
  41. let vView = yield onTestPropFound(results);
  42. let results2 = yield onFooObjFetchAfterUpdate(vView);
  43. let vView2 = yield onUpdatedTestPropFound(results2);
  44. let results3 = yield onFooObjFetchAfterPropRename(vView2);
  45. let vView3 = yield onRenamedTestPropFound(results3);
  46. let results4 = yield onPropUpdateError(vView3);
  47. yield onRenamedTestPropFoundAgain(results4);
  48. let prop = results4[0].matchedProp;
  49. yield testPropDelete(prop);
  50. });
  51. function onFooObjFetch(aVar) {
  52. gVariablesView = aVar._variablesView;
  53. ok(gVariablesView, "variables view object");
  54. return findVariableViewProperties(aVar, [
  55. { name: "testProp", value: "testValue" },
  56. ], { webconsole: hud });
  57. }
  58. function onTestPropFound(aResults) {
  59. let prop = aResults[0].matchedProp;
  60. ok(prop, "matched the |testProp| property in the variables view");
  61. is("testValue", aResults[0].value,
  62. "|fooObj.testProp| value is correct");
  63. // Check that property value updates work and that jsterm functions can be
  64. // used.
  65. return updateVariablesViewProperty({
  66. property: prop,
  67. field: "value",
  68. string: "document.title + window.location + $('p')",
  69. webconsole: hud
  70. });
  71. }
  72. function onFooObjFetchAfterUpdate(aVar) {
  73. info("onFooObjFetchAfterUpdate");
  74. let expectedValue = content.document.title + content.location +
  75. "[object HTMLParagraphElement]";
  76. return findVariableViewProperties(aVar, [
  77. { name: "testProp", value: expectedValue },
  78. ], { webconsole: hud });
  79. }
  80. function onUpdatedTestPropFound(aResults) {
  81. let prop = aResults[0].matchedProp;
  82. ok(prop, "matched the updated |testProp| property value");
  83. is(content.wrappedJSObject.fooObj.testProp, aResults[0].value,
  84. "|fooObj.testProp| value has been updated");
  85. // Check that property name updates work.
  86. return updateVariablesViewProperty({
  87. property: prop,
  88. field: "name",
  89. string: "testUpdatedProp",
  90. webconsole: hud
  91. });
  92. }
  93. function* onFooObjFetchAfterPropRename(aVar) {
  94. info("onFooObjFetchAfterPropRename");
  95. let expectedValue = yield ContentTask.spawn(gBrowser.selectedBrowser, {}, function* () {
  96. let para = content.wrappedJSObject.document.querySelector("p");
  97. return content.document.title + content.location + para;
  98. });
  99. // Check that the new value is in the variables view.
  100. return findVariableViewProperties(aVar, [
  101. { name: "testUpdatedProp", value: expectedValue },
  102. ], { webconsole: hud });
  103. }
  104. function onRenamedTestPropFound(aResults) {
  105. let prop = aResults[0].matchedProp;
  106. ok(prop, "matched the renamed |testProp| property");
  107. ok(!content.wrappedJSObject.fooObj.testProp,
  108. "|fooObj.testProp| has been deleted");
  109. is(content.wrappedJSObject.fooObj.testUpdatedProp, aResults[0].value,
  110. "|fooObj.testUpdatedProp| is correct");
  111. // Check that property value updates that cause exceptions are reported in
  112. // the web console output.
  113. return updateVariablesViewProperty({
  114. property: prop,
  115. field: "value",
  116. string: "foobarzFailure()",
  117. webconsole: hud
  118. });
  119. }
  120. function* onPropUpdateError(aVar) {
  121. info("onPropUpdateError");
  122. let expectedValue = yield ContentTask.spawn(gBrowser.selectedBrowser, {}, function* () {
  123. let para = content.wrappedJSObject.document.querySelector("p");
  124. return content.document.title + content.location + para;
  125. });
  126. // Make sure the property did not change.
  127. return findVariableViewProperties(aVar, [
  128. { name: "testUpdatedProp", value: expectedValue },
  129. ], { webconsole: hud });
  130. }
  131. function onRenamedTestPropFoundAgain(aResults) {
  132. let prop = aResults[0].matchedProp;
  133. ok(prop, "matched the renamed |testProp| property again");
  134. return waitForMessages({
  135. webconsole: hud,
  136. messages: [{
  137. name: "exception in property update reported in the web console output",
  138. text: "foobarzFailure",
  139. category: CATEGORY_OUTPUT,
  140. severity: SEVERITY_ERROR,
  141. }],
  142. });
  143. }
  144. function testPropDelete(aProp) {
  145. gVariablesView.window.focus();
  146. aProp.focus();
  147. executeSoon(() => {
  148. EventUtils.synthesizeKey("VK_DELETE", {}, gVariablesView.window);
  149. });
  150. return waitForSuccess({
  151. name: "property deleted",
  152. timeout: 60000,
  153. validator: () => !("testUpdatedProp" in content.wrappedJSObject.fooObj)
  154. });
  155. }