Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 28 additions & 0 deletions crates/mdbook-core/src/book.rs
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,14 @@ impl Book {
}
}

/// A depth-first iterator over each [`Chapter`], skipping draft chapters.
pub fn chapters(&self) -> impl Iterator<Item = &Chapter> {
self.iter().filter_map(|item| match item {
BookItem::Chapter(ch) if !ch.is_draft_chapter() => Some(ch),
_ => None,
})
}

/// Recursively apply a closure to each item in the book, allowing you to
/// mutate them.
///
Expand All @@ -61,6 +69,26 @@ impl Book {
for_each_mut(&mut func, &mut self.items);
}

/// Recursively apply a closure to each non-draft chapter in the book,
/// allowing you to mutate them.
pub fn for_each_chapter_mut<F>(&mut self, mut func: F)
where
F: FnMut(&mut Chapter),
{
for_each_mut(
&mut |item| {
let BookItem::Chapter(ch) = item else {
return;
};
if ch.is_draft_chapter() {
return;
}
func(ch)
},
&mut self.items,
);
}

/// Append a `BookItem` to the `Book`.
pub fn push_item<I: Into<BookItem>>(&mut self, item: I) -> &mut Self {
self.items.push(item.into());
Expand Down
17 changes: 6 additions & 11 deletions crates/mdbook-driver/src/builtin_renderers/markdown_renderer.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
use anyhow::{Context, Result};
use mdbook_core::book::BookItem;
use mdbook_core::utils;
use mdbook_renderer::{RenderContext, Renderer};
use std::fs;
Expand Down Expand Up @@ -33,16 +32,12 @@ impl Renderer for MarkdownRenderer {
}

trace!("markdown render");
for item in book.iter() {
if let BookItem::Chapter(ref ch) = *item {
if !ch.is_draft_chapter() {
utils::fs::write_file(
&ctx.destination,
ch.path.as_ref().expect("Checked path exists before"),
ch.content.as_bytes(),
)?;
}
}
for ch in book.chapters() {
utils::fs::write_file(
&ctx.destination,
ch.path.as_ref().expect("Checked path exists before"),
ch.content.as_bytes(),
)?;
}

fs::create_dir_all(destination)
Expand Down
8 changes: 1 addition & 7 deletions crates/mdbook-html/src/html_handlebars/hbs_renderer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -459,13 +459,7 @@ impl Renderer for HtmlHandlebars {
utils::fs::write_file(destination, "CNAME", format!("{cname}\n").as_bytes())?;
}

let chapters: Vec<_> = book
.iter()
.filter_map(|item| match item {
BookItem::Chapter(ch) if !ch.is_draft_chapter() => Some(ch),
_ => None,
})
.collect();
let chapters: Vec<_> = book.chapters().collect();
for (i, ch) in chapters.iter().enumerate() {
let previous = (i != 0).then(|| chapters[i - 1]);
let next = (i != chapters.len() - 1).then(|| chapters[i + 1]);
Expand Down
15 changes: 4 additions & 11 deletions crates/mdbook-html/src/html_handlebars/search.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ use super::static_files::StaticFiles;
use crate::theme::searcher;
use anyhow::{Context, Result, bail};
use elasticlunr::{Index, IndexBuilder};
use mdbook_core::book::{Book, BookItem, Chapter};
use mdbook_core::book::{Book, Chapter};
use mdbook_core::config::{Search, SearchChapterSettings};
use mdbook_core::utils;
use mdbook_markdown::HtmlRenderOptions;
Expand Down Expand Up @@ -43,11 +43,7 @@ pub(super) fn create_files(
let chapter_configs = sort_search_config(&search_config.chapter);
validate_chapter_config(&chapter_configs, book)?;

for item in book.iter() {
let chapter = match item {
BookItem::Chapter(ch) if !ch.is_draft_chapter() => ch,
_ => continue,
};
for chapter in book.chapters() {
if let Some(path) = settings_path(chapter) {
let chapter_settings = get_chapter_settings(&chapter_configs, path);
if !chapter_settings.enable.unwrap_or(true) {
Expand Down Expand Up @@ -349,11 +345,8 @@ fn validate_chapter_config(
) -> Result<()> {
for (path, _) in chapter_configs {
let found = book
.iter()
.filter_map(|item| match item {
BookItem::Chapter(ch) if !ch.is_draft_chapter() => settings_path(ch),
_ => None,
})
.chapters()
.filter_map(|ch| settings_path(ch))
.any(|source_path| source_path.starts_with(path));
if !found {
bail!(
Expand Down
16 changes: 4 additions & 12 deletions examples/remove-emphasis/mdbook-remove-emphasis/src/main.rs
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
//! This is a demonstration of an mdBook preprocessor which parses markdown
//! and removes any instances of emphasis.

use mdbook_preprocessor::book::{Book, BookItem, Chapter};
use mdbook_preprocessor::book::{Book, Chapter};
use mdbook_preprocessor::errors::Result;
use mdbook_preprocessor::{Preprocessor, PreprocessorContext};
use pulldown_cmark::{Event, Parser, Tag, TagEnd};
Expand Down Expand Up @@ -36,17 +36,9 @@ impl Preprocessor for RemoveEmphasis {

fn run(&self, _ctx: &PreprocessorContext, mut book: Book) -> Result<Book> {
let mut total = 0;
book.for_each_mut(|item| {
let BookItem::Chapter(ch) = item else {
return;
};
if ch.is_draft_chapter() {
return;
}
match remove_emphasis(&mut total, ch) {
Ok(s) => ch.content = s,
Err(e) => eprintln!("failed to process chapter: {e:?}"),
}
book.for_each_chapter_mut(|ch| match remove_emphasis(&mut total, ch) {
Ok(s) => ch.content = s,
Err(e) => eprintln!("failed to process chapter: {e:?}"),
});
eprintln!("removed {total} emphasis");
Ok(book)
Expand Down
10 changes: 2 additions & 8 deletions guide/guide-helper/src/lib.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
//! Preprocessor for the mdBook guide.

use mdbook_preprocessor::book::{Book, BookItem};
use mdbook_preprocessor::book::Book;
use mdbook_preprocessor::errors::Result;
use mdbook_preprocessor::{Preprocessor, PreprocessorContext};
use semver::{Version, VersionReq};
Expand Down Expand Up @@ -53,13 +53,7 @@ fn insert_version(book: &mut Book) {
let manifest: toml::Value = toml::from_str(&manifest_contents).unwrap();
let version = manifest["package"]["version"].as_str().unwrap();
const MARKER: &str = "{{ mdbook-version }}";
book.for_each_mut(|item| {
let BookItem::Chapter(ch) = item else {
return;
};
if ch.is_draft_chapter() {
return;
}
book.for_each_chapter_mut(|ch| {
if ch.content.contains(MARKER) {
ch.content = ch.content.replace(MARKER, version);
}
Expand Down
Loading