2 min readBy Shivraj Soni

Markdown-html parser

A small Rust crate that turns Markdown into HTML—lex, parse, render. No unsafe, no bloat.

RustCrate
View live

Markdown to HTML Parser in Rust

I wanted a minimal Markdown→HTML pipeline in Rust: something I could drop into a project without pulling in a huge library. So I built mark-html — a small crate that does lexing, parsing, and rendering in three clear stages. It’s not a full CommonMark implementation; it covers the bits I use most (headings, bold, italic, links, lists, code blocks) and stays deterministic and allocation-conscious. No unsafe.

Crate: mark-html · Version: 0.2.0


What it supports

  • Headings (#, ##, …)
  • Bold (**text**), italic (*text*)
  • Links [text](url)
  • Unordered lists (- item)
  • Inline code (backticks) and fenced code blocks with optional language

Parsing is deterministic; the parser avoids unsafe code. HTML sanitization is not included—if you render untrusted input, sanitize the output yourself.


Install

Add to Cargo.toml:

[dependencies]
mark-html = "0.2.0"

Or: cargo add mark-html


Usage

extern crate mark_html;

fn main() {
    let markdown = "## Hello, World!\n\nThis is a **test** of our *new* parser.\n\n- Item 1\n- Item 2";
    let html = mark_html::to_html(markdown);
    println!("{}", html);
}

API: pub fn to_html(input: &str) -> String — pass Markdown, get HTML.


How it’s built

Three stages, kept separate so adding features (e.g. blockquotes, ordered lists) doesn’t break existing behavior:

  1. Lexing — Scan the input into tokens. e.g. **hello**[BoldStart, Text("hello"), BoldEnd].
  2. Parsing — Turn tokens into an AST (e.g. a paragraph with bold/italic nodes).
  3. Rendering — Walk the AST and emit minimal HTML.

0.2.0 changes

  • Fenced code blocks with optional language.
  • Better handling of nested inline formatting (bold + italic).
  • Some lexer speedups.

Example

Input (Markdown):

# Main Title

This is a paragraph with **bold** and _italic_ text. Here is a [link to GitHub](https://github.com/Shivrajsoni).

- First list item
- Second list item

Output (HTML):

<h1>Main Title</h1>
<p>
  This is a paragraph with <strong>bold</strong> and <em>italic</em> text. Here
  is a <a href="https://github.com/Shivrajsoni">link to GitHub</a>.
</p>
<ul>
  <li>First list item</li>
  <li>Second list item</li>
</ul>

Roadmap

  • [x] Ordered lists, blockquotes, code block language classes
  • [ ] Tables, images

If you need a tiny, controllable Markdown→HTML pipeline in Rust, this might be enough.