去提问»
提问背景 Question:
// 初始化解析器时开启 HardLineBreak md := goldmark.New(goldmark.WithExtensions( extension.NewRenderer(extension.WithHardLineBreak()), )) 这个需要什么库支持,需要放进init中初始化吧,不可能每次用一下。

Goldmark HardLineBreak 初始化指南

发布时间:2026-08-18 15:29 👁️ 阅读:1

是的,goldmark 解析器,尤其是带扩展的配置,应该在应用程序启动时(例如在 init() 函数中)只初始化一次,然后复用这个实例。每次使用时都重新初始化会带来不必要的性能开销。

你需要引入以下库:

  • github.com/yuin/goldmark
  • github.com/yuin/goldmark/extension

以下是一个在 Go 应用程序中初始化 goldmark 并开启 HardLineBreak 的示例:

package main

import (
	"bytes"
	"fmt"
	"log"

	"github.com/yuin/goldmark"
	"github.com/yuin/goldmark/extension"
	"github.com/yuin/goldmark/parser"
	"github.com/yuin/goldmark/renderer/html"
)

// 定义一个全局变量来存储 Goldmark 解析器实例
var md goldmark.Markdown

// init 函数会在包被导入时自动执行一次
func init() {
	md = goldmark.New(
		goldmark.WithExtensions(
			extension.NewFootnote(), // 示例:可以添加其他扩展
			extension.NewLinkify(),
			extension.GFM, // GitHub Flavored Markdown 常用
			extension.NewRenderer(extension.WithHardLineBreak()), // 开启 HardLineBreak
		),
		goldmark.WithParserOptions(
			parser.WithAutoHeadingID(), // 自动生成标题ID
		),
		goldmark.WithRendererOptions(
			html.WithUnsafe(), // 允许渲染不安全的HTML(如style, script标签)
		),
	)
	log.Println("Goldmark parser initialized.")
}

func main() {
	source := []byte(`Hello
World
This is a test.
- Item 1
- Item 2`)

	var buf bytes.Buffer
	if err := md.Convert(source, &buf); err != nil {
		log.Fatal(err)
	}

	fmt.Println(buf.String())

	// 示例2:另一段文本
	source2 := []byte(`Another
Line
With a hard break.`)
	var buf2 bytes.Buffer
	if err := md.Convert(source2, &buf2); err != nil {
		log.Fatal(err)
	}
	fmt.Println(buf2.String())
}

关键点:

  1. 全局实例 md: goldmark.Markdown 实例被声明为全局变量,确保只创建一次。
  2. init() 函数: 在 init() 函数中进行初始化操作。init() 函数在 main() 函数执行之前且包的所有变量声明完成后自动执行。
  3. goldmark.WithExtensions(...): 这是添加各种 Goldmark 扩展的方式。extension.NewRenderer(extension.WithHardLineBreak()) 专门用于开启硬换行功能。
  4. 复用 md 实例: 在 main 函数或其他业务逻辑中,直接使用已初始化的 md 变量来转换 Markdown 文本,无需每次都重新调用 goldmark.New()