Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/foolin/goview
Goview is a lightweight, minimalist and idiomatic template library based on golang html/template for building Go web application.
https://github.com/foolin/goview
chi echo framework gin go golang gorice html library template view
Last synced: 5 days ago
JSON representation
Goview is a lightweight, minimalist and idiomatic template library based on golang html/template for building Go web application.
- Host: GitHub
- URL: https://github.com/foolin/goview
- Owner: foolin
- License: mit
- Created: 2019-04-14T11:22:41.000Z (over 5 years ago)
- Default Branch: master
- Last Pushed: 2023-10-29T03:57:41.000Z (about 1 year ago)
- Last Synced: 2024-11-30T04:06:07.265Z (12 days ago)
- Topics: chi, echo, framework, gin, go, golang, gorice, html, library, template, view
- Language: Go
- Homepage:
- Size: 10.3 MB
- Stars: 428
- Watchers: 6
- Forks: 36
- Open Issues: 15
-
Metadata Files:
- Readme: README.md
- License: LICENSE
- Support: supports/echoview-v4/README.md
Awesome Lists containing this project
- awesome-go - goview - Goview is a lightweight, minimalist and idiomatic template library based on golang html/template for building Go web application. (Template Engines / HTTP Clients)
- zero-alloc-awesome-go - goview - Goview is a lightweight, minimalist and idiomatic template library based on golang html/template for building Go web application. (Template Engines / HTTP Clients)
- awesome-list - goview
- awesome-go - goview - lightweight, minimalist and idiomatic template library based on golang html/template. (HTML template engines)
- awesome-go-extra - goview - 04-14T11:22:41Z|2022-01-06T02:36:17Z| (Template Engines / HTTP Clients)
- awesome-gin - foolin/goview
- awesome-go - goview - 基于 Go 的轻量级、简洁的模板库,适用于构建 Go Web 应用程序。 (模板引擎 / 交互工具)
- awesome-go - goview - 基于 Go 的轻量级、简洁的模板库,适用于构建 Go Web 应用程序。 (模板引擎 / 交互工具)
README
# goview
[![GoDoc Widget]][GoDoc] [![Travis Widget]][Travis] [![GoReportCard Widget]][GoReportCard]
Goview is a lightweight, minimalist and idiomatic template library based on golang [html/template](https://golang.org/pkg/html/template/) for building Go web application.
## Contents
- [Install](#install)
- [Features](#features)
- [Docs](#docs)
- [Supports](#supports)
- [Gin Framework](https://github.com/foolin/goview/tree/master/supports/ginview)
- [Iris Framework](https://github.com/foolin/goview/tree/master/supports/irisview)
- [Echo Framework](https://github.com/foolin/goview/tree/master/supports/echoview)
- [Go.Rice](https://github.com/foolin/goview/tree/master/supports/gorice)
- [Usage](#usage)
- [Overview](#overview)
- [Config](#config)
- [Include syntax](#include-syntax)
- [Render name](#render-name)
- [Custom template functions](#custom-template-functions)
- [Examples](#examples)
- [Basic example](#basic-example)
- [Gin example](#gin-example)
- [Iris example](#iris-example)
- [Iris multiple example](#iris-multiple-example)
- [Echo example](#echo-example)
- [Go-chi example](#go-chi-example)
- [Advance example](#advance-example)
- [Multiple example](#multiple-example)
- [go.rice example](#gorice-example)
- [more examples](#more-examples)## Install
```bash
go get github.com/foolin/goview
```## Features
* **Lightweight** - use golang html/template syntax.
* **Easy** - easy use for your web application.
* **Fast** - Support configure cache template.
* **Include syntax** - Support include file.
* **Master layout** - Support configure master layout file.
* **Extension** - Support configure template file extension.
* **Easy** - Support configure templates directory.
* **Auto reload** - Support dynamic reload template(disable cache mode).
* **Multiple Engine** - Support multiple templates for frontend and backend.
* **No external dependencies** - plain ol' Go html/template.
* **Gorice** - Support gorice for package resources.
* **Gin/Iris/Echo/Chi** - Support gin framework, Iris framework, echo framework, go-chi framework.## Docs
See## Supports
- **[ginview](https://github.com/foolin/goview/tree/master/supports/ginview)** goview for gin framework
- **[irisview](https://github.com/foolin/goview/tree/master/supports/irisview)** goview for Iris framework
- **[echoview](https://github.com/foolin/goview/tree/master/supports/echoview)** goview for echo framework
- **[gorice](https://github.com/foolin/goview/tree/master/supports/gorice)** goview for go.rice## Usage
### Overview
Project structure:
```go
|-- app/views/
|--- index.html
|--- page.html
|-- layouts/
|--- footer.html
|--- master.html
```Use default instance:
```go
//write http.ResponseWriter
//"index" -> index.html
goview.Render(writer, http.StatusOK, "index", goview.M{})
```Use new instance with config:
```go
gv := goview.New(goview.Config{
Root: "views",
Extension: ".tpl",
Master: "layouts/master",
Partials: []string{"partials/ad"},
Funcs: template.FuncMap{
"sub": func(a, b int) int {
return a - b
},
"copy": func() string {
return time.Now().Format("2006")
},
},
DisableCache: true,
Delims: Delims{Left: "{{", Right: "}}"},
})
//Set new instance
goview.Use(gv)
//write http.ResponseWriter
goview.Render(writer, http.StatusOK, "index", goview.M{})```
Use multiple instance with config:
```go
//============== Frontend ============== //
gvFrontend := goview.New(goview.Config{
Root: "views/frontend",
Extension: ".tpl",
Master: "layouts/master",
Partials: []string{"partials/ad"},
Funcs: template.FuncMap{
"sub": func(a, b int) int {
return a - b
},
"copy": func() string {
return time.Now().Format("2006")
},
},
DisableCache: true,
Delims: Delims{Left: "{{", Right: "}}"},
})
//write http.ResponseWriter
gvFrontend.Render(writer, http.StatusOK, "index", goview.M{})
//============== Backend ============== //
gvBackend := goview.New(goview.Config{
Root: "views/backend",
Extension: ".tpl",
Master: "layouts/master",
Partials: []string{"partials/ad"},
Funcs: template.FuncMap{
"sub": func(a, b int) int {
return a - b
},
"copy": func() string {
return time.Now().Format("2006")
},
},
DisableCache: true,
Delims: Delims{Left: "{{", Right: "}}"},
})
//write http.ResponseWriter
gvBackend.Render(writer, http.StatusOK, "index", goview.M{})```
### Config
```go
goview.Config{
Root: "views", //template root path
Extension: ".tpl", //file extension
Master: "layouts/master", //master layout file
Partials: []string{"partials/head"}, //partial files
Funcs: template.FuncMap{
"sub": func(a, b int) int {
return a - b
},
// more funcs
},
DisableCache: false, //if disable cache, auto reload template file for debug.
Delims: Delims{Left: "{{", Right: "}}"},
}
```### Include syntax
```go
//template file
{{include "layouts/footer"}}
```### Render name:
Render name use `index` without `.html` extension, that will render with master layout.
- **"index"** - Render with master layout.
- **"index.html"** - Not render with master layout.```
Notice: `.html` is default template extension, you can change with config
```Render with master
```go
//use name without extension `.html`
goview.Render(w, http.StatusOK, "index", goview.M{})
```The `w` is instance of `http.ResponseWriter`
Render only file(not use master layout)
```go
//use full name with extension `.html`
goview.Render(w, http.StatusOK, "page.html", goview.M{})
```### Custom template functions
We have two type of functions `global functions`, and `temporary functions`.
`Global functions` are set within the `config`.
```go
goview.Config{
Funcs: template.FuncMap{
"reverse": e.Reverse,
},
}
``````go
//template file
{{ reverse "route-name" }}
````Temporary functions` are set inside the handler.
```go
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "index", goview.M{
"reverse": e.Reverse,
})
if err != nil {
fmt.Fprintf(w, "Render index error: %v!", err)
}
})
```
```go
//template file
{{ call $.reverse "route-name" }}
```## Examples
See [_examples/](https://github.com/foolin/goview/blob/master/_examples/) for a variety of examples.
### Basic example
```gopackage main
import (
"fmt"
"github.com/foolin/goview"
"net/http"
)func main() {
//render index use `index` without `.html` extension, that will render with master layout.
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "index", goview.M{
"title": "Index title!",
"add": func(a int, b int) int {
return a + b
},
})
if err != nil {
fmt.Fprintf(w, "Render index error: %v!", err)
}})
//render page use `page.tpl` with '.html' will only file template without master layout.
http.HandleFunc("/page", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "page.html", goview.M{"title": "Page file title!!"})
if err != nil {
fmt.Fprintf(w, "Render page.html error: %v!", err)
}
})fmt.Println("Listening and serving HTTP on :9090")
http.ListenAndServe(":9090", nil)}
```
Project structure:
```go
|-- app/views/
|--- index.html
|--- page.html
|-- layouts/
|--- footer.html
|--- master.html
See in "examples/basic" folder
```[Basic example](https://github.com/foolin/goview/tree/master/_examples/basic)
### Gin example
```bash
go get github.com/foolin/goview/supports/ginview
``````go
package main
import (
"github.com/foolin/goview/supports/ginview"
"github.com/gin-gonic/gin"
"net/http"
)func main() {
router := gin.Default()//new template engine
router.HTMLRender = ginview.Default()router.GET("/", func(ctx *gin.Context) {
//render with master
ctx.HTML(http.StatusOK, "index", gin.H{
"title": "Index title!",
"add": func(a int, b int) int {
return a + b
},
})
})router.GET("/page", func(ctx *gin.Context) {
//render only file, must full name with extension
ctx.HTML(http.StatusOK, "page.html", gin.H{"title": "Page file title!!"})
})router.Run(":9090")
}```
Project structure:
```go
|-- app/views/
|--- index.html
|--- page.html
|-- layouts/
|--- footer.html
|--- master.html
See in "examples/basic" folder
```[Gin example](https://github.com/foolin/goview/tree/master/_examples/gin)
### Iris example
```bash
$ go get github.com/foolin/goview/supports/irisview
``````go
package mainimport (
"github.com/foolin/goview/supports/irisview"
"github.com/kataras/iris/v12"
)func main() {
app := iris.New()// Register the goview template engine.
app.RegisterView(irisview.Default())app.Get("/", func(ctx iris.Context) {
// Render with master.
ctx.View("index", iris.Map{
"title": "Index title!",
"add": func(a int, b int) int {
return a + b
},
})
})app.Get("/page", func(ctx iris.Context) {
// Render only file, must full name with extension.
ctx.View("page.html", iris.Map{"title": "Page file title!!"})
})app.Listen(":9090")
}
```Project structure:
```go
|-- app/views/
|--- index.html
|--- page.html
|-- layouts/
|--- footer.html
|--- master.html
See in "examples/iris" folder
```[Iris example](https://github.com/foolin/goview/tree/master/_examples/iris)
### Iris multiple example
```go
package mainimport (
"html/template"
"time""github.com/foolin/goview"
"github.com/foolin/goview/supports/irisview"
"github.com/kataras/iris/v12"
)func main() {
app := iris.New()// Register a new template engine.
app.RegisterView(irisview.New(goview.Config{
Root: "views/frontend",
Extension: ".html",
Master: "layouts/master",
Partials: []string{"partials/ad"},
Funcs: template.FuncMap{
"copy": func() string {
return time.Now().Format("2006")
},
},
DisableCache: true,
}))app.Get("/", func(ctx iris.Context) {
ctx.View("index", iris.Map{
"title": "Frontend title!",
})
})//=========== Backend ===========//
// Assign a new template middleware.
mw := irisview.NewMiddleware(goview.Config{
Root: "views/backend",
Extension: ".html",
Master: "layouts/master",
Partials: []string{},
Funcs: template.FuncMap{
"copy": func() string {
return time.Now().Format("2006")
},
},
DisableCache: true,
})backendGroup := app.Party("/admin", mw)
backendGroup.Get("/", func(ctx iris.Context) {
// Use the ctx.View as you used to. Zero changes to your codebase,
// even if you use multiple templates.
ctx.View("index", iris.Map{
"title": "Backend title!",
})
})app.Listen(":9090")
}
```Project structure:
```go
|-- app/views/
|-- fontend/
|--- index.html
|-- layouts/
|--- footer.html
|--- head.html
|--- master.html
|-- partials/
|--- ad.html
|-- backend/
|--- index.html
|-- layouts/
|--- footer.html
|--- head.html
|--- master.html
See in "examples/iris-multiple" folder
```[Iris multiple example](https://github.com/foolin/goview/tree/master/_examples/iris-multiple)
### Echo example
Echo <=v3 version:
```bash
go get github.com/foolin/goview/supports/echoview
```Echo v4 version:
```bash
go get github.com/foolin/goview/supports/echoview-v4
``````go
package main
import (
"github.com/foolin/goview/supports/echoview"
"github.com/labstack/echo"
"github.com/labstack/echo/middleware"
"net/http"
)func main() {
// Echo instance
e := echo.New()// Middleware
e.Use(middleware.Logger())
e.Use(middleware.Recover())//Set Renderer
e.Renderer = echoview.Default()// Routes
e.GET("/", func(c echo.Context) error {
//render with master
return c.Render(http.StatusOK, "index", echo.Map{
"title": "Index title!",
"add": func(a int, b int) int {
return a + b
},
})
})e.GET("/page", func(c echo.Context) error {
//render only file, must full name with extension
return c.Render(http.StatusOK, "page.html", echo.Map{"title": "Page file title!!"})
})// Start server
e.Logger.Fatal(e.Start(":9090"))
}```
Project structure:
```go
|-- app/views/
|--- index.html
|--- page.html
|-- layouts/
|--- footer.html
|--- master.html
See in "examples/basic" folder
```[Echo example](https://github.com/foolin/goview/tree/master/_examples/echo)
[Echo v4 example](https://github.com/foolin/goview/tree/master/_examples/echo-v4)### Go-chi example
```gopackage main
import (
"fmt"
"github.com/foolin/goview"
"github.com/go-chi/chi"
"net/http"
)func main() {
r := chi.NewRouter()
//render index use `index` without `.html` extension, that will render with master layout.
r.Get("/", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "index", goview.M{
"title": "Index title!",
"add": func(a int, b int) int {
return a + b
},
})
if err != nil {
fmt.Fprintf(w, "Render index error: %v!", err)
}
})//render page use `page.tpl` with '.html' will only file template without master layout.
r.Get("/page", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "page.html", goview.M{"title": "Page file title!!"})
if err != nil {
fmt.Fprintf(w, "Render page.html error: %v!", err)
}
})fmt.Println("Listening and serving HTTP on :9090")
http.ListenAndServe(":9090", r)}
```
Project structure:
```go
|-- app/views/
|--- index.html
|--- page.html
|-- layouts/
|--- footer.html
|--- master.html
See in "examples/basic" folder
```[Chi example](https://github.com/foolin/goview/tree/master/_examples/go-chi)
### Advance example
```gopackage main
import (
"fmt"
"github.com/foolin/goview"
"html/template"
"net/http"
"time"
)func main() {
gv := goview.New(goview.Config{
Root: "views",
Extension: ".tpl",
Master: "layouts/master",
Partials: []string{"partials/ad"},
Funcs: template.FuncMap{
"sub": func(a, b int) int {
return a - b
},
"copy": func() string {
return time.Now().Format("2006")
},
},
DisableCache: true,
})//Set new instance
goview.Use(gv)//render index use `index` without `.html` extension, that will render with master layout.
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "index", goview.M{
"title": "Index title!",
"add": func(a int, b int) int {
return a + b
},
})
if err != nil {
fmt.Fprintf(w, "Render index error: %v!", err)
}})
//render page use `page.tpl` with '.html' will only file template without master layout.
http.HandleFunc("/page", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "page.tpl", goview.M{"title": "Page file title!!"})
if err != nil {
fmt.Fprintf(w, "Render page.html error: %v!", err)
}
})fmt.Println("Listening and serving HTTP on :9090")
http.ListenAndServe(":9090", nil)
}```
Project structure:
```go
|-- app/views/
|--- index.tpl
|--- page.tpl
|-- layouts/
|--- footer.tpl
|--- head.tpl
|--- master.tpl
|-- partials/
|--- ad.tpl
See in "examples/advance" folder
```[Advance example](https://github.com/foolin/goview/tree/master/_examples/advance)
### Multiple example
```gopackage main
import (
"html/template"
"net/http"
"time""github.com/foolin/goview"
"github.com/gin-gonic/gin"
)func main() {
router := gin.Default()//new template engine
router.HTMLRender = gintemplate.New(gintemplate.TemplateConfig{
Root: "views/fontend",
Extension: ".html",
Master: "layouts/master",
Partials: []string{"partials/ad"},
Funcs: template.FuncMap{
"copy": func() string {
return time.Now().Format("2006")
},
},
DisableCache: true,
})router.GET("/", func(ctx *gin.Context) {
// `HTML()` is a helper func to deal with multiple TemplateEngine's.
// It detects the suitable TemplateEngine for each path automatically.
gintemplate.HTML(ctx, http.StatusOK, "index", gin.H{
"title": "Fontend title!",
})
})//=========== Backend ===========//
//new middleware
mw := gintemplate.NewMiddleware(gintemplate.TemplateConfig{
Root: "views/backend",
Extension: ".html",
Master: "layouts/master",
Partials: []string{},
Funcs: template.FuncMap{
"copy": func() string {
return time.Now().Format("2006")
},
},
DisableCache: true,
})// You should use helper func `Middleware()` to set the supplied
// TemplateEngine and make `HTML()` work validly.
backendGroup := router.Group("/admin", mw)backendGroup.GET("/", func(ctx *gin.Context) {
// With the middleware, `HTML()` can detect the valid TemplateEngine.
gintemplate.HTML(ctx, http.StatusOK, "index", gin.H{
"title": "Backend title!",
})
})router.Run(":9090")
}```
Project structure:
```go
|-- app/views/
|-- fontend/
|--- index.html
|-- layouts/
|--- footer.html
|--- head.html
|--- master.html
|-- partials/
|--- ad.html
|-- backend/
|--- index.html
|-- layouts/
|--- footer.html
|--- head.html
|--- master.html
See in "examples/multiple" folder
```[Multiple example](https://github.com/foolin/goview/tree/master/_examples/multiple)
### go.rice example
```bash
go get github.com/foolin/goview/supports/gorice
``````go
package main
import (
"fmt"
"github.com/GeertJohan/go.rice"
"github.com/foolin/goview"
"github.com/foolin/goview/supports/gorice"
"net/http"
)func main() {
//static
staticBox := rice.MustFindBox("static")
staticFileServer := http.StripPrefix("/static/", http.FileServer(staticBox.HTTPBox()))
http.Handle("/static/", staticFileServer)//new view engine
gv := gorice.New(rice.MustFindBox("views"))
//set engine for default instance
goview.Use(gv)//render index use `index` without `.html` extension, that will render with master layout.
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "index", goview.M{
"title": "Index title!",
"add": func(a int, b int) int {
return a + b
},
})
if err != nil {
fmt.Fprintf(w, "Render index error: %v!", err)
}})
//render page use `page.tpl` with '.html' will only file template without master layout.
http.HandleFunc("/page", func(w http.ResponseWriter, r *http.Request) {
err := goview.Render(w, http.StatusOK, "page.html", goview.M{"title": "Page file title!!"})
if err != nil {
fmt.Fprintf(w, "Render page.html error: %v!", err)
}
})fmt.Println("Listening and serving HTTP on :9090")
http.ListenAndServe(":9090", nil)
}```
Project structure:
```go
|-- app/views/
|--- index.html
|--- page.html
|-- layouts/
|--- footer.html
|--- master.html
|-- app/static/
|-- css/
|--- bootstrap.css
|-- img/
|--- gopher.pngSee in "examples/gorice" folder
```[gorice example](https://github.com/foolin/goview/tree/master/_examples/gorice)
### More examples
See [_examples/](https://github.com/foolin/goview/blob/master/_examples/) for a variety of examples.
[GoDoc]: https://godoc.org/github.com/foolin/goview
[GoDoc Widget]: https://godoc.org/github.com/foolin/goview?status.svg
[Travis]: https://travis-ci.org/foolin/goview
[Travis Widget]: https://travis-ci.org/foolin/goview.svg?branch=master
[GoReportCard]: https://goreportcard.com/report/github.com/foolin/goview
[GoReportCard Widget]: https://goreportcard.com/badge/github.com/foolin/goview
[GoCover]: https://goreportcard.com/report/github.com/foolin/goview
[GoCover Widget]: https://goreportcard.com/badge/github.com/foolin/goview### Todo
[ ] Add Partials support directory or glob
[ ] Add functions support.