...

Source file src/github.com/shurcooL/httpfs/html/vfstemplate/vfstemplate.go

Documentation: github.com/shurcooL/httpfs/html/vfstemplate

     1  // Package vfstemplate offers html/template helpers that use http.FileSystem.
     2  package vfstemplate
     3  
     4  import (
     5  	"fmt"
     6  	"html/template"
     7  	"net/http"
     8  	"path"
     9  
    10  	"github.com/shurcooL/httpfs/path/vfspath"
    11  	"github.com/shurcooL/httpfs/vfsutil"
    12  )
    13  
    14  // ParseFiles creates a new Template if t is nil and parses the template definitions from
    15  // the named files. The returned template's name will have the (base) name and
    16  // (parsed) contents of the first file. There must be at least one file.
    17  // If an error occurs, parsing stops and the returned *Template is nil.
    18  func ParseFiles(fs http.FileSystem, t *template.Template, filenames ...string) (*template.Template, error) {
    19  	return parseFiles(fs, t, filenames...)
    20  }
    21  
    22  // ParseGlob parses the template definitions in the files identified by the
    23  // pattern and associates the resulting templates with t. The pattern is
    24  // processed by vfspath.Glob and must match at least one file. ParseGlob is
    25  // equivalent to calling t.ParseFiles with the list of files matched by the
    26  // pattern.
    27  func ParseGlob(fs http.FileSystem, t *template.Template, pattern string) (*template.Template, error) {
    28  	filenames, err := vfspath.Glob(fs, pattern)
    29  	if err != nil {
    30  		return nil, err
    31  	}
    32  	if len(filenames) == 0 {
    33  		return nil, fmt.Errorf("vfs/html/vfstemplate: pattern matches no files: %#q", pattern)
    34  	}
    35  	return parseFiles(fs, t, filenames...)
    36  }
    37  
    38  // parseFiles is the helper for the method and function. If the argument
    39  // template is nil, it is created from the first file.
    40  func parseFiles(fs http.FileSystem, t *template.Template, filenames ...string) (*template.Template, error) {
    41  	if len(filenames) == 0 {
    42  		// Not really a problem, but be consistent.
    43  		return nil, fmt.Errorf("vfs/html/vfstemplate: no files named in call to ParseFiles")
    44  	}
    45  	for _, filename := range filenames {
    46  		b, err := vfsutil.ReadFile(fs, filename)
    47  		if err != nil {
    48  			return nil, err
    49  		}
    50  		s := string(b)
    51  		name := path.Base(filename)
    52  		// First template becomes return value if not already defined,
    53  		// and we use that one for subsequent New calls to associate
    54  		// all the templates together. Also, if this file has the same name
    55  		// as t, this file becomes the contents of t, so
    56  		//  t, err := New(name).Funcs(xxx).ParseFiles(name)
    57  		// works. Otherwise we create a new template associated with t.
    58  		var tmpl *template.Template
    59  		if t == nil {
    60  			t = template.New(name)
    61  		}
    62  		if name == t.Name() {
    63  			tmpl = t
    64  		} else {
    65  			tmpl = t.New(name)
    66  		}
    67  		_, err = tmpl.Parse(s)
    68  		if err != nil {
    69  			return nil, err
    70  		}
    71  	}
    72  	return t, nil
    73  }
    74  

View as plain text