diff --git a/src/tests.rs b/src/tests.rs index fd5127d9..8efd1852 100644 --- a/src/tests.rs +++ b/src/tests.rs @@ -21,6 +21,20 @@ use super::{ ToCss, Token, TokenSerializationType, UnicodeRange, }; +// Fixtures are Cargo.toml `exclude`d so crates.io packages can compile tests +// without include_str!. Miri isolation cannot open() them, so keep +// include_str! on the miri path (git checkout only). +macro_rules! css_parsing_test_json { + ($path:tt) => {{ + #[cfg(miri)] + let s = String::from(include_str!($path)); + #[cfg(not(miri))] + let s = std::fs::read_to_string(&format!("{}/src/{}", env!("CARGO_MANIFEST_DIR"), $path)) + .unwrap(); + s + }}; +} + macro_rules! JArray { ($($e: expr,)*) => { JArray![ $( $e ),* ] }; ($($e: expr),*) => { Value::Array(vec!( $( $e.to_json() ),* )) } @@ -108,7 +122,7 @@ fn run_json_tests Value>(json_data: &str, parse: F) { #[test] fn component_value_list() { run_json_tests( - include_str!("css-parsing-tests/component_value_list.json"), + &css_parsing_test_json!("css-parsing-tests/component_value_list.json"), |input| Value::Array(component_values_to_json(input)), ); } @@ -116,7 +130,7 @@ fn component_value_list() { #[test] fn one_component_value() { run_json_tests( - include_str!("css-parsing-tests/one_component_value.json"), + &css_parsing_test_json!("css-parsing-tests/one_component_value.json"), |input| { let result: Result> = input.parse_entirely(|input| { Ok(one_component_value_to_json(input.next()?.clone(), input)) @@ -129,7 +143,7 @@ fn one_component_value() { #[test] fn declaration_list() { run_json_tests( - include_str!("css-parsing-tests/declaration_list.json"), + &css_parsing_test_json!("css-parsing-tests/declaration_list.json"), |input| { Value::Array( RuleBodyParser::new(input, &mut JsonParser) @@ -143,7 +157,7 @@ fn declaration_list() { #[test] fn one_declaration() { run_json_tests( - include_str!("css-parsing-tests/one_declaration.json"), + &css_parsing_test_json!("css-parsing-tests/one_declaration.json"), |input| { parse_one_declaration(input, &mut JsonParser).unwrap_or(JArray!["error", "invalid"]) }, @@ -152,31 +166,38 @@ fn one_declaration() { #[test] fn rule_list() { - run_json_tests(include_str!("css-parsing-tests/rule_list.json"), |input| { - Value::Array( - RuleBodyParser::new(input, &mut JsonParser) - .map(|result| result.unwrap_or(JArray!["error", "invalid"])) - .collect(), - ) - }); + run_json_tests( + &css_parsing_test_json!("css-parsing-tests/rule_list.json"), + |input| { + Value::Array( + RuleBodyParser::new(input, &mut JsonParser) + .map(|result| result.unwrap_or(JArray!["error", "invalid"])) + .collect(), + ) + }, + ); } #[test] fn stylesheet() { - run_json_tests(include_str!("css-parsing-tests/stylesheet.json"), |input| { - Value::Array( - StyleSheetParser::new(input, &mut JsonParser) - .map(|result| result.unwrap_or(JArray!["error", "invalid"])) - .collect(), - ) - }); + run_json_tests( + &css_parsing_test_json!("css-parsing-tests/stylesheet.json"), + |input| { + Value::Array( + StyleSheetParser::new(input, &mut JsonParser) + .map(|result| result.unwrap_or(JArray!["error", "invalid"])) + .collect(), + ) + }, + ); } #[test] fn one_rule() { - run_json_tests(include_str!("css-parsing-tests/one_rule.json"), |input| { - parse_one_rule(input, &mut JsonParser).unwrap_or(JArray!["error", "invalid"]) - }); + run_json_tests( + &css_parsing_test_json!("css-parsing-tests/one_rule.json"), + |input| parse_one_rule(input, &mut JsonParser).unwrap_or(JArray!["error", "invalid"]), + ); } #[test] @@ -200,7 +221,7 @@ fn stylesheet_from_bytes() { } run_raw_json_tests( - include_str!("css-parsing-tests/stylesheet_bytes.json"), + &css_parsing_test_json!("css-parsing-tests/stylesheet_bytes.json"), |input, expected| { let map = match input { Value::Object(map) => map, @@ -354,16 +375,19 @@ fn test_expect_url() { #[test] fn nth() { - run_json_tests(include_str!("css-parsing-tests/An+B.json"), |input| { - input - .parse_entirely(|i| { - let result: Result<_, ParseError<()>> = parse_nth(i).map_err(Into::into); - result - }) - .ok() - .map(|(v0, v1)| json!([v0, v1])) - .unwrap_or(Value::Null) - }); + run_json_tests( + &css_parsing_test_json!("css-parsing-tests/An+B.json"), + |input| { + input + .parse_entirely(|i| { + let result: Result<_, ParseError<()>> = parse_nth(i).map_err(Into::into); + result + }) + .ok() + .map(|(v0, v1)| json!([v0, v1])) + .unwrap_or(Value::Null) + }, + ); } #[test] @@ -383,29 +407,32 @@ fn parse_comma_separated_ignoring_errors() { #[test] fn unicode_range() { - run_json_tests(include_str!("css-parsing-tests/urange.json"), |input| { - let result: Result<_, ParseError<()>> = input.parse_comma_separated(|input| { - let result = UnicodeRange::parse(input).ok().map(|r| (r.start, r.end)); - if input.is_exhausted() { - Ok(result) - } else { - while input.next().is_ok() {} - Ok(None) - } - }); - result - .unwrap() - .iter() - .map(|v| { - if let Some((v0, v1)) = v { - json!([v0, v1]) + run_json_tests( + &css_parsing_test_json!("css-parsing-tests/urange.json"), + |input| { + let result: Result<_, ParseError<()>> = input.parse_comma_separated(|input| { + let result = UnicodeRange::parse(input).ok().map(|r| (r.start, r.end)); + if input.is_exhausted() { + Ok(result) } else { - Value::Null + while input.next().is_ok() {} + Ok(None) } - }) - .collect::>() - .to_json() - }); + }); + result + .unwrap() + .iter() + .map(|v| { + if let Some((v0, v1)) = v { + json!([v0, v1]) + } else { + Value::Null + } + }) + .collect::>() + .to_json() + }, + ); } #[test] @@ -420,7 +447,7 @@ fn serializer_preserving_comments() { fn serializer(preserve_comments: bool) { run_json_tests( - include_str!("css-parsing-tests/component_value_list.json"), + &css_parsing_test_json!("css-parsing-tests/component_value_list.json"), |input| { fn write_to( mut previous_token: TokenSerializationType,