Markdown to HTML Converter — Convert Markdown Files to HTML
Converting Markdown to HTML transforms markup syntax to web-ready HTML tags. Here's how to convert Markdown to HTML in JavaScript and Python, customize the output, and handle...
Converting Markdown to HTML means parsing Markdown syntax and generating the corresponding HTML tags. Every # becomes <h1>, every **text** becomes <strong>text</strong>, and code blocks become <pre><code> elements. The right library handles edge cases, security, and extensions automatically.
Use the Markdown Preview to write Markdown and see the HTML output in real time.
The conversion mapping
| Markdown | HTML output |
|---|---|
# Heading | <h1>Heading</h1> |
**bold** | <strong>bold</strong> |
*italic* | <em>italic</em> |
`code` | <code>code</code> |
[text](url) | <a href="url">text</a> |
 | <img alt="alt" src="src"> |
> quote | <blockquote><p>quote</p></blockquote> |
--- | <hr> |
- item | <ul><li>item</li></ul> |
1. item | <ol><li>item</li></ol> |
JavaScript: marked
marked is the most popular JavaScript Markdown parser:
npm install marked
import { marked } from 'marked';
const markdown = `
# Hello World
This is **bold** and *italic* text.
\`\`\`javascript
const greeting = 'Hello';
console.log(greeting);
\`\`\`
- Item one
- Item two
`;
// Basic conversion:
const html = marked(markdown);
console.log(html);
// With options:
import { marked, Renderer } from 'marked';
import hljs from 'highlight.js';
marked.setOptions({
breaks: true, // Convert single newlines to <br>
gfm: true, // GitHub Flavored Markdown
headerIds: true, // Add id attributes to headings
mangle: false, // Don't mangle header IDs
});
// Custom renderer for code blocks with syntax highlighting:
const renderer = new Renderer();
renderer.code = (code, language) => {
const highlighted = language && hljs.getLanguage(language)
? hljs.highlight(code, { language }).value
: hljs.highlightAuto(code).value;
return `<pre><code class="hljs language-${language}">${highlighted}</code></pre>`;
};
marked.use({ renderer });
const html = marked(markdown);
JavaScript: markdown-it
markdown-it is more extensible and CommonMark-compliant:
npm install markdown-it
import MarkdownIt from 'markdown-it';
const md = new MarkdownIt({
html: false, // Disable raw HTML in Markdown (security)
linkify: true, // Auto-convert URLs to links
typographer: true, // Smart quotes, dashes, etc.
});
// With plugins:
import markdownItAnchor from 'markdown-it-anchor';
import markdownItToc from 'markdown-it-toc-done-right';
md.use(markdownItAnchor, { permalink: true, permalinkSymbol: '#' });
md.use(markdownItToc, { containerClass: 'table-of-contents' });
const html = md.render(markdown);
markdown-it plugins
// Syntax highlighting (with shiki):
import Shiki from 'markdown-it-shiki';
md.use(Shiki, { theme: 'github-dark' });
// Math rendering (KaTeX):
import markdownItKatex from '@traptitech/markdown-it-katex';
md.use(markdownItKatex);
// Footnotes:
import markdownItFootnote from 'markdown-it-footnote';
md.use(markdownItFootnote);
// Container blocks:
import markdownItContainer from 'markdown-it-container';
md.use(markdownItContainer, 'warning', {
render: (tokens, idx) => {
return tokens[idx].nesting === 1
? '<div class="warning">'
: '</div>';
}
});
Python: markdown library
pip install markdown
import markdown
text = """
# Hello World
This is **bold** and *italic* text.
```python
def hello():
print("Hello!")
- Item one
- Item two """
Basic conversion:
html = markdown.markdown(text)
With extensions:
html = markdown.markdown(text, extensions=[
‘fenced_code’, # Fenced code blocks (```)
‘codehilite’, # Syntax highlighting (requires Pygments)
‘tables’, # GFM-style tables
‘toc’, # Table of contents
‘nl2br’, # Newlines to
‘attr_list’, # Add HTML attributes to elements
])
With config:
html = markdown.markdown(text, extensions=[ markdown.extensions.codehilite.CodeHiliteExtension( guess_lang=False, css_class=‘highlight’ ), ‘toc’, ], extension_configs={ ‘toc’: { ‘title’: ‘Table of Contents’, ‘permalink’: True, } })
## Python: mistune (fast alternative)
```bash
pip install mistune
import mistune
# Simple usage:
html = mistune.html(markdown_text)
# With plugins and options:
from mistune.plugins import plugin_table, plugin_task_lists
md = mistune.create_markdown(
plugins=[plugin_table, plugin_task_lists],
renderer=mistune.HTMLRenderer(escape=True) # Sanitize HTML
)
html = md(markdown_text)
Security: sanitizing HTML output
Never render untrusted Markdown directly to HTML without sanitization. A malicious user could inject:
<script>tags via raw HTML in Markdown- Event handlers via HTML attributes
- Links to
javascript:URLs
import { marked } from 'marked';
import DOMPurify from 'dompurify';
function renderMarkdown(markdown) {
const rawHtml = marked(markdown);
// Sanitize: remove <script>, onclick, javascript: links, etc.
return DOMPurify.sanitize(rawHtml);
}
// Or configure marked to strip HTML:
marked.setOptions({ sanitize: true }); // DEPRECATED in marked v5
// Better: use a separate sanitizer
Server-side sanitization (Node.js):
import sanitizeHtml from 'sanitize-html';
const clean = sanitizeHtml(rawHtml, {
allowedTags: ['h1', 'h2', 'h3', 'p', 'a', 'strong', 'em', 'ul', 'li', 'ol',
'code', 'pre', 'blockquote', 'img', 'br', 'hr', 'table', 'tr', 'td', 'th'],
allowedAttributes: {
a: ['href', 'title', 'target'],
img: ['src', 'alt', 'title'],
code: ['class'],
pre: ['class'],
}
});
Server-side vs client-side rendering
Server-side (recommended for SEO): Convert Markdown in your build process or server handler, send HTML to the client. The page is crawlable and loads without JavaScript.
Client-side: Parse Markdown in the browser. Useful for editors, live preview, and user-generated content. Requires the JavaScript bundle for the parser.
// Client-side (browser):
import { marked } from 'marked';
const textarea = document.getElementById('markdown-input');
const preview = document.getElementById('html-output');
textarea.addEventListener('input', () => {
preview.innerHTML = DOMPurify.sanitize(marked(textarea.value));
});
Related tools
- Markdown Preview — live Markdown to HTML preview
- Markdown Cheatsheet — Markdown syntax reference
- Markdown Editor Online — online editor guide
Related posts
- Markdown Cheatsheet — Every Syntax Element with Examples — Markdown uses simple symbols for headings, bold, links, code, and tables. Here's…
- Markdown Code Blocks — Syntax Highlighting and Fenced Code — Markdown code blocks use triple backticks to display formatted code. Add a langu…
- Markdown Editor Online — Write and Preview Markdown Instantly — An online Markdown editor shows the rendered output as you type, so you don't ne…
- Markdown Syntax — Complete Guide with Live Examples — Markdown syntax covers headings, bold, italic, links, images, code blocks, table…
Related tool
Live Markdown preview with GitHub-flavored syntax. Tables, task lists, code blocks, strikethrough. Side-by-side editor and rendered output.
Written by Mian Ali Khalid. Part of the Dev Productivity pillar.