#markdown #front-matter #markdown-parser #pulldown-cmark

pulldown-cmark-frontmatter

A Frontmatter extractor for Markdown documents

3 unstable releases

0.2.0 Sep 21, 2023
0.1.1 Mar 10, 2023
0.1.0 Jan 10, 2023

#785 in Parser implementations

Download history 15/week @ 2024-01-05 5/week @ 2024-01-12 2/week @ 2024-01-19 7/week @ 2024-02-16 174/week @ 2024-02-23 49/week @ 2024-03-01 20/week @ 2024-03-08 25/week @ 2024-03-15 32/week @ 2024-03-22 24/week @ 2024-03-29

101 downloads per month
Used in 3 crates

MIT/Apache

20KB
298 lines

pulldown-cmark-frontmatter

pulldown-cmark-frontmatter forbids unsafe code crate version Live Build Status HTML Coverage Report for main branch Documentation

This crate was written by someone unaffiliated with the pulldown-cmark crate.

This crate makes it easy to parse frontmatter contained within Markdown documents when using the pulldown-cmark Markdown parser.

Unlike many other frontmatter styles, this crate enforces a basic document format:

  • Optional top-level (h1) heading
  • Optional code block
  • Remaining Markdown document

By utilizing a code block instead of other markers, most Markdown editing software can more intelligently handle syntax highlighting, errors, and more.

The FrontmatterExtractor type will detect and return a plain-text representation of a top-level heading, if it's the first element in the document. The heading will still be returned when iterating over the pulldown_cmark::Events.

After the optional top-level heading, if a code block is encountered, it will be returned as Frontmatter::code_block. Unlike the heading, the frontmatter code block will not appear in the iterated Events.

This repository includes frontmatter-example.md which both the HTML rendering example and the extractor example use.

HTML Rendering Example

This example shows how to use this crate with pulldown-cmark's html module. It is included in the repository at examples/html.rs.

// This example renders the example Markdown to html using
// `pulldown_cmark::html`, while also extracting the frontmatter from
// Markdown.
let mut extractor = FrontmatterExtractor::new(pulldown_cmark::Parser::new(include_str!(
    "../frontmatter-example.md"
)));

// The only difference from using the FrontmatterExtractor and the regular
// pulldown_cmark::Parser is that you must pass a mutable reference to the
// extractor to be able to read the Frontmatter it extracts.
let mut rendered = String::new();
pulldown_cmark::html::push_html(&mut rendered, &mut extractor);
assert_eq!(rendered, include_str!("../frontmatter-example.html"));

let frontmatter = extractor.frontmatter.expect("frontmatter not detected");
assert_eq!(
    frontmatter.title.expect("title not detected"),
    "Frontmatter Example Document"
);
let code_block = frontmatter.code_block.expect("code block not detected");
assert_eq!(code_block.language.as_deref(), Some("toml"));
let attrs: ExampleAttributes = toml::from_str(&code_block.source).expect("invalid toml");
assert_eq!(attrs.author, "https://fosstodon.org/@ecton");

The repository includes the rendered html output to see what the produced HTML looks like.

Extractor Example

This example extracts the frontmatter from a Markdown document without parsing the entire document. It is included in the repository at examples/extractor.rs.

// This example extracts the frontmatter from the Markdown,
// `FrontmatterExtractor::extract()` which stops parsing the Markdown
// document after the frontmatter extraction is complete.
let extractor = FrontmatterExtractor::from_markdown(include_str!("../frontmatter-example.md"));
let frontmatter = extractor.extract().expect("frontmatter not detected");
assert_eq!(
    frontmatter.title.expect("title not detected"),
    "Frontmatter Example Document"
);
let code_block = frontmatter.code_block.expect("code block not detected");
assert_eq!(code_block.language.as_deref(), Some("toml"));
let attrs: ExampleAttributes = toml::from_str(&code_block.source).expect("invalid toml");
assert_eq!(attrs.author, "https://fosstodon.org/@ecton");

Open-source Licenses

This project, like all projects from Khonsu Labs, is open-source. This repository is available under the MIT License or the Apache License 2.0.

To learn more about contributing, please see CONTRIBUTING.md.

Dependencies

~1MB
~21K SLoC