Parses reStructuredText and generates HTML or VitePress-compatible Markdown
npm install rst-compilerThis is a reStructuredText parser and HTML/Markdown generator implemented in pure TypeScript.
`` ts
import fs from 'node:fs'
import { RstToHtmlCompiler } from 'rst-compiler'
const rst = fs.readFileSync('./index.rst').toString('utf-8')
const html = new RstToHtmlCompiler().compile(rst)
console.log(html.header) // Content that should be written to
Multiple Documents Usage
In order to resolve references that may exist in other documents, the compiler uses two-stage compilation:
`ts
const compiler = new RstToHtmlCompiler()// 1. The compiler first needs to parse each document into their respective ASTs
// References are NOT checked at this stage since the compiler does not know what other documents you may have
const doc1ParserOutput = compiler.parse(':doc:
See Document 2 <./foo>')
const doc2ParserOutput = compiler.parse('Document 2')// 2. The compiler then reads all the ASTs for your project in order to resolve references and generate HTML
const doc1Html = compiler.generate({
basePath: '/blog/', // Any links to other documents will be prefixed with this value
currentDocPath: 'index', // Relative to basePath
docs: [
{
docPath: 'index',
parserOutput: doc1ParserOutput,
},
{
docPath: 'foo',
parserOutput: doc2ParserOutput,
},
],
})
console.log(doc1Html.body) // See Document 2
`
Limitations
Since reStructuredText does not have a formal specification,
this program's behavior may deviate slightly from the reference implementation in Python's docutils library due to differences in parsing strategies.
* Only spaces can be used for indentation
* Third-party extensions and most directives and interpreted text roles from Sphinx are not available since they are implemented in Python
* It is not recommended to run the compiler on untrusted input as there is no XSS sanitation on the output.
In addition, the compiler makes extensive use of lookahead and lookbehind regular expressions which may cause ReDoS attacks.
Plugins
If you wish to add additional functionality, you should either implement custom Directives (for block-level output) or custom InterpretedTexts (for inline-level output).
`ts
import { RstCompilerPlugin } from 'rst-compiler'const plugin: RstCompilerPlugin = {
onInstall: (compiler) => {
compiler.useDirectiveGenerator({
directives: [
'custom-directive',
],
generate: (generatorState, node) => {
generatorState.visitNodes(node.children)
},
})
},
}
const compiler = new RstToHtmlCompiler()
compiler.usePlugin(plugin)
`All of the built-in Directives and InterpretedText in the compiler are implemented as plugins as well.
Please see the Plugins directory for example code.
InterpretedText Roles Supported
All standard text roles are supported.
In addition, the following text roles from Sphinx are supported:
$3
See sphinx for more information.
$3
See sphinx for more information.
$3
`rst
See :download:this example script .
``ts
const { downloads } = RstToHtmlCompiler.compile(rst)
console.log(downloads[0])
// {
// srcPath: '/example.py',
// destPath: '/_downloads/954c614a01144f97fd09b9c1d1dbc574fc10e6c0/example.py',
// }
`The output will be an
that links to the _downloads directory.
You will need to serve it with appropriate Content-Type headers that allow browsers to download the link.See sphinx for more information.
Directives Supported
$3
`rst
.. danger:: Beware killer rabbits!
`See docutils for more information.
$3
`rst
.. image:: picture.png
`See docutils for more information.
$3
`rst
.. only:: html and draft This text will only appear when html and draft fields in RstGeneratorOptions.outputEnv are true
``ts
RstToHtmlCompiler.compile(rst, {}, {
outputEnv: {
html: true,
draft: true,
},
})
`See sphinx for more information.
$3
`rst
.. code:: python def my_function():
"just a test"
print(8/2)
`By default, the HTML compiler will simply output plaintext inside
tags.shiki
If you wish to enable syntax highlighting, you will need to provide aobject inRstGeneratorOptions:`ts`
import { createHighlighter } from 'shiki'
import { RstToHtmlCompiler, RstGeneratorOptions } from 'rst-compiler'const generatorOptions: Partial
= {
shiki: {
theme: 'github-light',
highlighter: await createHighlighter({
langs: ['python', 'js'],
themes: ['github-light'],
}),
},
}RstToHtmlCompiler.compile(rst, {}, generatorOptions)
`See docutils for more information.
$3
rst`
.. math::\sin(x) = \sum_{n=0}^{\infty} \frac{(-1)^n x^{2n+1}}{(2n+1)!}
`ts`
const html = RstToHtmlCompiler.compile(rst)
console.log(html.header) // Will contain to katex's css`See docutils for more information.
$3
rst`
.. tabs::.. tab:: Label A
Text A
.. tab:: Label B
Text B
`ts
const html = RstToHtmlCompiler.compile(rst)
console.log(html.header) // Will contain