Source code
Revision control
Copy as Markdown
Other Tools
Test Info:
/* Any copyright is dedicated to the Public Domain.
"use strict";
const TEST_JSON_URL = URL_ROOT + "breadcrumb.json";
const TOTAL_ROWS = 4470;
add_task(async function () {
info("Test jsonview breadcrumbs");
await addJsonViewTab(TEST_JSON_URL);
info("Check that the breadcrumb is not rendered by default");
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb, null, "breadcrumb is not rendered");
});
info("Expand all nodes in the Json Panel");
await clickJsonNode(".jsonPanelBox .toolbar button.expand");
info("Check that the JSON tree is rendered correctly");
const count = await getElementCount(".jsonPanelBox .treeTable .treeRow");
is(count, TOTAL_ROWS, "There must be expected number of rows");
info("Check that the breadcrumb is displayed when selecting a row");
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info("Select the first row ('strings' object)");
content.document.querySelector(".treeRow:nth-child(1)").click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(breadcrumb.children.length, 1, "breadcrumb has 1 child (1 item)");
const breadcrumbItem = content.document.querySelector(".breadcrumb-item");
is(
breadcrumbItem.children.length,
2,
"breadcrumb has 2 children (1 image and 1 text)"
);
const breadcrumbIcon = content.document.querySelector(".breadcrumb-icon");
is(
breadcrumbIcon.className,
"breadcrumb-icon breadcrumb-icon-object",
"Breadcrumb icon is rendered"
);
const breadcrumbValue = content.document.querySelector(".breadcrumb-value");
is(breadcrumbValue.textContent, "strings", "Breadcrumb value is rendered");
});
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info("Select the second row ('name' string");
content.document.querySelector(".treeRow:nth-child(2)").click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(
breadcrumb.children.length,
3,
"breadcrumb has 3 children (2 items + 1 separator)"
);
const breadcrumbItems =
content.document.querySelectorAll(".breadcrumb-item");
is(breadcrumbItems.length, 2, "2 breadcrumb items are rendered");
const breadcrumbSeparator = content.document.querySelector(
".breadcrumb-separator"
);
is(breadcrumbSeparator !== null, true, "Separator is rendered");
const breadcrumbIcon2 = breadcrumbItems[1].childNodes[0];
is(
breadcrumbIcon2.className,
"breadcrumb-icon breadcrumb-icon-string",
"Breadcrumb icon is rendered"
);
const breadcrumbValue2 = breadcrumbItems[1].childNodes[1];
is(breadcrumbValue2.textContent, "name", "Breadcrumb value is rendered");
});
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info(
"Select the third row ('tricky\/path/with/separators' tricky key string)"
);
content.document.querySelector(".treeRow:nth-child(3)").click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(
breadcrumb.children.length,
3,
"breadcrumb has 3 children (2 items + 1 separator)"
);
const breadcrumbItems =
content.document.querySelectorAll(".breadcrumb-item");
is(breadcrumbItems.length, 2, "2 breadcrumb items are rendered");
const breadcrumbSeparator = content.document.querySelector(
".breadcrumb-separator"
);
is(breadcrumbSeparator !== null, true, "Separator is rendered");
const breadcrumbIcon2 = breadcrumbItems[1].childNodes[0];
is(
breadcrumbIcon2.className,
"breadcrumb-icon breadcrumb-icon-array",
"Breadcrumb icon is rendered"
);
const breadcrumbValue2 = breadcrumbItems[1].childNodes[1];
is(
breadcrumbValue2.textContent,
"tricky/path/with/separators",
"Breadcrumb value is rendered"
);
});
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info("Select the fourth row (1st item in array)");
content.document.querySelector(".treeRow:nth-child(4)").click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(
breadcrumb.children.length,
5,
"breadcrumb has 5 children (3 items + 2 separators)"
);
const breadcrumbItems =
content.document.querySelectorAll(".breadcrumb-item");
is(breadcrumbItems.length, 3, "3 breadcrumb items are rendered");
const breadcrumbSeparators = content.document.querySelectorAll(
".breadcrumb-separator"
);
is(breadcrumbSeparators.length, 2, "2 Separators are rendered");
const breadcrumbIcon3 = breadcrumbItems[2].childNodes[0];
is(
breadcrumbIcon3.className,
"breadcrumb-icon breadcrumb-icon-number",
"Breadcrumb icon is rendered"
);
const breadcrumbValue3 = breadcrumbItems[2].childNodes[1];
is(breadcrumbValue3.textContent, "0", "Breadcrumb value is rendered");
});
info("Check breadcrumb for all number types");
await assertNumber(6, "small");
await assertNumber(7, "big");
await assertNumber(8, "precise");
await assertNumber(9, "negzero");
await assertNumber(10, "zero");
await assertNumber(11, "exp");
info("Check breadcrumb for boolean values");
await assertBoolean(13, "true");
await assertBoolean(14, "false");
info("Check breadcrumb for null value");
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info("Select the 15th row (null value)");
content.document.querySelector(".treeRow:nth-child(15)").click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(breadcrumb.children.length, 1, "breadcrumb has 1 child (1 item)");
const breadcrumbItem =
content.document.querySelectorAll(".breadcrumb-item");
is(breadcrumbItem.length, 1, "1 breadcrumb items is rendered");
const breadcrumbIcon = breadcrumbItem[0].childNodes[0];
is(
breadcrumbIcon.className,
"breadcrumb-icon breadcrumb-icon-null",
"Breadcrumb icon is rendered"
);
const breadcrumbValue = breadcrumbItem[0].childNodes[1];
is(breadcrumbValue.textContent, "null", "Breadcrumb value is rendered");
});
info("Check breadcrumb for nested objects");
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info("Select the deepest row");
content.document.querySelector(".treeRow:nth-child(21)").click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(
breadcrumb.children.length,
11,
"breadcrumb has 11 children (6 items + 5 separators)"
);
const breadcrumbItems =
content.document.querySelectorAll(".breadcrumb-item");
is(breadcrumbItems.length, 6, "6 breadcrumb items are rendered");
const breadcrumbSeparators = content.document.querySelectorAll(
".breadcrumb-separator"
);
is(breadcrumbSeparators.length, 5, "5 Separators are rendered");
const expected = [
["object", "deep"],
["object", "two"],
["array", "three"],
["object", "0"],
["object", "four"],
["string", "five"],
];
for (let i = 0; i < 6; i++) {
const [iconType, valueText] = expected[i];
const breadcrumbIcon = breadcrumbItems[i].childNodes[0];
is(
breadcrumbIcon.className,
`breadcrumb-icon breadcrumb-icon-${iconType}`,
"Breadcrumb icon is rendered"
);
const breadcrumbValue = breadcrumbItems[i].childNodes[1];
is(
breadcrumbValue.textContent,
valueText,
"Breadcrumb value is rendered"
);
}
});
info("Check that breadcrumb skip bucket range");
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info("Select the 5th row (bucket range)");
content.document.querySelector(".treeRow:nth-child(25)").click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(
breadcrumb.children.length,
5,
"breadcrumb has 5 children (3 items + 2 separator)"
);
const breadcrumbItems =
content.document.querySelectorAll(".breadcrumb-item");
is(breadcrumbItems.length, 3, "3 breadcrumb items are rendered");
const breadcrumbSeparators = content.document.querySelectorAll(
".breadcrumb-separator"
);
is(breadcrumbSeparators.length, 2, "2 breadcrumb separators are rendered");
const expected = [
["breadcrumb-icon breadcrumb-icon-array", "bucket"],
["breadcrumb-icon breadcrumb-icon-object", "0"],
["breadcrumb-icon breadcrumb-icon-string", "name"],
];
for (let i = 0; i < breadcrumbItems.length; i++) {
const breadcrumbIcon = breadcrumbItems[i].childNodes[0];
const breadcrumbValue = breadcrumbItems[i].childNodes[1];
is(
breadcrumbIcon.className,
expected[i][0],
"Breadcrumb icon is rendered"
);
is(
breadcrumbValue.textContent,
expected[i][1],
"Breadcrumb value is rendered"
);
}
});
info("Check that breadcrumb properly react to filtering the tree");
// XXX use proper shortcut to focus the filter box
await sendString("numbers", ".jsonPanelBox .searchBox");
// The filtering is done asynchronously so, we need to wait.
await waitForFilter();
await SpecialPowers.spawn(gBrowser.selectedBrowser, [], function () {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(breadcrumb.children.length, 1, "breadcrumb has 1 child (1 item)");
const breadcrumbItem = content.document.querySelector(".breadcrumb-item");
is(breadcrumbItem !== null, true, "breadcrumb item is rendered");
const breadcrumbIcon = breadcrumbItem.childNodes[0];
is(
breadcrumbIcon.className,
"breadcrumb-icon breadcrumb-icon-object",
"Breadcrumb icon is rendered"
);
const breadcrumbValue = breadcrumbItem.childNodes[1];
is(breadcrumbValue.textContent, "numbers", "Breadcrumb value is rendered");
});
});
async function assertBoolean(row_number, boolean_type) {
await SpecialPowers.spawn(
gBrowser.selectedBrowser,
[row_number, boolean_type],
function (row_num, bool_type) {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info(`Select the ${row_num}th row ('${bool_type}' boolean)`);
content.document.querySelector(`.treeRow:nth-child(${row_num})`).click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(
breadcrumb.children.length,
3,
"breadcrumb has 3 children (2 items + 1 separator)"
);
const breadcrumbItems =
content.document.querySelectorAll(".breadcrumb-item");
is(breadcrumbItems.length, 2, "2 breadcrumb items are rendered");
const breadcrumbSeparator = content.document.querySelector(
".breadcrumb-separator"
);
is(breadcrumbSeparator !== null, true, "Separator is rendered");
const breadcrumbIcon2 = breadcrumbItems[1].childNodes[0];
is(
breadcrumbIcon2.className,
"breadcrumb-icon breadcrumb-icon-boolean",
"Breadcrumb icon is rendered"
);
const breadcrumbValue2 = breadcrumbItems[1].childNodes[1];
is(
breadcrumbValue2.textContent,
bool_type,
"Breadcrumb value is rendered"
);
}
);
}
async function assertNumber(row_number, number_type) {
await SpecialPowers.spawn(
gBrowser.selectedBrowser,
[row_number, number_type],
function (row_num, num_type) {
const tree = content.document.querySelector(".treeTable");
tree.focus();
is(tree, content.document.activeElement, "Tree should be focused");
info(`Select the ${row_num}th row ('${num_type}' number)`);
content.document.querySelector(`.treeRow:nth-child(${row_num})`).click();
const breadcrumb = content.document.querySelector(".json-breadcrumb");
is(breadcrumb !== null, true, "breadcrumb is rendered");
is(
breadcrumb.children.length,
3,
"breadcrumb has 3 children (2 items + 1 separator)"
);
const breadcrumbItems =
content.document.querySelectorAll(".breadcrumb-item");
is(breadcrumbItems.length, 2, "2 breadcrumb items are rendered");
const breadcrumbSeparator = content.document.querySelector(
".breadcrumb-separator"
);
is(breadcrumbSeparator !== null, true, "Separator is rendered");
const breadcrumbIcon2 = breadcrumbItems[1].childNodes[0];
is(
breadcrumbIcon2.className,
"breadcrumb-icon breadcrumb-icon-number",
"Breadcrumb icon is rendered"
);
const breadcrumbValue2 = breadcrumbItems[1].childNodes[1];
is(
breadcrumbValue2.textContent,
num_type,
"Breadcrumb value is rendered"
);
}
);
}