235

我讨厌 reST,但喜欢 Sphinx。有没有办法让 Sphinx 读取 Markdown 而不是 reStructuredText?

4

12 回答 12

108

您可以在同一个 Sphinx 项目中使用 Markdown 和 reStructuredText。如何做到这一点在Sphinx 文档中有简要说明。

安装myst-parser( pip install myst-parser) 然后编辑conf.py

# simply add the extension to your list of extensions
extensions = ['myst_parser']

source_suffix = ['.rst', '.md']

在 Github (serra/sphinx-with-markdown) 上创建了一个小示例项目,展示了它是如何工作的。它使用 Sphinx 3.5.4 版和 myst-parser 0.14.0 版。

事实上,MyST 解析器允许您在 Markdown 中编写整个 Sphinx 文档。它支持指令并有几个扩展,您可以通过 conf.py 中的配置启用。

MyST 解析器需要 Sphinx 2.1 或更高版本。对于 Sphinx 的早期版本,您可以使用recommonmark在 Sphinx 中使用 Markdown 。查看此答案的早期版本以了解如何操作。

于 2015-11-19T07:40:50.447 回答
104

这样做的“正确”方法是为降价编写一个docutils 解析器。(加上一个 Sphinx 选项来选择解析器。)它的美妙之处在于对所有 docutils 输出格式的即时支持(但您可能不关心这一点,因为大多数已经存在类似的降价工具)。无需从头开始开发解析​​器的方法:

  1. 您可以作弊并编写一个“解析器”,使用Pandoc将 Markdown 转换为 RST 并将其传递给 RST 解析器:-)。

  2. 您可以使用现有的 markdown->XML 解析器并将结果(使用 XSLT?)转换为 docutils 模式。

  3. 您可以使用一些现有的 python markdown 解析器,让您定义自定义渲染器并使其构建 docutils 节点树。

  4. 您可以分叉现有的 RST 阅读器,删除与降价无关的所有内容并更改不同的语法(这种比较可能会有所帮助)...
    编辑:除非您准备好对其进行大量测试,否则我不推荐这条路线。Markdown 已经有太多微妙不同的方言了,这可能会导致另一个...

更新: https ://github.com/sgenoud/remarkdown是 docutils 的降价阅读器。它没有采用上述任何捷径,而是使用受peg-markdown启发的Parsley PEG 语法。

更新:https ://github.com/readthedocs/recommonmark是另一个 docutils 阅读器,ReadTheDocs 原生支持。 派生自 remarkdown 但使用CommonMark-py解析器。

  • 可以将特定的或多或少的自然 Markdown 语法转换为适当的结构,例如指向目录树的链接列表。* 没有角色的通用本机语法。
  • 支持嵌入任何rST 内容,包括指令,带有```eval_rst围栏块以及指令的简写DIRECTIVE_NAME:: ...

更新MyST是另一个文档/狮身人面像阅读器。基于 markdown-it-py,兼容 CommonMark。

  • 具有{ROLE_NAME}`...`角色的通用语法。
  • 具有用于带有 ```{DIRECTIVE_NAME} ...防护块的指令的通用语法。

所有情况下,您都需要发明 Markdown 的扩展来表示Sphinx 指令和角色。虽然您可能不需要所有这些,但其中一些.. toctree::是必不可少的。
我认为这是最难的部分。在 Sphinx 扩展之前的 reStructuredText 已经比 markdown 更丰富了。即使是大量扩展的降价,例如pandoc,也主要是 rST 功能集的一个子集。这是一个很大的基础!

实现方面,最简单的事情是添加一个通用结构来表达任何 docutils 角色/指令。语法灵感的明显候选者是:

  • 属性语法,pandoc 和其他一些实现已经允许在许多内联和块结构上使用。例如`foo`{.method}-> `foo`:method:
  • HTML/XML。从<span class="method">foo</span>插入 docutils 内部 XML 的最笨拙的方法!
  • 某种用于指令的 YAML?

但是这样的通用映射不会是最降价的解决方案......目前最活跃的讨论降价扩展的地方是https://groups.google.com/forum/#!topic/pandoc-discusshttps:// github.com/scholmd/scholmd/

这也意味着您不能只重用降价解析器而不以某种方式扩展它。Pandoc 通过支持自定义过滤器再次不辜负其文件转换的瑞士军刀的美誉。(事实上​​,如果我要解决这个问题,我会尝试在 docutils 阅读器/变压器/编写器和 pandoc 阅读器/过滤器/编写器之间建立一个通用的桥梁。这比你需要的要多,但回报会比狮身人面像/降价。)


另一种疯狂的想法:不是扩展 markdown 来处理 Sphinx,而是扩展 reStructuredText 以支持(大部分)markdown 的超集!美妙之处在于您将能够按原样使用任何 Sphinx 功能,但能够在 markdown 中编写大部分内容。

已经有相当多的语法重叠;最值得注意的是链接语法不兼容。我认为,如果您为降价链接和样式标题添加对 RST 的支持###,并将默认`backticks`角色更改为文字,并且可能将缩进块更改为文字(现在 RST 支持> ...引号),您将获得支持大多数降价的可用内容.

于 2010-03-21T16:53:55.687 回答
34

这不使用 Sphinx,但MkDocs将使用 Markdown 构建您的文档。我也讨厌 rst,到目前为止,我真的很喜欢 MkDocs。

于 2014-04-07T17:36:12.863 回答
33

2021 年 5 月更新:不推荐使用recommonmark ,取而代之的是 myst-parser(感谢 astrojuanlu)

更新:现在正式支持并记录在sphinx docs中。

看起来一个基本的实现已经进入了 Sphinx,但还没有得到消息。见github问题评论

