我正在尝试创建一些模板,但我无法理解接下来的事情: 为什么这样的 build 行不通? 我有 test.go 文件:
package main
import (
"net/http"
"html/template"
"fmt"
)
func main() {
http.HandleFunc("/test.html", TestHandler)
http.ListenAndServe(":8080", nil)
}
func TestHandler(w http.ResponseWriter, r *http.Request) {
//Parsing HTML
t, err := template.ParseFiles("test.html")
if err != nil {
fmt.Println(err)
}
Name := "MyName"
City := "MyCity"
t.ExecuteTemplate(w, "T1", Name)
t.ExecuteTemplate(w, "T2", City)
}
我还有 test.html:
<html>
<head>
<title>Tamplates</title>
</head>
<body>
<h1>Testing some templates</h1>
<p> Empty template: {{ `"Some text"` }} </p>
<p> Name is {{ template "T1" . }} </p>
<p> City is {{ template "T2" . }} </p>
</body>
</html>
这是个简单的例子,但不知为什么它不起作用。
我尝试添加字符串 {{ define "T1"}} {{ . }} {{ end }}
和 {{ 定义“T2”}} {{ . }} {{ end }}
在 h1 标题之前,但结果网页只包含字符串 MyName MyCity
最佳答案
更新 (07/02/2016)
我将尽我所能解释为什么您的代码没有正确执行,以及使用嵌套模板的正确解决方案。
在您的 test.html 文件中,您导入了两个模板:T1
和 T2
,
<p> Name is {{ template "T1" . }} </p>
<p> City is {{ template "T2" . }} </p>
这些模板应该被定义并写入某个地方以供使用(一个好的写入位置可以在单独的文件中)。这是我发现的第一个问题,您是这样定义它们的:
{{ define "T1" }} {{ . }} {{ end }}
{{ define "T2" }} {{ . }} {{ end }}
请注意,{{.}}
是当前对象的简写,因此它将呈现您在调用 ExecuteTemplate
函数时传递的任何数据。因此,要解决这个问题,您应该在每个模板中指定要渲染的对象:
{{ define "T1" }} {{ .Name }} {{ end }}
{{ define "T2" }} {{ .City }} {{ end }}
现在,这是我发现的第二个问题。在您的 TestHandler
函数中,您只是渲染子模板,首先是 T1
模板,然后是 T2
模板:
t.ExecuteTemplate(w, "T1", Name)
t.ExecuteTemplate(w, "T2", City)
因此,您绝不会调用父模板。
您可以在下面找到使用嵌套模板的外观。希望能解决您对模板使用的疑惑。
test.go文件
package main
import (
"fmt"
"html/template"
"net/http"
)
func main() {
http.HandleFunc("/test.html", TestHandler)
http.ListenAndServe(":8080", nil)
}
func TestHandler(w http.ResponseWriter, r *http.Request) {
//Parsing HTML
t, err := template.ParseFiles("test2.html", "t1.tmpl", "t2.tmpl")
if err != nil {
fmt.Println(err)
}
items := struct {
Name string
City string
}{
Name: "MyName",
City: "MyCity",
}
t.Execute(w, items)
}
test.html文件
<html>
<head>
<title>Templates</title>
</head>
<body>
<h1>Testing some templates</h1>
<p> Empty template: {{ `"Some text"` }} </p>
<p> Name is {{ template "T1" . }} </p>
<p> City is {{ template "T2" . }} </p>
</body>
</html>
t1.tmpl 文件
{{ define "T1" }} {{ .Name }} {{ end }}
t2.tmpl 文件
{{ define "T2" }} {{ .City }} {{ end }}
不使用子模板:
我对您的代码进行了一些更改,使其能够正常工作。我只是将结构集合中的“名称”和“城市”变量发送到 Execute方法。检查以下内容:
package main
import (
"fmt"
"html/template"
"net/http"
)
func main() {
http.HandleFunc("/test.html", TestHandler)
http.ListenAndServe(":8080", nil)
}
func TestHandler(w http.ResponseWriter, r *http.Request) {
//Parsing HTML
t, err := template.ParseFiles("test.html")
if err != nil {
fmt.Println(err)
}
items := struct {
Name string
City string
}{
Name: "MyName",
City: "MyCity",
}
t.Execute(w, items)
}
并使用 {{.Name}}
和 {{.City}}
访问那些导出的字段。
<html>
<head>
<title>Tamplates</title>
</head>
<body>
<h1>Testing some templates</h1>
<p> Name is {{.Name}} </p>
<p> City is {{.City}} </p>
</body>
</html>
关于html - 无法在golang中很好地执行模板,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35243493/