如何在golang模板中使用动态HTML标签?



我试图渲染一个标题与一个动态标签(回退应该是h2)。

<{{ or .Settings.headlineTag "h2" }}> 
{{ .Content.headline }}
</ {{ or .Settings.headlineTag "h2" }}>

不幸的是输出被转义了:

&lt;h2>
Headline
&lt;/ h2>

我怎样才能使它按预期工作?

https://pkg.go.dev/html/template#hdr-Typed_Strings:

默认情况下,该包假定所有管道生成一个纯文本字符串。它添加了必要的转义管道阶段,以正确安全地将纯文本字符串嵌入到适当的上下文中。

当数据值不是纯文本时,可以通过标记它的类型来确保它没有过度转义。

从内容中输入HTML、JS、URL和其他类型。Go可以携带安全的内容,免除逃逸。

下面是创建一个函数来组合标签并返回template.HTML的示例:

package main
import (
"fmt"
"html/template"
"os"
)
func main() {
data := []struct {
Tag     string
Content string
}{
{
Tag:     "h1",
Content: "How to use dynamic <HTML> tags in golang template?",
},
{
Content: `.Settings.headlineTag "h2"`,
},
}
const tpl = `
{{ range . }}
{{ tag .Tag "h2" .Content }}
{{ end }}
`
t, err := template.New("webpage").
Funcs(template.FuncMap{
"tag": func(tag, fallback, content string) template.HTML {
name := tag
if name == "" {
name = fallback
}
v := fmt.Sprintf("<%s>%s</%s>", name, template.HTMLEscapeString(content), name)
return template.HTML(v)
},
}).
Parse(tpl)
if err != nil {
panic(err)
}
err = t.Execute(os.Stdout, data)
if err != nil {
panic(err)
}
}

输出:

<h1>How to use dynamic &lt;HTML&gt; tags in golang template?</h1>
<h2>.Settings.headlineTag &#34;h2&#34;</h2>