安装依赖:

pip install commonmark recommonmark

调整conf.py

source_parsers = {
    '.md': 'recommonmark.parser.CommonMarkParser',
}
source_suffix = ['.rst', '.md']
于 2016-03-19T16:02:59.227 回答
20

Markdown 和 ReST 做不同的事情。

RST 提供了一个用于处理文档的对象模型。

Markdown 提供了一种雕刻文本的方法。

想要从你的 sphinx 项目中引用你的 Markdown 内容似乎是合理的,使用 RST 来存根整个信息架构和更大文档的流程。让 Markdown 做它该做的事情,让作者专注于编写文本。

有没有办法引用降价域,只是按原样雕刻内容?RST/sphinx 似乎已经处理了一些特性,比如toctree没有在降价中复制它们。

于 2013-06-21T05:31:54.253 回答
14

我建议使用MyST Markdown。这是一种 Markdown 风格,旨在引入 reStructuredText 的主要功能。MyST 代表 Markedly Structured Text,可以被认为是“rST but with Markdown”。

MyST 是 CommonMark 标准的超集,它被定义为通过markdown-it-py对 CommonMark 进行离散扩展的集合)。这意味着 CommonMark 语法在 MyST 中开箱即用,但您也可以根据需要使用更多语法功能。

MyST 对 reStructuredText 中的几乎所有功能都有语法,并针对完整的 Sphinx 测试套件进行了测试,以确保可以重新创建相同的功能。例如:

以下是在 MyST 中编写指令的方法:

```{directivename} directive options
:key: value
:key2: value2

Directive content
```

以下是您在 MyST 中编写角色的方式

Here's some text and a {rolename}`role content`

MyST Markdown 的 Sphinx 解析器也有一些很好的 Sphinx 特有的特性,比如使用 Markdown 链接语法 ( [some text](somelink)) 来处理 Sphinx 中的交叉引用。例如,您可以在 MyST 中定义一个标签并引用它,如下所示:

(my-label)=
# My header

Some text and a [cross reference](my-label).

有关更完整的 MyST Markdown 语法列表,一个很好的参考是Jupyter Book 备忘单,其中列出了许多常见的文档需求以及完成它的相应 MyST 语法。(MyST 是作为 Jupyter Book 的一个组件创建的,尽管从技术角度来看它是一个完全独立的项目)。

MyST 现在是Sphinx 文档ReadTheDocs 文档中推荐的用于 Sphinx 的 Markdown 工具。

要将 MyST Parser 添加到您的 Sphinx 文档中,只需执行以下操作:

pip install myst-parser

在 中conf.py,添加:

extensions = [
  ...
  "myst_parser",
  ...
]

您的 Sphinx 文档现在将能够解析 CommonMark markdown 以及扩展的 MyST Markdown 语法!查看MyST 文档了解更多信息!

我希望这有助于澄清一些事情!

于 2021-05-06T14:49:34.670 回答
11

现在正式支持:http ://www.sphinx-doc.org/en/stable/markdown.html

另请参阅https://myst-parser.readthedocs.io/en/latest/syntax/optional.html以获取扩展,包括使 url 自动链接的链接。

于 2017-06-01T15:04:20.557 回答
8

我接受了 Beni 的建议,即使用 pandoc 来完成这项任务。安装后,以下脚本会将源目录中的所有 markdown 文件转换为 rst 文件,这样您就可以在 markdown 中编写所有文档。希望这对其他人有用。

#!/usr/bin/env python
import os
import subprocess

DOCUMENTATION_SOURCE_DIR = 'documentation/source/'
SOURCE_EXTENSION = '.md'
OUTPUT_EXTENSION = '.rst'

for _, __, filenames in os.walk(DOCUMENTATION_SOURCE_DIR):
    for filename in filenames:
        if filename.endswith('.md'):
            filename_stem = filename.split('.')[0]
            source_file = DOCUMENTATION_SOURCE_DIR + filename_stem + SOURCE_EXTENSION
            output_file = DOCUMENTATION_SOURCE_DIR + filename_stem + OUTPUT_EXTENSION
            command = 'pandoc -s {0} -o {1}'.format(source_file, output_file)
            print(command)
            subprocess.call(command.split(' '))
于 2015-05-12T17:00:29.873 回答
8

这是一个新选项。MyST 为 Markdown 添加了一些功能,允许 Sphinx 像 rst 一样构建文档。 https://myst-parser.readthedocs.io/en/latest/

于 2020-05-23T22:33:27.137 回答
1

有一种解决方法。
sphinx-quickstart.py 脚本生成一个 Makefile。
每次您想生成文档时,您都可以轻松地从 Makefile 调用 Pandoc,以便将 Markdown 转换为 reStructuredText。

于 2013-05-07T23:45:30.603 回答
0

这是该recommonmark方法的更新。

pip install recommonmark

我个人使用 Sphinx 3.5.1,所以

# for Sphinx-1.4 or newer
extensions = ['recommonmark']

在此处查看官方文档。

于 2021-03-08T15:15:06.530 回答
0

请注意,以下 maven 插件完全支持使用maven和嵌入式 Sphinx + MarkDown 支持构建文档:

https://trustin.github.io/sphinx-maven-plugin/index.html

<plugin>
  <groupId>kr.motd.maven</groupId>
  <artifactId>sphinx-maven-plugin</artifactId>
  <version>1.6.1</version>
  <configuration>
    <outputDirectory>${project.build.directory}/docs</outputDirectory>
  </configuration>
  <executions>
    <execution>
      <phase>package</phase>
      <goals>
        <goal>generate</goal>
      </goals>
    </execution>
  </executions>
</plugin>
于 2017-12-05T14:29:06.020 回答