Skip to content

Commit

Permalink
Fix an issue parsing known CSS properties with unknown values.
Browse files Browse the repository at this point in the history
We were failing to parse any future rules after failing to parse the
value, rather than skipping it and continuing.
  • Loading branch information
jugglerchris committed Dec 20, 2024
1 parent b9d0476 commit a6be2ea
Showing 1 changed file with 112 additions and 19 deletions.
131 changes: 112 additions & 19 deletions src/css/parser.rs
Original file line number Diff line number Diff line change
Expand Up @@ -424,40 +424,64 @@ pub(crate) fn parse_declaration(text: &str) -> IResult<&str, Option<Declaration>
))(text)?;
let decl = match prop.0.as_str() {
"background-color" => {
let value = parse_color(&value.tokens)?;
Decl::BackgroundColor { value }
if let Ok(value) = parse_color(&value.tokens) {
Decl::BackgroundColor { value }
} else {
Decl::Unknown { name: prop }
}
}
"background" => match parse_background_color(&value)? {
Some(value) => Decl::BackgroundColor { value },
"background" => match parse_background_color(&value) {
Ok(Some(value)) => Decl::BackgroundColor { value },
_ => Decl::Unknown { name: prop },
},
"color" => {
let value = parse_color(&value.tokens)?;
Decl::Color { value }
if let Ok(value) = parse_color(&value.tokens) {
Decl::Color { value }
} else {
Decl::Unknown { name: prop }
}
}
"height" => {
let value = parse_height(&value)?;
Decl::Height { value }
if let Ok(value) = parse_height(&value) {
Decl::Height { value }
} else {
Decl::Unknown { name: prop }
}
}
"max-height" => {
let value = parse_height(&value)?;
Decl::MaxHeight { value }
if let Ok(value) = parse_height(&value) {
Decl::MaxHeight { value }
} else {
Decl::Unknown { name: prop }
}
}
"overflow" => {
let value = parse_overflow(&value)?;
Decl::Overflow { value }
if let Ok(value) = parse_overflow(&value) {
Decl::Overflow { value }
} else {
Decl::Unknown { name: prop }
}
}
"overflow-y" => {
let value = parse_overflow(&value)?;
Decl::OverflowY { value }
if let Ok(value) = parse_overflow(&value) {
Decl::OverflowY { value }
} else {
Decl::Unknown { name: prop }
}
}
"display" => {
let value = parse_display(&value)?;
Decl::Display { value }
if let Ok(value) = parse_display(&value) {
Decl::Display { value }
} else {
Decl::Unknown { name: prop }
}
}
"white-space" => {
let value = parse_white_space(&value)?;
Decl::WhiteSpace { value }
if let Ok(value) = parse_white_space(&value) {
Decl::WhiteSpace { value }
} else {
Decl::Unknown { name: prop }
}
}
_ => Decl::Unknown {
name: prop,
Expand Down Expand Up @@ -893,7 +917,7 @@ pub(crate) fn parse_selector(text: &str) -> IResult<&str, Selector> {
parse_selector_without_element,
fail,
))(text)?;
// Reverse. Also remove any leading/trailing CombDescendent, as leading/trailing whitespace
// Reverse. Also remove any leading/trailing CombDescendant, as leading/trailing whitespace
// shouldn't count as a descendent combinator.
if let Some(&SelectorComponent::CombDescendant) = components.last() {
components.pop();
Expand Down Expand Up @@ -1086,6 +1110,20 @@ mod test {
]
))
);
assert_eq!(
super::parse_rules("color: inherit"),
Ok((
"",
vec![
Declaration {
data: Decl::Unknown {
name: PropertyName("color".into()),
},
important: Importance::Default,
},
]
))
);
}

#[test]
Expand Down Expand Up @@ -1262,6 +1300,61 @@ mod test {
);
}

#[test]
fn test_parse_multi_selector() {
assert_eq!(
super::parse_stylesheet(
"
.foo a .foo-bar2 { color: inherit; }
.foo a.foo-bar .foo-bar2 { color: #112233; }
"
),
Ok((
"",
vec![
RuleSet {
selectors: vec![Selector {
components: vec![
SelectorComponent::Class("foo-bar2".into()),
SelectorComponent::CombDescendant,
SelectorComponent::Element("a".into()),
SelectorComponent::CombDescendant,
SelectorComponent::Class("foo".into()),
],
},],
declarations: vec![
Declaration {
data: Decl::Unknown {
name: PropertyName("color".into()),
},
important: Importance::Default,
},
],
},
RuleSet {
selectors: vec![Selector {
components: vec![
SelectorComponent::Class("foo-bar2".into()),
SelectorComponent::CombDescendant,
SelectorComponent::Class("foo-bar".into()),
SelectorComponent::Element("a".into()),
SelectorComponent::CombDescendant,
SelectorComponent::Class("foo".into()),
],
},],
declarations: vec![
Declaration {
data: Decl::Color {
value: Colour::Rgb(0x11, 0x22, 0x33)
},
important: Importance::Default,
},
],
}]
))
);
}

#[test]
fn test_background() {
assert_eq!(
Expand Down

0 comments on commit a6be2ea

Please sign in to comment.