mirror of
https://github.com/servo/servo.git
synced 2025-08-02 20:20:14 +01:00
Add unit tests for revalidation selectors.
If these break, our cache may be subtly wrong in certain situations, which may be hard to detect. MozReview-Commit-ID: AXG2tpGnQ6k
This commit is contained in:
parent
25832b962f
commit
6e413653e7
1 changed files with 106 additions and 1 deletions
|
@ -4,15 +4,17 @@
|
|||
|
||||
use html5ever_atoms::LocalName;
|
||||
use selectors::parser::LocalName as LocalNameSelector;
|
||||
use selectors::parser::Selector;
|
||||
use servo_atoms::Atom;
|
||||
use std::sync::Arc;
|
||||
use style::properties::{PropertyDeclarationBlock, PropertyDeclaration};
|
||||
use style::properties::{longhands, Importance};
|
||||
use style::rule_tree::CascadeLevel;
|
||||
use style::selector_parser::SelectorParser;
|
||||
use style::selector_parser::{SelectorImpl, SelectorParser};
|
||||
use style::shared_lock::SharedRwLock;
|
||||
use style::stylesheets::StyleRule;
|
||||
use style::stylist::{Rule, SelectorMap};
|
||||
use style::stylist::needs_revalidation;
|
||||
use style::thread_state;
|
||||
|
||||
/// Helper method to get some Rules from selector strings.
|
||||
|
@ -56,6 +58,109 @@ fn get_mock_map(selectors: &[&str]) -> (SelectorMap, SharedRwLock) {
|
|||
(map, shared_lock)
|
||||
}
|
||||
|
||||
fn parse_selectors(selectors: &[&str]) -> Vec<Selector<SelectorImpl>> {
|
||||
selectors.iter()
|
||||
.map(|x| SelectorParser::parse_author_origin_no_namespace(x).unwrap().0
|
||||
.into_iter()
|
||||
.nth(0)
|
||||
.unwrap())
|
||||
.collect()
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_revalidation_selectors() {
|
||||
let test = parse_selectors(&[
|
||||
// Not revalidation selectors.
|
||||
"div",
|
||||
"#bar",
|
||||
"div:not(.foo)",
|
||||
"div span",
|
||||
"div > span",
|
||||
|
||||
// Attribute selectors.
|
||||
"div[foo]",
|
||||
"div:not([foo])",
|
||||
"div[foo = \"bar\"]",
|
||||
"div[foo ~= \"bar\"]",
|
||||
"div[foo |= \"bar\"]",
|
||||
"div[foo ^= \"bar\"]",
|
||||
"div[foo $= \"bar\"]",
|
||||
"div[foo *= \"bar\"]",
|
||||
"*|div[foo][bar = \"baz\"]",
|
||||
|
||||
// Non-state-based pseudo-classes.
|
||||
"div:empty",
|
||||
"div:first-child",
|
||||
"div:last-child",
|
||||
"div:only-child",
|
||||
"div:nth-child(2)",
|
||||
"div:nth-last-child(2)",
|
||||
"div:nth-of-type(2)",
|
||||
"div:nth-last-of-type(2)",
|
||||
"div:first-of-type",
|
||||
"div:last-of-type",
|
||||
"div:only-of-type",
|
||||
|
||||
// Note: it would be nice to test :moz-any and the various other non-TS
|
||||
// pseudo classes supported by gecko, but we don't have access to those
|
||||
// in these unit tests. :-(
|
||||
|
||||
// Sibling combinators.
|
||||
"span + div",
|
||||
"span ~ div",
|
||||
|
||||
// Revalidation selectors that will get sliced.
|
||||
"td > h1[dir]",
|
||||
"td > span + h1[dir]",
|
||||
"table td > span + div ~ h1[dir]",
|
||||
]).into_iter()
|
||||
.filter(|s| needs_revalidation(&s))
|
||||
.map(|s| s.inner.slice_to_first_ancestor_combinator().complex)
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
let reference = parse_selectors(&[
|
||||
// Attribute selectors.
|
||||
"div[foo]",
|
||||
"div:not([foo])",
|
||||
"div[foo = \"bar\"]",
|
||||
"div[foo ~= \"bar\"]",
|
||||
"div[foo |= \"bar\"]",
|
||||
"div[foo ^= \"bar\"]",
|
||||
"div[foo $= \"bar\"]",
|
||||
"div[foo *= \"bar\"]",
|
||||
"*|div[foo][bar = \"baz\"]",
|
||||
|
||||
// Non-state-based pseudo-classes.
|
||||
"div:empty",
|
||||
"div:first-child",
|
||||
"div:last-child",
|
||||
"div:only-child",
|
||||
"div:nth-child(2)",
|
||||
"div:nth-last-child(2)",
|
||||
"div:nth-of-type(2)",
|
||||
"div:nth-last-of-type(2)",
|
||||
"div:first-of-type",
|
||||
"div:last-of-type",
|
||||
"div:only-of-type",
|
||||
|
||||
// Sibling combinators.
|
||||
"span + div",
|
||||
"span ~ div",
|
||||
|
||||
// Revalidation selectors that got sliced.
|
||||
"h1[dir]",
|
||||
"span + h1[dir]",
|
||||
"span + div ~ h1[dir]",
|
||||
]).into_iter()
|
||||
.map(|s| s.inner.complex)
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
assert_eq!(test.len(), reference.len());
|
||||
for (t, r) in test.into_iter().zip(reference.into_iter()) {
|
||||
assert_eq!(t, r)
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_rule_ordering_same_specificity() {
|
||||
let (rules_list, _) = get_mock_rules(&["a.intro", "img.sidebar"]);
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue