Golang 的 gomarkdown/markdown
库提供了丰富的扩展选项(extensions)和渲染配置(RendererOptions),让你能够精确控制 Markdown 的解析和 HTML 的生成。本文将会详细介绍这两个方面。
gomarkdown/markdown Parser Extensions (解析器扩展)
解析器扩展控制 Markdown 解析时启用的特性。主要扩展选项包括:
常用扩展组合
parser.CommonExtensions
: 包含最常用扩展的组合
块级元素扩展
parser.Tables
: 支持 GitHub 风格的表格parser.FencedCode
: 支持围栏式代码块 (```language)parser.Footnotes
: 支持脚注 ([^1], [^1]: 脚注内容)parser.HeadingIDs
: 为标题添加 ID 属性parser.AutoHeadingIDs
: 自动为标题生成 IDparser.Definition
: 支持定义列表parser.MathJax
: 支持 MathJax 语法
内联元素扩展
parser.Autolink
: 自动将 URL 转换为链接parser.Strikethrough
: 支持删除线 (text)parser.TaskList
: 支持任务列表 (- [x])parser.NoEmptyLineBeforeBlock
: 不需要空行来分隔块级元素parser.NoIntraEmphasis
: 禁止 word_with_underscores 中的强调
其他扩展
parser.HardLineBreak
: 单个换行符视为硬换行parser.BackslashLineBreak
: 行尾反斜杠表示换行parser.LaxHTMLBlocks
: 更宽松的 HTML 块解析规则parser.TypographicSubs
: 启用排版替换 (– → —)parser.SuperSubscript
: 支持上标和下标 (^, ~)
使用示例:
extensions := parser.Tables | parser.FencedCode | parser.Autolink
p := parser.NewWithExtensions(extensions)
gomarkdown/markdown HTML Renderer Options (HTML 渲染器选项)
html.RendererOptions
结构体包含多种配置,用于自定义 HTML 输出:
标志选项 (Flags)
html.CommonFlags
: 常用标志的组合html.HrefTargetBlank
: 为链接添加target="_blank"
属性html.NofollowLinks
: 为链接添加rel="nofollow"
属性html.NoreferrerLinks
: 为链接添加rel="noreferrer"
属性html.NoopenerLinks
: 为链接添加rel="noopener"
属性html.CompletePage
: 生成完整的 HTML 页面(包含 DOCTYPE 和 head/body 标签)html.UseXHTML
: 使用 XHTML 格式而非 HTMLhtml.FootnoteReturnLinks
: 为脚注添加返回链接
其他选项
Title
: 页面标题(配合 CompletePage 使用)CSS
: CSS 样式表的 URL(配合 CompletePage 使用)Icon
: 页面图标的 URL(配合 CompletePage 使用)Footnote
: 自定义脚注配置HeadingIDPrefix
: 标题 ID 的前缀HeadingIDSuffix
: 标题 ID 的后缀RenderNodeHook
: 自定义节点渲染钩子函数CodeBlockData
: 代码块额外数据函数
使用示例:
opts := html.RendererOptions{
Flags: html.CommonFlags | html.HrefTargetBlank,
CSS: "style.css",
Title: "My Markdown Document",
RenderNodeHook: func(w io.Writer, node ast.Node, entering bool) (ast.WalkStatus, bool) {
// 自定义节点渲染逻辑
return ast.GoToNext, false
},
}
renderer := html.NewRenderer(opts)
Go 语言中使用 gomarkdown/markdown 解析 markdown 的完整示例
下面是一个更完整的示例,展示如何使用多种扩展和选项:
func renderMarkdown(content []byte) []byte {
// 解析器配置
extensions := parser.CommonExtensions |
parser.AutoHeadingIDs |
parser.NoEmptyLineBeforeBlock |
parser.Tables |
parser.FencedCode |
parser.Strikethrough |
parser.TaskList
p := parser.NewWithExtensions(extensions)
doc := p.Parse(content)
// 渲染器配置
htmlFlags := html.CommonFlags |
html.HrefTargetBlank |
html.NoreferrerLinks |
html.NoopenerLinks
opts := html.RendererOptions{
Flags: htmlFlags,
HeadingIDPrefix: "section-",
FootnoteReturnLinkContents: "↩",
RenderNodeHook: func(w io.Writer, node ast.Node, entering bool) (ast.WalkStatus, bool) {
// 可以在这里实现自定义渲染逻辑
// 例如:为表格添加特定的类
if heading, ok := node.(*ast.Heading); ok && entering {
fmt.Fprintf(w, "<h%d class=\"custom-heading\">", heading.Level)
return ast.GoToNext, true
}
return ast.GoToNext, false
},
}
renderer := html.NewRenderer(opts)
return markdown.Render(doc, renderer)
}
通过这些配置,你可以精确控制 Markdown 的解析和渲染过程,解决之前遇到的有序列表问题,并满足各种自定义需求。