tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

commit 37b89fd45fb7083a6292bcd8ad031975e62cc314
parent 8c15e05f81970d6d2aec9807c7d427cbe7773eda
Author: Nicolas Chevobbe <nchevobbe@mozilla.com>
Date:   Tue,  4 Nov 2025 14:39:00 +0000

Bug 1997520 - [devtools] Use checkRuleViewContent in browser_rules_at_starting-style.js. r=devtools-reviewers,ochameau.

This allows us to remove the checks that we were doing for overridden properties as those are included in checkRuleViewContent.
checkRuleViewContent is slightly modified: we filter out .registered-properties for now, and we tweak the assertion messages
so failures are easier to debug.

Differential Revision: https://phabricator.services.mozilla.com/D270809

Diffstat:
Mdevtools/client/inspector/rules/test/browser_rules_at_starting-style.js | 343+++++++++++++++++++++++++++++++++++++++++++++----------------------------------
Mdevtools/client/inspector/rules/test/head.js | 20++++++++++++--------
2 files changed, 207 insertions(+), 156 deletions(-)

diff --git a/devtools/client/inspector/rules/test/browser_rules_at_starting-style.js b/devtools/client/inspector/rules/test/browser_rules_at_starting-style.js @@ -113,23 +113,30 @@ add_task(async function () { encodeURIComponent(TEST_URI) ); const { inspector, view } = await openRuleView(); - await assertRules("body", [ - { selector: `element`, ancestorRulesData: null }, + + await selectNode("body", inspector); + await checkRuleViewContent(view, [ + { selector: `element`, ancestorRulesData: null, declarations: [] }, { selector: `body, [data-test="in-starting-style"]`, ancestorRulesData: ["@starting-style {"], + declarations: [{ name: "color", value: "navy" }], }, { selector: `body, [data-test="in-starting-style-layer"]`, ancestorRulesData: ["@starting-style {", " @layer {"], + declarations: [{ name: "color", value: "hotpink", overridden: true }], }, + { header: "@property" }, ]); - await assertRules("h1", [ - { selector: `element`, ancestorRulesData: null }, + await selectNode("h1", inspector); + await checkRuleViewContent(view, [ + { selector: `element`, ancestorRulesData: null, declarations: [] }, { selector: `h1, [data-test="in-starting-style"]`, ancestorRulesData: ["@starting-style {"], + declarations: [{ name: "background-color", value: "salmon" }], }, { selector: ``, @@ -137,131 +144,222 @@ add_task(async function () { `h1, [data-test="top-level"] {`, " @starting-style {", ], + declarations: [{ name: "color", value: "gold" }], }, { selector: `h1, [data-test="top-level"]`, ancestorRulesData: null, + declarations: [ + { name: "color", value: "tomato" }, + { name: "transition", value: "all 1s" }, + ], }, + { header: "@property" }, ]); - await assertRules("main", [ - { selector: `element`, ancestorRulesData: null }, + await selectNode("main", inspector); + await checkRuleViewContent(view, [ + { selector: `element`, ancestorRulesData: null, declarations: [] }, { selector: ``, ancestorRulesData: [ `main, [data-test="top-level"] {`, " @starting-style {", ], + declarations: [ + { name: "--empty-start", value: "" }, + { + name: "background-color", + value: "goldenrod", + // background-color value in last starting-style rule is not overridden + overridden: false, + }, + { + name: "padding-top", + value: "3px", + // padding-top value in last starting-style rule is overridden by the !important + // set on the top level rule + overridden: true, + }, + { + name: "margin-top", + value: "3px", + // margin-top value in last starting-style rule is overridden by the !important set + // on another starting-style rule + overridden: true, + }, + { + name: "outline-color", + value: "goldenrod", + // outline-color value in last starting-style rule is overridden by the !important + // set on another starting-style rule + overridden: true, + }, + ], }, { selector: `main, [data-test="top-level"]`, ancestorRulesData: null, + declarations: [ + { name: "--my-color", value: "white" }, + { name: "--my-overridden-color", value: "white !important" }, + { name: "--my-registered-color", value: "white" }, + { name: "--empty-start", value: "1px" }, + { + name: "--check-my-overridden-color", + value: "var(--my-overridden-color)", + }, + { + name: "--check-my-registered-color", + value: "var(--my-registered-color)", + }, + { name: "--check-empty-start", value: "var(--empty-start)" }, + { name: "color", value: "var(--my-color)" }, + { + name: "background-color", + value: "firebrick", + // background-color value in top level rule is not overridden, even if the + // property is also set in a starting style rule + overridden: false, + }, + { + name: "padding-top", + value: "2px !important", + // padding-top value in top level rule is not overridden + overridden: false, + }, + { + name: "margin-top", + value: "2px", + // margin-top value in top level rule is not overridden + overridden: false, + }, + { name: "transition", value: "all 1s 1000s" }, + { + name: "outline-color", + value: "firebrick", + // outline-color value in top level rule is not overridden + overridden: false, + }, + { name: "outline-width", value: "5px" }, + { name: "outline-style", value: "solid" }, + { name: "outline-offset", value: "10px" }, + ], }, { selector: `main, [data-test="in-starting-style"]`, ancestorRulesData: ["@starting-style {"], + declarations: [ + { name: "--my-color", value: "black !important" }, + { name: "--my-overridden-color", value: "black", overridden: true }, + { name: "--my-registered-color", value: "black !important" }, + { name: "--check-my-color", value: "var(--my-color)" }, + { + name: "--check-my-overridden-color", + value: "var(--my-overridden-color)", + overridden: true, + }, + { + name: "--check-my-registered-color", + value: "var(--my-registered-color)", + overridden: true, + }, + { + name: "--check-my-unset-registered-color", + value: "var(--my-unset-registered-color)", + }, + { + name: "background-color", + value: "dodgerblue", + // background-color value in top-level starting style rule is overridden + overridden: true, + }, + { + name: "padding-top", + value: "1px", + // padding-top value in top-level starting style rule is overridden + overridden: true, + }, + { + name: "margin-top", + value: "1px !important", + // margin-top value in top-level starting style rule is not overridden, + // since it's declared with !important + overridden: false, + }, + { + name: "outline-color", + value: "dodgerblue", + // outline-color value in top-level starting style rule is overridden + overridden: true, + }, + ], }, { selector: `main, [data-test="in-starting-style-layer-2"]`, ancestorRulesData: [`@starting-style {`, " @layer {"], + declarations: [ + { + name: "background-color", + value: "cyan", + // background-color value in second layer in starting style rule is overridden + overridden: true, + }, + { + name: "padding-top", + value: "5px", + // padding-top value in second layer in starting style rule is overridden + overridden: true, + }, + { + name: "margin-top", + value: "5px", + // margin-top value in second layer in starting style rule is overridden + overridden: true, + }, + { + name: "outline-color", + value: "cyan !important", + // outline-color value in second layer in starting style rule is overridden even + // if it was declared with !important + overridden: true, + }, + ], }, { selector: `main, [data-test="in-starting-style-layer"]`, ancestorRulesData: [`@starting-style {`, " @layer {"], + declarations: [ + { + name: "background-color", + value: "forestgreen", + // background-color value in first layer in starting style rule is overridden + overridden: true, + }, + { + name: "padding-top", + value: "4px", + // padding-top value in first layer in starting style rule is overridden + overridden: true, + }, + { + name: "margin-top", + value: "4px", + // margin-top value in first layer in starting style rule is overridden + overridden: true, + }, + { + name: "outline-color", + value: "forestgreen !important", + // outline-color value in first layer in starting style rule is not overridden + // as it's declared with !important + overridden: false, + }, + ], }, + { header: "@property" }, ]); - await selectNode("main", inspector); - - info("Check that we're handling overridden properties correctly"); - //Check background-color - ok( - !isPropertyOverridden(view, 1, { "background-color": "goldenrod" }), - "background-color value in last starting-style rule is not overridden" - ); - ok( - !isPropertyOverridden(view, 2, { "background-color": "firebrick" }), - "background-color value in top level rule is not overridden, even if the property is also set in a starting style rule" - ); - ok( - isPropertyOverridden(view, 3, { "background-color": "dodgerblue" }), - "background-color value in top-level starting style rule is overridden" - ); - ok( - isPropertyOverridden(view, 4, { "background-color": "cyan" }), - "background-color value in second layer in starting style rule is overridden" - ); - ok( - isPropertyOverridden(view, 5, { "background-color": "forestgreen" }), - "background-color value in first layer in starting style rule is overridden" - ); - - //Check padding-top - ok( - isPropertyOverridden(view, 1, { "padding-top": "3px" }), - "padding-top value in last starting-style rule is overridden by the !important set on the top level rule" - ); - ok( - !isPropertyOverridden(view, 2, { "padding-top": "2px" }), - "padding-top value in top level rule is not overridden" - ); - ok( - isPropertyOverridden(view, 3, { "padding-top": "1px" }), - "padding-top value in top-level starting style rule is overridden" - ); - ok( - isPropertyOverridden(view, 4, { "padding-top": "5px" }), - "padding-top value in second layer in starting style rule is overridden" - ); - ok( - isPropertyOverridden(view, 5, { "padding-top": "4px" }), - "padding-top value in first layer in starting style rule is overridden" - ); - - //Check margin-top - ok( - isPropertyOverridden(view, 1, { "margin-top": "3px" }), - "margin-top value in last starting-style rule is overridden by the !important set on another starting-style rule" - ); - ok( - !isPropertyOverridden(view, 2, { "margin-top": "2px" }), - "margin-top value in top level rule is not overridden" - ); - ok( - !isPropertyOverridden(view, 3, { "margin-top": "1px" }), - "margin-top value in top-level starting style rule is not overridden, since it's declared with !important" - ); - ok( - isPropertyOverridden(view, 4, { "margin-top": "5px" }), - "margin-top value in second layer in starting style rule is overridden" - ); - ok( - isPropertyOverridden(view, 5, { "margin-top": "4px" }), - "margin-top value in first layer in starting style rule is overridden" - ); - - //Check outline-color - ok( - isPropertyOverridden(view, 1, { "outline-color": "goldenrod" }), - "outline-color value in last starting-style rule is overridden by the !important set on another startint-style rule" - ); - ok( - !isPropertyOverridden(view, 2, { "outline-color": "firebrick" }), - "outline-color value in top level rule is not overridden" - ); - ok( - isPropertyOverridden(view, 3, { "outline-color": "dodgerblue" }), - "outline-color value in top-level starting style rule is overridden" - ); - ok( - isPropertyOverridden(view, 4, { "outline-color": "cyan" }), - "outline-color value in second layer in starting style rule is overridden even if it was declared with !important" - ); - ok( - !isPropertyOverridden(view, 5, { "outline-color": "forestgreen" }), - "outline-color value in first layer in starting style rule is not overridden as it's declared with !important" - ); - info( "Check that CSS variables set in starting-style are not impacting the var() tooltip" ); @@ -494,57 +592,6 @@ add_task(async function () { startingStyleClasses: ["empty-css-variable"], } ); - - async function assertRules(nodeSelector, expectedRules) { - await selectNode(nodeSelector, inspector); - const rulesInView = Array.from( - // don't retrieve @property rules - view.element.querySelectorAll(".ruleview-rule:not([data-name])") - ); - is( - rulesInView.length, - expectedRules.length, - `[${nodeSelector}] All expected rules are displayed` - ); - - for (let i = 0; i < expectedRules.length; i++) { - const expectedRule = expectedRules[i]; - info(`[${nodeSelector}] Checking rule #${i}: ${expectedRule.selector}`); - - const selector = rulesInView[i].querySelector( - ".ruleview-selectors-container" - )?.innerText; - - is( - selector, - expectedRule.selector, - `[${nodeSelector}] Expected selector for rule #${i}` - ); - - const isInherited = rulesInView[i].matches( - ".ruleview-header-inherited + .ruleview-rule" - ); - if (expectedRule.inherited) { - ok(isInherited, `[${nodeSelector}] rule #${i} is inherited`); - } else { - ok(!isInherited, `[${nodeSelector}] rule #${i} is not inherited`); - } - - if (expectedRule.ancestorRulesData == null) { - is( - getRuleViewAncestorRulesDataElementByIndex(view, i), - null, - `[${nodeSelector}] No ancestor rules data displayed for ${selector}` - ); - } else { - is( - getRuleViewAncestorRulesDataTextByIndex(view, i), - expectedRule.ancestorRulesData.join("\n"), - `[${nodeSelector}] Expected ancestor rules data displayed for ${selector}` - ); - } - } - } }); function isPropertyOverridden(view, ruleIndex, property) { diff --git a/devtools/client/inspector/rules/test/head.js b/devtools/client/inspector/rules/test/head.js @@ -1392,9 +1392,13 @@ function getSmallIncrementKey() { * Pseudo-elements, …), the text of said header. */ function checkRuleViewContent(view, expectedElements) { - const rulesInView = Array.from(view.element.children); + const elementsInView = Array.from(view.element.children).filter( + // We don't check @property content for now + el => !el.classList.contains("registered-properties") + ); + is( - rulesInView.length, + elementsInView.length, expectedElements.length, "All expected elements are displayed" ); @@ -1403,7 +1407,7 @@ function checkRuleViewContent(view, expectedElements) { const expectedElement = expectedElements[i]; info(`Checking element #${i}: ${expectedElement.selector}`); - const elementInView = rulesInView[i]; + const elementInView = elementsInView[i]; if (expectedElement.header) { is( @@ -1447,7 +1451,7 @@ function checkRuleViewContent(view, expectedElements) { is( isInherited, expectedElement.inherited ?? false, - `Element #${i} (${selector}) is ${expectedElement.inherited ? "inherited" : "not inherited"}` + `Element #${i} ("${selector}") is ${expectedElement.inherited ? "inherited" : "not inherited"}` ); const declarations = elementInView.querySelectorAll(".ruleview-property"); @@ -1483,24 +1487,24 @@ function checkRuleViewContent(view, expectedElements) { is( ruleViewPropertyElement.classList.contains("ruleview-overridden"), !!expectedDeclaration?.overridden, - `"${selector}" ${propName.innerText} is ${expectedDeclaration?.overridden ? "overridden" : "not overridden"} ` + `Element #${i} ("${selector}") declaration #${j} ("${propName.innerText}: ${propValue.innerText}") is ${expectedDeclaration?.overridden ? "overridden" : "not overridden"} ` ); is( !!ruleViewPropertyElement.querySelector( ".ruleview-warning:not([hidden])" ), !!expectedDeclaration?.valid, - `"${selector}" ${propName.innerText} is ${expectedDeclaration?.valid === false ? "not valid" : "valid"}` + `Element #${i} ("${selector}") declaration #${j} ("${propName.innerText}: ${propValue.innerText}") is ${expectedDeclaration?.valid === false ? "not valid" : "valid"}` ); is( !!ruleViewPropertyElement.hasAttribute("dirty"), !!expectedDeclaration?.dirty, - `"${selector}" ${propName.innerText} is ${expectedDeclaration?.dirty ? "dirty" : "not dirty"}` + `Element #${i} ("${selector}") declaration #${j} ("${propName.innerText}: ${propValue.innerText}") is ${expectedDeclaration?.dirty ? "dirty" : "not dirty"}` ); is( ruleViewPropertyElement.querySelector(".ruleview-highlight") !== null, !!expectedDeclaration?.highlighted, - `"${selector}" ${propName.innerText} is ${expectedDeclaration?.highlighted ? "highlighted" : "not highlighted"} ` + `Element #${i} ("${selector}") declaration #${j} ("${propName.innerText}: ${propValue.innerText}") is ${expectedDeclaration?.highlighted ? "highlighted" : "not highlighted"} ` ); } }