Skip to content

Configuration

All options are passed via ConversionOptions (builder pattern in Rust, keyword arguments in Python/Ruby/Elixir/R, object literal in TypeScript, struct in Go/Java/C#, constructor in PHP).

Option Type Default Description
output_format "markdown" | "djot" | "plain" "markdown" Target output format. "plain" strips all markup and link targets, returning only visible text.
Option Type Default Description
heading_style "atx" | "underlined" | "atx_closed" "atx" ATX uses # prefixes (# H1). Underlined uses ===/--- for h1/h2. ATX closed adds trailing hashes (# H1 #).
Option Type Default Description
list_indent_type "spaces" | "tab" "spaces" Indentation character for nested lists.
list_indent_width int 2 Number of spaces per nesting level (when using spaces). Not range-checked by the core library.
bullets string "-*+" Characters to cycle through for unordered list markers. For example "-*+" uses - at level 1, * at level 2, + at level 3.
Option Type Default Description
strong_em_symbol "*" | "_" "*" Symbol used for bold (**text**) and italic (*text*).
newline_style "spaces" | "backslash" "spaces" How to render <br> tags: two trailing spaces or backslash at end of line.
sub_symbol string "" Symbol to wrap <sub> content (e.g. "~"~text~).
sup_symbol string "" Symbol to wrap <sup> content (e.g. "^"^text^).
highlight_style "double-equal" | "html" | "bold" | "none" "double-equal" Rendering of <mark> elements.
Option Type Default Description
escape_asterisks bool false Escape * characters in text.
escape_underscores bool false Escape _ characters in text.
escape_misc bool false Escape characters like [, ], <, >, #, etc.
escape_ascii bool false Escape all ASCII punctuation (strict CommonMark compliance).
Option Type Default Description
code_block_style "indented" | "backticks" | "tildes" "backticks" How to format multi-line code blocks.
code_language string "" Default language tag for fenced code blocks without an explicit language.
Option Type Default Description
autolinks bool true When link text equals the href, emit <url> instead of [url](url).
default_title bool false Use the href as link title when no title attribute is present.
link_style "inline" | "reference" "inline" inline emits [text](url). reference emits [text][1] with numbered definitions collected at the end of the document.
url_escape_style "angle" | "percent" "angle" Escaping for link/image URL destinations. angle wraps destinations containing spaces or newlines in <...>. percent percent-encodes every character that is not an RFC 3986 unreserved character or /.
Option Type Default Description
keep_inline_images_in array [] Element names where images should be kept as Markdown ![alt](src) rather than converted to alt text.
extract_images bool false Extract data URIs and embedded SVGs. Rust and WASM expose inline images when built with inline-images; generated native bindings may omit the Rust-only image payload.
skip_images bool false Drop image elements entirely. No ![alt](src) output, no alt-text fallback.
max_image_size int (bytes) 5242880 Maximum byte size for an extracted inline image. Larger images are skipped. 5 MB default.
capture_svg bool false Include inline <svg> elements in result.images when extract_images is enabled.
infer_dimensions bool true Infer missing width and height from decoded image bytes when extracting inline images.
Option Type Default Description
br_in_tables bool false Preserve line breaks in table cells as <br> rather than converting to spaces.
compact_tables bool false Emit tables without column padding (no aligned widths, --- separator per column). Token-efficient output for RAG / LLM contexts.
Option Type Default Description
whitespace_mode "normalized" | "strict" "normalized" normalized cleans excess whitespace; strict preserves whitespace as-is.
strip_newlines bool false Remove all newlines from input HTML before processing (useful for minified HTML).
Option Type Default Description
wrap bool false Enable line wrapping.
wrap_width int 80 Column width for line wrapping when wrap is enabled. Not range-checked by the core library; a value of 0 behaves as unlimited.
Option Type Default Description
convert_as_inline bool false Treat block-level elements as inline (no paragraph breaks).
strip_tags array [] Tags to strip entirely (only text content is preserved, no Markdown conversion).
preserve_tags array [] Tags to emit verbatim as HTML instead of converting to Markdown. Counterpart to strip_tags.
Option Type Default Description
max_depth int | null null Maximum DOM traversal depth. null uses the library’s internal native-stack safety limit (64). Values above the limit are clamped to an absolute ceiling (1024) to guard against stack overflow on pathologically deep input; there is no way to disable the depth limit entirely.
exclude_selectors array [] CSS selectors for elements to drop entirely, including all descendants (unlike strip_tags, which keeps the text content). Supports tag names, .class, #id, [attribute], etc. Invalid selectors are silently skipped at conversion time.
tier_strategy "auto" | "tier2" "auto" Which internal conversion path to use. auto runs a fast byte-scanner (Tier 1) when eligible and falls back to the full DOM walk (Tier 2) otherwise. tier2 always uses the DOM-walk path. Not exposed as a stable option in every binding.

Conversion output is not sanitized. There is no configurable cap on input size — callers that accept HTML from untrusted sources are responsible for enforcing their own size limits before calling convert(). See Security.

Option Type Default Description
encoding string "utf-8" CLI only. Character encoding of the input file or stdin. The value must be a label that the WHATWG Encoding Standard recognises ("windows-1252", "shift_jis", "iso-8859-1", etc.). The core library stores but does not use this field; decoding happens in the CLI before the string reaches convert().
Option Type Default Description
debug bool false CLI only. When true, the CLI prints diagnostic lines to stderr after each conversion (e.g. "Generated 1234 bytes of markdown"). The core library stores but does not act on this field.
Option Type Default Description
extract_metadata bool true Populate result.metadata (title, description, Open Graph, Twitter Card, JSON-LD, links, images). Table extraction into result.tables runs unconditionally — it is not gated by this flag.
Option Type Default Description
include_document_structure bool false Populate result.document with a parsed tree of headings, paragraphs, lists, and tables.

preprocessing is a nested PreprocessingOptions value (Rust field names shown below; bindings expose the same sub-fields as keyword arguments or a nested object). The CLI uses different flag names for the same settings (--preprocess, --keep-navigation, --keep-forms) — those CLI-only names do not exist on ConversionOptions; see CLI Reference.

Option Type Default Description
enabled bool true Enable HTML preprocessing globally. Required for the options below to have an effect.
preset "minimal" | "standard" | "aggressive" "standard" Preset level carried through for forward compatibility. Current releases honour the boolean flags below and do not branch on preset.
remove_navigation bool true Remove <nav>, and remove <header>/<footer>/<aside> that otherwise look like navigation.
remove_forms bool true Accepted and stored. Current releases do not drop form elements during preprocessing regardless of this flag.

When enabled is true and remove_navigation is true (the default for both), the preprocessor drops:

  • every <nav> element
  • <header> elements outside a semantic content ancestor (<article>, <main>, etc.)
  • <header>, <footer>, and <aside> that carry navigation hints in their class or id attributes (menu, sidebar, breadcrumb, and similar)

Script and style tags are always stripped before the DOM walk starts, independent of enabled.

Given this HTML:

<h1>Report</h1>
<p>
See <a href="https://example.com"><strong>example</strong></a
>.
</p>
# Report
See [**example**](https://example.com).

markdown and djot both preserve structure and link targets. djot uses single-asterisk strong emphasis; markdown uses double asterisks. plain strips all formatting, link targets, and list markers, returning readable text only.

use html_to_markdown_rs::{convert, CodeBlockStyle, ConversionOptions, HeadingStyle};
let options = ConversionOptions::builder()
.heading_style(HeadingStyle::Atx)
.code_block_style(CodeBlockStyle::Backticks)
.wrap(true)
.wrap_width(80)
.extract_metadata(true)
.build();
let result = convert(html, Some(options))?;

Found a bug or mistake on this page?

If something here is wrong or out of date, open an issue on GitHub or contribute a fix via pull request.