package core import ( "fmt" "html/template" "io/fs" "path" ) // LoadTemplates parses each views/*.html into its own tree alongside every // layouts/*.html. Returns a set keyed by view filename. // // Placeholder funcs are installed at parse time; the real ones are bound // per render, when a Ctx exists to close over. func LoadTemplates(fsys fs.FS) (TemplateSet, error) { layouts, err := fs.Glob(fsys, "layouts/*.html") if err != nil { return nil, err } views, err := fs.Glob(fsys, "views/*.html") if err != nil { return nil, err } if len(views) == 0 { return nil, fmt.Errorf("no templates under views/") } set := TemplateSet{} for _, v := range views { name := path.Base(v) t := template.New(name).Funcs(FuncMap(&Ctx{})) files := append(append([]string{}, layouts...), v) if t, err = t.ParseFS(fsys, files...); err != nil { return nil, fmt.Errorf("parse %s: %w", v, err) } set[name] = t } return set, nil }