对于中小型应用来说,尤其是golang应用,我们可能不需要使用nginx或nodejs为vue静态文件搭建一个前端服务器,额外的前端服务器会增加运维成本,多消耗精力。gin框架中的静态文件服务器,配合statik库,甚至可以将静态文件打包进二进制文件中,对线上部署更加友好了。

依赖库:
"github.com/gin-contrib/static"
"github.com/gin-gonic/gin"
"github.com/rakyll/statik/fs"
项目文件结构:

├─main.go
├─statik
| └statik.go //打包后的静态文件
├─dist //vue静态文件夹
| ├─favicon.ico
| ├─index.html
| ├─js
| | ├─app.07afa014.js
| ├─img
| | ├─iconfont.f6026e89.svg
| | └logo.82b9c7a5.png
| ├─fonts
| | ├─element-icons.535877f5.woff
| | └element-icons.732389de.ttf
| ├─css
| | ├─app.666bbb25.css

流程:

1、在入口文件main.go最上面,添加2行

//go:generate statik -src=./dist
//go:generate go fmt statik/statik.go

这2句代码的意思是,我们在项目目录下执行 go generate 命令时,会运行这2句代码,将dist下的静态文件打包到statik/statik.go

2、代码部分:

import (
"github.com/gin-contrib/static"
"github.com/gin-gonic/gin"
"github.com/rakyll/statik/fs"
_ "path/statik" //项目下的statik
)

声明一个filesystem结构体

type GinFS struct {
FS http.FileSystem
}
// Open 打开文件
func (b *GinFS) Open(name string) (http.File, error) {
return b.FS.Open(name)
}

// Exists 文件是否存在
func (b *GinFS) Exists(prefix string, filepath string) bool {
if _, err := b.FS.Open(filepath); err != nil {
return false
}
return true
}
var StaticFS static.ServeFileSystem
StaticFS = &GinFS{}
StaticFS.(*GinFS).FS,_ = fs.New()
c.Use(static.Serve("/",StaticFS))

此时,就建立了一个静态文件服务器,注意gin的路由方法不能相对于根目录了,否则gin就会从路由名往下找静态文件了,我们需要增加一个路由分组,让gin绕过静态文件。如

v1 := c.Group("/v1",AuthToken()){
v1.GET("/menus",func(c *gin.Context) {
......
}
}
构建项目
  • 运行 go generate 打包静态文件
  • 运行 go build 构建单文件执行文件