/
store.go
93 lines (79 loc) · 2.27 KB
/
store.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
package template
import (
"strings"
"sync"
"text/template"
"github.com/devgek/webskeleton/config"
"github.com/gobuffalo/packr/v2"
)
//TemplateRoot rootdir for template files
// var TemplateRoot = "./web/templates/"
//TStore ...
type TStore interface {
GetTemplate(name string) (*template.Template, error)
}
// BoxBasedTemplateStore ...
type BoxBasedTemplateStore struct {
sync.Mutex
Box *packr.Box
templates map[string]*template.Template
}
//NewBoxBasedTemplateStore ...
func NewBoxBasedTemplateStore(box *packr.Box) TStore {
return &BoxBasedTemplateStore{Box: box, templates: map[string]*template.Template{}}
}
//GetTemplate ...
func (ts *BoxBasedTemplateStore) GetTemplate(fileName string) (*template.Template, error) {
ts.Lock()
defer ts.Unlock()
//if dev mode, then parse the template on each request
if val, ok := ts.templates[fileName]; ok && !config.IsDev() {
return val, nil
}
var templ *template.Template
var err error
switch {
case fileName == "login":
templ, err = parsePacked(ts.Box, fileName+".html")
case strings.Contains(fileName, "page"):
templ, err = parsePacked(ts.Box, "layout.html", fileName+".html")
default:
templ, err = parsePacked(ts.Box, "layout.html", fileName+".html", fileName+"-edit.html", "confirm-delete.html")
}
if err == nil {
ts.templates[fileName] = templ
}
return templ, err
}
// ParsePacked parses html templates from packr box
// template is nil, it is created from the first file.
func parsePacked(box *packr.Box, filenames ...string) (*template.Template, error) {
var t *template.Template
for _, filename := range filenames {
s, err := box.FindString(filename)
if err != nil {
return nil, err
}
name := filename
// First template becomes return value if not already defined,
// and we use that one for subsequent New calls to associate
// all the templates together. Also, if this file has the same name
// as t, this file becomes the contents of t, so
// t, err := New(name).Funcs(xxx).ParseFiles(name)
// works. Otherwise we create a new template associated with t.
var tmpl *template.Template
if t == nil {
t = template.New(name)
}
if name == t.Name() {
tmpl = t
} else {
tmpl = t.New(name)
}
_, err = tmpl.Parse(s)
if err != nil {
return nil, err
}
}
return t, nil
}