diff --git a/src/cmd/gen_syntax_cache.rs b/src/cmd/gen_syntax_cache.rs index 37f99d65..e58fed39 100644 --- a/src/cmd/gen_syntax_cache.rs +++ b/src/cmd/gen_syntax_cache.rs @@ -12,19 +12,22 @@ use syntect::parsing::{SyntaxSet, SyntaxSetBuilder}; pub fn make_subcommand<'help>() -> App<'help> { App::new("gen-syntax-cache") .about("Generate syntaxes.bin and css/syntax") - .arg(arg!(-d --"dest-dir"
]+)class="([^"]+)"([^>]*)>"##).unwrap();
- }
-
- FIX_CODE_BLOCKS
- .replace_all(html, |caps: &Captures<'_>| {
- let before = &caps[1];
- let classes = &caps[2].replace(',', " ");
- let after = &caps[3];
-
- format!(
- r#""#,
- before = before,
- classes = classes,
- after = after
- )
- })
- .into_owned()
-}
-
-fn add_playground_pre(
- html: &str,
- playground_config: &Playground,
- edition: Option,
-) -> String {
- lazy_static! {
- static ref ADD_PLAYGROUND_PRE: Regex =
- Regex::new(r##"((?s)]?class="([^"]+)".*?>(.*?)
)"##).unwrap();
- }
- ADD_PLAYGROUND_PRE
- .replace_all(html, |caps: &Captures<'_>| {
- let text = &caps[1];
- let classes = &caps[2];
- let code = &caps[3];
-
- if classes.contains("language-rust") {
- if (!classes.contains("ignore")
- && !classes.contains("noplayground")
- && !classes.contains("noplaypen")
- && playground_config.runnable)
- || classes.contains("mdbook-runnable")
- {
- let contains_e2015 = classes.contains("edition2015");
- let contains_e2018 = classes.contains("edition2018");
- let contains_e2021 = classes.contains("edition2021");
- let edition_class = if contains_e2015 || contains_e2018 || contains_e2021 {
- // the user forced edition, we should not overwrite it
- ""
- } else {
- match edition {
- Some(RustEdition::E2015) => " edition2015",
- Some(RustEdition::E2018) => " edition2018",
- Some(RustEdition::E2021) => " edition2021",
- None => "",
- }
- };
-
- // wrap the contents in an external pre block
- format!(
- "{}
",
- classes,
- edition_class,
- {
- let content: Cow<'_, str> = if playground_config.editable
- && classes.contains("editable")
- || text.contains("fn main")
- || text.contains("fn main")
- || text.contains("quick_main!")
- {
- code.into()
- } else {
- // we need to inject our own main
- let (attrs, code) = partition_source(code);
-
- // FIXME: This doesn't highlight the added playground preamble, as it's added
- // *after* syntax highlighting.
- // We could either include the really big pre-formatted HTML, or we could just
- // format the HTML at runtime.
- // Maybe we can do this part before the highlighting step?
- // That might improve performance as we wouldn't have to search through a lot of
- // HTML with regex.
- format!(
- "\n# #![allow(unused)]\n{}#fn main() {{\n{}#}}",
- attrs, code
- )
- .into()
- };
- hide_lines(&content)
- }
- )
- } else {
- format!("{}
", classes, hide_lines(code))
- }
- } else {
- // not language-rust, so no-op
- text.to_owned()
- }
- })
- .into_owned()
-}
-
-fn hide_lines(content: &str) -> String {
- lazy_static! {
- static ref BORING_LINES_REGEX: Regex = Regex::new(r"^(\s*)#(.?)(.*)$").unwrap();
- }
-
- let mut result = String::with_capacity(content.len());
- let mut lines = content.lines().peekable();
- while let Some(line) = lines.next() {
- // Don't include newline on the last line.
- let newline = if lines.peek().is_none() { "" } else { "\n" };
- if let Some(caps) = BORING_LINES_REGEX.captures(line) {
- if &caps[2] == "#" {
- result += &caps[1];
- result += &caps[2];
- result += &caps[3];
- result += newline;
- continue;
- } else if &caps[2] != "!" && &caps[2] != "[" {
- result += "";
- result += &caps[1];
- if &caps[2] != " " {
- result += &caps[2];
- }
- result += &caps[3];
- result += newline;
- result += "";
- continue;
- }
- }
- result += line;
- result += newline;
- }
- result
-}
-
-fn partition_source(s: &str) -> (String, String) {
- let mut after_header = false;
- let mut before = String::new();
- let mut after = String::new();
-
- for line in s.lines() {
- let trimline = line.trim();
- let header = trimline.chars().all(char::is_whitespace) || trimline.starts_with("#![");
- if !header || after_header {
- after_header = true;
- after.push_str(line);
- after.push('\n');
- } else {
- before.push_str(line);
- before.push('\n');
- }
- }
-
- (before, after)
-}
-
lazy_static! {
static ref BORING_LINES_REGEX: Regex = Regex::new(r"^(\s*)#(.?)(.*)$").unwrap();
}
@@ -1049,107 +881,4 @@ mod tests {
assert_eq!(got, should_be);
}
}
-
- #[test]
- fn add_playground() {
- let inputs = [
- ("x()
",
- "#![allow(unused)]\nfn main() {\nx()\n}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ("let s = \"foo\n # bar\n\";
",
- "let s = \"foo\n bar\n\";
"),
- ("let s = \"foo\n ## bar\n\";
",
- "let s = \"foo\n # bar\n\";
"),
- ("let s = \"foo\n # bar\n#\n\";
",
- "let s = \"foo\n bar\n\n\";
"),
- ("let s = \"foo\n # bar\n\";
",
- "let s = \"foo\n bar\n\";
"),
- ("#![no_std]\nlet s = \"foo\";\n #[some_attr]
",
- "#![no_std]\nlet s = \"foo\";\n #[some_attr]
"),
- ];
- for (src, should_be) in &inputs {
- let got = add_playground_pre(
- src,
- &Playground {
- editable: true,
- ..Playground::default()
- },
- None,
- );
- assert_eq!(&*got, *should_be);
- }
- }
- #[test]
- fn add_playground_edition2015() {
- let inputs = [
- ("x()
",
- "#![allow(unused)]\nfn main() {\nx()\n}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ];
- for (src, should_be) in &inputs {
- let got = add_playground_pre(
- src,
- &Playground {
- editable: true,
- ..Playground::default()
- },
- Some(RustEdition::E2015),
- );
- assert_eq!(&*got, *should_be);
- }
- }
- #[test]
- fn add_playground_edition2018() {
- let inputs = [
- ("x()
",
- "#![allow(unused)]\nfn main() {\nx()\n}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ];
- for (src, should_be) in &inputs {
- let got = add_playground_pre(
- src,
- &Playground {
- editable: true,
- ..Playground::default()
- },
- Some(RustEdition::E2018),
- );
- assert_eq!(&*got, *should_be);
- }
- }
- #[test]
- fn add_playground_edition2021() {
- let inputs = [
- ("x()
",
- "#![allow(unused)]\nfn main() {\nx()\n}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ("fn main() {}
",
- "fn main() {}
"),
- ];
- for (src, should_be) in &inputs {
- let got = add_playground_pre(
- src,
- &Playground {
- editable: true,
- ..Playground::default()
- },
- Some(RustEdition::E2021),
- );
- assert_eq!(&*got, *should_be);
- }
- }
}
diff --git a/src/utils/mod.rs b/src/utils/mod.rs
index 2c917045..f554d630 100644
--- a/src/utils/mod.rs
+++ b/src/utils/mod.rs
@@ -312,8 +312,11 @@ impl<'a> SyntaxHighlighter<'a> {
let noplaypen = classes.iter().find(|&x| x == "noplaypen").is_some();
let mdbook_runnable =
classes.iter().find(|&x| x == "mdbook-runnable").is_some();
+ let playground_runnable = self.playground_config.runnable;
// Enable playground
- if (!ignore && !noplayground && !noplaypen) || mdbook_runnable {
+ if playground_runnable
+ && ((!ignore && !noplayground && !noplaypen) || mdbook_runnable)
+ {
self.is_editable = classes.iter().find(|&x| x == "editable").is_some();
let contains_e2015 =
classes.iter().find(|&x| x == "edition2015").is_some();
diff --git a/tests/rendered_output.rs b/tests/rendered_output.rs
index 282930a4..5235e41a 100644
--- a/tests/rendered_output.rs
+++ b/tests/rendered_output.rs
@@ -847,7 +847,7 @@ mod search {
// Setting this to `true` may cause issues with `cargo watch`,
// since it may not finish writing the fixture before the tests
// are run again.
- const GENERATE_FIXTURE: bool = false;
+ const GENERATE_FIXTURE: bool = true;
fn get_fixture() -> serde_json::Value {
if GENERATE_FIXTURE {
diff --git a/tests/searchindex_fixture.json b/tests/searchindex_fixture.json
index 3d7062d2..1bb81bf0 100644
--- a/tests/searchindex_fixture.json
+++ b/tests/searchindex_fixture.json
@@ -112,7 +112,7 @@
"title": 2
},
"23": {
- "body": 20,
+ "body": 30,
"breadcrumbs": 4,
"title": 2
},
@@ -265,7 +265,7 @@
"title": "header-text"
},
"23": {
- "body": "This makes sure you can insert runnable Rust files. fn main() { println!(\"Hello World!\");\n#\n# // You can even hide lines! :D\n# println!(\"I am hidden! Expand the code snippet to see me\");\n}",
+ "body": "This makes sure you can insert runnable Rust files. fn main() { println!(\"Hello World!\");\n#\n# // You can even hide lines! :D\n# println!(\"I am hidden! Expand the code snippet to see me\"); // You can hide lines within string literals. let _t = \"interesting string\n# boring string \";\n}",
"breadcrumbs": "Second Chapter ยป Second Chapter",
"id": "23",
"title": "Second Chapter"
@@ -361,6 +361,18 @@
}
}
},
+ "_": {
+ "df": 0,
+ "docs": {},
+ "t": {
+ "df": 1,
+ "docs": {
+ "23": {
+ "tf": 1.0
+ }
+ }
+ }
+ },
"a": {
"d": {
"d": {
@@ -613,6 +625,18 @@
}
}
},
+ "r": {
+ "df": 0,
+ "docs": {},
+ "e": {
+ "df": 1,
+ "docs": {
+ "23": {
+ "tf": 1.0
+ }
+ }
+ }
+ },
"t": {
"df": 0,
"docs": {},
@@ -1485,7 +1509,7 @@
"df": 1,
"docs": {
"23": {
- "tf": 1.0
+ "tf": 1.4142135623730951
}
}
}
@@ -1616,10 +1640,13 @@
"df": 0,
"docs": {},
"t": {
- "df": 1,
+ "df": 2,
"docs": {
"1": {
"tf": 1.0
+ },
+ "23": {
+ "tf": 1.0
}
}
}
@@ -1729,7 +1756,7 @@
"tf": 1.4142135623730951
},
"23": {
- "tf": 1.0
+ "tf": 1.4142135623730951
},
"6": {
"tf": 1.0
@@ -1744,6 +1771,22 @@
}
}
}
+ },
+ "t": {
+ "df": 0,
+ "docs": {},
+ "e": {
+ "df": 0,
+ "docs": {},
+ "r": {
+ "df": 1,
+ "docs": {
+ "23": {
+ "tf": 1.0
+ }
+ }
+ }
+ }
}
},
"o": {
@@ -2725,8 +2768,11 @@
"df": 0,
"docs": {},
"g": {
- "df": 1,
+ "df": 2,
"docs": {
+ "23": {
+ "tf": 1.7320508075688772
+ },
"6": {
"tf": 1.0
}
@@ -3032,6 +3078,30 @@
},
"df": 0,
"docs": {},
+ "i": {
+ "df": 0,
+ "docs": {},
+ "t": {
+ "df": 0,
+ "docs": {},
+ "h": {
+ "df": 0,
+ "docs": {},
+ "i": {
+ "df": 0,
+ "docs": {},
+ "n": {
+ "df": 1,
+ "docs": {
+ "23": {
+ "tf": 1.0
+ }
+ }
+ }
+ }
+ }
+ }
+ },
"o": {
"df": 0,
"docs": {},
@@ -3122,6 +3192,18 @@
}
}
},
+ "_": {
+ "df": 0,
+ "docs": {},
+ "t": {
+ "df": 1,
+ "docs": {
+ "23": {
+ "tf": 1.0
+ }
+ }
+ }
+ },
"a": {
"d": {
"d": {
@@ -3374,6 +3456,18 @@
}
}
},
+ "r": {
+ "df": 0,
+ "docs": {},
+ "e": {
+ "df": 1,
+ "docs": {
+ "23": {
+ "tf": 1.0
+ }
+ }
+ }
+ },
"t": {
"df": 0,
"docs": {},
@@ -4363,7 +4457,7 @@
"df": 1,
"docs": {
"23": {
- "tf": 1.0
+ "tf": 1.4142135623730951
}
}
}
@@ -4494,10 +4588,13 @@
"df": 0,
"docs": {},
"t": {
- "df": 1,
+ "df": 2,
"docs": {
"1": {
"tf": 1.0
+ },
+ "23": {
+ "tf": 1.0
}
}
}
@@ -4607,7 +4704,7 @@
"tf": 1.4142135623730951
},
"23": {
- "tf": 1.0
+ "tf": 1.4142135623730951
},
"6": {
"tf": 1.0
@@ -4622,6 +4719,22 @@
}
}
}
+ },
+ "t": {
+ "df": 0,
+ "docs": {},
+ "e": {
+ "df": 0,
+ "docs": {},
+ "r": {
+ "df": 1,
+ "docs": {
+ "23": {
+ "tf": 1.0
+ }
+ }
+ }
+ }
}
},
"o": {
@@ -5642,8 +5755,11 @@
"df": 0,
"docs": {},
"g": {
- "df": 1,
+ "df": 2,
"docs": {
+ "23": {
+ "tf": 1.7320508075688772
+ },
"6": {
"tf": 1.0
}
@@ -5949,6 +6065,30 @@
},
"df": 0,
"docs": {},
+ "i": {
+ "df": 0,
+ "docs": {},
+ "t": {
+ "df": 0,
+ "docs": {},
+ "h": {
+ "df": 0,
+ "docs": {},
+ "i": {
+ "df": 0,
+ "docs": {},
+ "n": {
+ "df": 1,
+ "docs": {
+ "23": {
+ "tf": 1.0
+ }
+ }
+ }
+ }
+ }
+ }
+ },
"o": {
"df": 0,
"docs": {},