Golang模板中自定义函数无法使用的问题

Golang模板中自定义函数无法使用的问题 以下代码运行正常 playground

package main

import (
	"html/template"
	"os"
)

func main() {
	tmpl := `
{{ $slice := mkSlice "a" 5 "b" }}
{{ range $slice }}
     {{ . }}
{{ end }}
`
	funcMap := map[string]interface{}{"mkSlice": mkSlice}
	t := template.New("").Funcs(template.FuncMap(funcMap))
	template.Must(t.Parse(tmpl))
	t.Execute(os.Stdout, nil)
}

func mkSlice(args ...interface{}) []interface{} {
	return args
}

但当我尝试从模板文件运行时,没有任何内容显示,也没有收到任何错误!

func mkSlice(args ...interface{}) []interface{} { // 在模板中创建数组
	return args
}

funcMap := map[string]interface{}{"mkSlice": mkSlice}
tmpl := template.New("").Funcs(template.FuncMap(funcMap))
template.Must(tmpl.ParseFiles("index.html"))
tmpl.Execute(w, nil)

index.html 文件内容如下:

{{ $slice := mkSlice "a" 5 "b" }}
{{ range $slice }}
    <span> {{ . }} </span>
{{ end }}

有什么想法吗?


更多关于Golang模板中自定义函数无法使用的问题的实战教程也可以访问 https://www.itying.com/category-94-b0.html

1 回复

更多关于Golang模板中自定义函数无法使用的问题的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


问题在于使用 ParseFiles 时模板关联的方式。当通过 ParseFiles 解析模板文件时,返回的模板是基于文件名(index.html)的,而不是最初创建的模板实例。

以下是修复后的代码:

func mkSlice(args ...interface{}) []interface{} {
    return args
}

funcMap := template.FuncMap{"mkSlice": mkSlice}
tmpl := template.New("index.html").Funcs(funcMap)
tmpl = template.Must(tmpl.ParseFiles("index.html"))
tmpl.Execute(w, nil)

或者使用 template.ParseFiles 配合 Funcs

func mkSlice(args ...interface{}) []interface{} {
    return args
}

tmpl := template.New("index.html").Funcs(template.FuncMap{
    "mkSlice": mkSlice,
})
tmpl = template.Must(tmpl.ParseFiles("index.html"))
tmpl.Execute(w, nil)

关键点:

  1. 创建模板时使用与文件名相同的名称(index.html
  2. 在解析文件之前注册自定义函数

如果使用多个模板文件,可以这样处理:

tmpl := template.New("").Funcs(template.FuncMap{
    "mkSlice": mkSlice,
})
tmpl = template.Must(tmpl.ParseFiles("index.html", "layout.html"))
tmpl.ExecuteTemplate(w, "index.html", nil)

这样自定义函数就能在模板文件中正常工作了。

回到顶部