Golang Gin 中间件

发布时间 2023-11-24 11:30:54作者: 看一百次夜空里的深蓝

一.中间件

  1 package main
  2 
  3 import (
  4     "fmt"
  5     "gin01/middlewares"
  6     "text/template"
  7     "time"
  8 
  9     "github.com/gin-gonic/gin"
 10 )
 11 
 12 /***
 13 中间件的注意事项:
 14     1. gin.Default()默认使用了Logger和Recover中间件,其中:
 15         Logger 中间件将日志写入gin.DefaultWriter,即使配置了GIN_MODE=release.
 16         Recover 中间件会recover任何panic.如果没有panic的话,会写入500响应.
 17         如果不详使用上面两个默认中间件,可以使用gin.New()新建一个没有任何默认中间件的路由.
 18 
 19     2. gin中间件中使用goroutine
 20         当在中间件或handler中启动新的goroutine时,不能使用原始上下文(c *gin.Context), 必须使用副本(c.Copy())
 21 
 22 ***/
 23 
 24 func UnixToTime(timestamp int) (result string, err error) {
 25     fmt.Println(timestamp)
 26     t := time.Unix(int64(timestamp), 0)
 27     return t.Format("2006-01-02 15:04:05"), nil
 28 
 29 }
 30 
 31 func initMiddleware(c *gin.Context) {
 32     fmt.Println("我是中间件start")
 33     start := time.Now().UnixMicro()
 34     c.Set("username", "name")           // 在中间件中设置的数据,
 35     username := c.GetString("username") // 可以在其他中间件中获取到
 36     fmt.Println(username)
 37     if true { // 这里如果没有调用到c.Next()的话就会按照原来的顺序执行
 38         c.Next()  // 主动在控制函数中调用剩下的所有控制函数
 39         c.Abort() // 终止该请求的剩余控制处理函数
 40     }
 41 
 42     // 当有耗时任务执行,并不影响返回响应的时候,不能直接将(c *gin.Context)在goroutine中使用
 43     cCp := c.Copy()
 44     go func() {
 45         time.Sleep(time.Second * 2)
 46         fmt.Println("Done! in path", cCp.Request.URL.Path)
 47     }()
 48 
 49     end := time.Now().UnixMicro()
 50     fmt.Println("我是中间件end,耗时:", end-start)
 51 }
 52 
 53 func GlobMiddlewareOne(c *gin.Context) {
 54     fmt.Println("我是全局中间件:GlobMiddlewareOne")
 55 }
 56 
 57 func GlobMiddlewareTwo(c *gin.Context) {
 58     fmt.Println("我是全局中间件:GlobMiddlewareTwo")
 59 }
 60 
 61 func main() {
 62     router := gin.Default()
 63     router.SetFuncMap(template.FuncMap{
 64         "UnixToTime": UnixToTime,
 65     })
 66 
 67     // 配置全局中间件
 68     router.Use(GlobMiddlewareOne, GlobMiddlewareTwo)
 69 
 70     router.LoadHTMLGlob("templates/**/*")
 71 
 72     router.Static("/static", "./static")
 73 
 74     // 中间件: GET/POST/PUT/DELETE 第一个参数是路由路径,第二个参数开始可以传多个func(*Context)控制函数,
 75     //                              收到请求后会依次按顺序执行, 你也可以c.Next()主动在控制函数中调用剩下的所有函数
 76     router.GET("/", middlewares.InitMiddleware, initMiddleware, func(c *gin.Context) {
 77         fmt.Println("我是首页")
 78         c.String(200, "我是首页")
 79     }, func(c *gin.Context) {
 80         fmt.Println("我是第三个控制函数")
 81         c.String(200, "我是第三个控制函数")
 82     })
 83 
 84     // 路由分组中间件
 85     // 分组中间件的设置一
 86     // adminRouters := r.Group("/admin", xxx)
 87     // 分组中间件的设置二
 88     // adminRouters.Use(xxx)
 89 
 90     router.Run("0.0.0.0:8080")
 91 
 92 }
 93 
 94 /***
 95 // 分组路由中间件的配置
 96 func AdminRouters(r *gin.Engine) {
 97 
 98     adminRouters := r.Group("/admin")
 99     // 分组中间件的设置一
100     // adminRouters := r.Group("/admin", xxx)
101     // 分组中间件的设置二
102     // adminRouters.Use(xxx)
103     {
104         // http://localhost:8080/admin/
105         adminRouters.GET("/", func(c *gin.Context) {
106             c.String(http.StatusOK, "后台首页")
107         })
108 
109         // 通过控制器去控制路由更方便,因为控制器可以继承
110         // http://localhost:8080/admin/user
111         adminRouters.GET("/user", admin.UserControl{}.Index)
112 
113         // http://localhost:8080/admin/user/add
114         adminRouters.GET("/user/add", admin.UserControl{}.Add)
115 
116         // http://localhost:8080/admin/user/edit
117         adminRouters.GET("/user/edit", admin.UserControl{}.Edit)
118 
119         // http://localhost:8080/admin/article
120         adminRouters.GET("/article", admin.ArticleControl{}.Index)
121     }
122 }
123 ***/

 

二.