go-gin

[复制链接]
发表于 2025-9-1 23:41:42 | 显示全部楼层 |阅读模式

马上注册,结交更多好友,享用更多功能,让你轻松玩转社区。

您需要 登录 才可以下载或查看,没有账号?立即注册

×
前置

gin是go的一个web框架,我们简单介绍一下gin的利用

导入gin :"github.com/gin-gonic/gin" 我们利用import导入gin的包

简单示例:

  1. package main
  2. import (
  3.         "github.com/gin-gonic/gin"
  4. )
  5. func main() {
  6.         r := gin.Default()
  7.         r.GET("/", func(c *gin.Context) {
  8.                 c.JSON(200, gin.H{
  9.                         "message": "hello world",
  10.                 })
  11.         })
  12.     r.Run(":8080")
  13. }
复制代码
这里界说了一个简单gin-web。我们可以在浏览器中通过访问:localhost:8080/这个url,它会显示
  1. {
  2.   "message": "hello world"
  3. }
复制代码
创建路由引擎以及设置路由

创建引擎

创建路由引擎的方式有两种
  
  1. r := gin.Default()  //默认的,内置logger recovery这两个中间件
  2. r := gin.New()      //空的,没有内置中间件
复制代码
中间件:假设后端是a,前端是b。中间件就是在a和b之间的一个东西,我们根据中间件可以做许多东西。关于中间件的部分我们后面会讲到
   设置路由

设置路由也有两种方法,第一种是一个一个的设置路由
  1. func main() {
  2.         r := gin.Default()
  3.         r.GET("/u/a", func(c *gin.Context) {
  4.                 c.JSON(200, gin.H{
  5.                         "message": "hello a",
  6.                 })
  7.         })
  8.         r.GET("/u/b", func(c *gin.Context) {
  9.                 c.JSON(200, gin.H{
  10.                         "message": "hello b",
  11.                 })
  12.         })
  13.         r.GET("/u/c", func(c *gin.Context) {
  14.                 c.JSON(200, gin.H{
  15.                         "message": "hello c",
  16.                 })
  17.         })
  18.         r.GET("/u/d", func(c *gin.Context) {
  19.                 c.JSON(200, gin.H{
  20.                         "message": "hello d",
  21.                 })
  22.         })
  23.         r.Run(":8080")
  24. }
复制代码
如许一个一个的设置固然简单,但是看起来会很臃肿。而且我们发现它们前面都是 /u的路由,如许设置还容易看错。那我们来看第二种方法:路由分组
路由分组

我们通过 Group方法来设置分组,它的参数就是这个组的前置路由,它会返回一个routergroup的指针,我们通过这个指针来设置后续的子路由
  1. func main() {
  2.         r := gin.Default()
  3.         group := r.Group("/u")//设置路由组
  4.         {
  5.                 group.GET("/a", func(c *gin.Context) {//添加组员a
  6.                         c.JSON(200, gin.H{
  7.                                 "message": "hello world",
  8.                         })
  9.                 })
  10.                 group.GET("/b", func(c *gin.Context) {//添加组员b
  11.                         c.JSON(200, gin.H{
  12.                                 "message": "hello world",
  13.                         })
  14.                 })
  15.                 group.GET("/c", func(c *gin.Context) {//添加组员c
  16.                         c.JSON(200, gin.H{
  17.                                 "message": "hello world",
  18.                         })
  19.                 })
  20.                 group.GET("/d", func(c *gin.Context) {//添加组员d
  21.                         c.JSON(200, gin.H{
  22.                                 "message": "hello world",
  23.                         })
  24.                 })
  25.         }
  26.         r.Run(":8080")//启动
  27. }
复制代码
如许分组方便我们后续阅读代码以及中间件设置。
数据获取

获取url中的变量

路径参数

  1. group.POST("/c/:name", func(c *gin.Context) {//这里的请求也可以是get或其他请求
  2.                         name := c.Param("name")
  3.                         c.JSON(200, gin.H{
  4.                                 "message": name,
  5.                         })
  6.                 })
复制代码
我们利用c.Param("name")获取到变量,然后返回数据。
一个路由可以携带多个变量,如 /c/:name/:age 如许我们访问的时候就可以携带两个变量了
查询参数

查询参数的设置如下
  1. group := r.Group("/u")
  2.         {
  3.                 group.POST("/c", func(c *gin.Context) {//路由设置没有改变
  4.                         name := c.Query("name")//使用Query查询
  5.                         c.JSON(200, gin.H{
  6.                                 "message": name,
  7.                         })
  8.                 })
  9.         }
复制代码
这种方式传参的时候需要用 /u/c?name=xxx 这种方式传参,路由后面加个 ?key=value多个参数用&毗连
获取表单数据

前端有时候会返回一个表单的数据,我们需要从表单中获取我们需要的数据。这里我们一般都利用post请求,因为它不会把信息显示在url中。get请求也可以但是我们只有在特定的情况下才会利用get请求(因为url的长度有限定)
这里的请求方法取决于表单的method
form表单有两个属性,一个method指定请求方法,一个action指定请求的url。
post请求获取表单数据

  1. <form action="http://localhost:8080/u/c" method="POST">
  2.         <input type="text" name="name">
  3.         <input type="text" name="pass">
  4.         <input type="submit" value="submittt">
  5. </form>
复制代码
这是一个简单的表单,里面包罗name、id还有一个提交按钮。请求方法为post,提交到http://localhost:8080/u/c这个url

我们如果要获取它的表单数据,需要知道提交过来的数据的 name 属性是什么,然后利用PostForm获取
  1. func main() {
  2.         r := gin.Default()
  3.         group := r.Group("/u")
  4.         {
  5.                 group.POST("/c", func(c *gin.Context) {
  6.                         name := c.PostForm("name")//对应表单name属性为name的文本域
  7.                         pass := c.PostForm("pass")//对应表单name属性为pass的文本域
  8.                         fmt.Println(name, pass)
  9.                         c.JSON(http.StatusOK, gin.H{
  10.                                 "name": name,
  11.                                 "pass": pass,
  12.                         })
  13.                 })
  14.         }
  15.         r.Run(":8080")
  16. }
复制代码

如果要获取单选框也是利用PostForm。多选框则是PostFormArray,而且返回的是一个string范例的切片
多选框内,多个相同的name属性的选择是一组,value属性对应获取到的值是什么
html代码
  1. <form action="http://localhost:8080/u/c" method="POST" >
  2.         <input type="checkbox" name="remember" value="1">
  3.         <input type="checkbox" name="remember" value="2">
  4.         <input type="checkbox" name="remember" value="3">
  5.         <input type="checkbox" name="remember" value="4">
  6.         <input type="submit" value="submittt">
  7. </form>
复制代码
go代码
  1. func main() {
  2.         r := gin.Default()
  3.         group := r.Group("/u")
  4.         {
  5.                 group.POST("/c", func(c *gin.Context) {
  6.                         arr := c.PostFormArray("remember")
  7.                         fmt.Println(reflect.TypeOf(arr))
  8.                         c.JSON(http.StatusOK, gin.H{
  9.                                 "arr": arr,
  10.                         })
  11.                 })
  12.         }
  13.         r.Run(":8080")
  14. }
复制代码
post请求获取表单文件

有的时候表单也是需要上传一些文件的,这时候就需要我们获取文件信息了
首先是表单部分,在表单的头部我们需要添加  enctype="multipart/form-data"这个属性来说明是含文件的上传
  1. <form action="http://localhost:8080/u/c" method="POST" enctype="multipart/form-data" >
  2.         <input type="file" name="file">
  3.         <input type="submit" value="submittt">
  4. </form>
复制代码
后端获取的时候需要利用c.FormFile()
  1. group.POST("/c", func(c *gin.Context) {
  2.                         file, err := c.FormFile("file")//返回文件和错误信息
  3.                         if err != nil {
  4.                                 fmt.Println("err:", err)
  5.                                 return
  6.                         } else {
  7.                                 fmt.Println(file.Filename)//文件名
  8.                                 fmt.Println(file.Size)//文件大小
  9.                                 os.MkdirAll("./tmp", os.ModePerm)//新建一个目录,如果目录存在就不会报错,而是直接跳过
  10.                                 err := c.SaveUploadedFile(file, "./tmp/"+file.Filename)//保存
  11.                 if err!= nil {
  12.                 错误处理
  13.                 }
  14.                         }
  15.                 })
复制代码
我们如果需要保存文件就要利用 c.SaveUploadedFile(file, "保存路径"+file.Filename),这个路径需要我们提前创建好。它会返回一个错误信息,我们可以根据错误信息来判断是否存储乐成
gin的中间件

中间件的本质就是一个函数,该函数的作用是检查某些数据是否是正常数据,从而决定是否继续实行
设置中间件的方法主要有以下几种

  • 全局设置         --   设置到路由引擎上
  • 单个路由设置  --   设置到单个的路由上
  • 路由组设置      --    设置到一个路由组上
  1. func main() {
  2.         r := gin.New()
  3.         r.Use()//全局引用中间件
  4.         group := r.Group("/u").Use()//路由组引用中间件
  5.         {
  6.                 group.GET("/a", func(c *gin.Context) {
  7.                         c.JSON(200, gin.H{
  8.                                 "message": "hello world",
  9.                         })
  10.                 })
  11.         }
  12.         r.GET("/b", func(c *gin.Context) {
  13.                 c.JSON(200, gin.H{
  14.                         "message": "hello world",
  15.                 })
  16.         }).Use()//单个路由引用中间件
  17.         r.Run(":8080")
  18. }
复制代码
中间件实行的顺序是和引用的顺序有关
.Use(中间件a,b,c,d)这里引用了四个中间件,当我访问对应的路由的时候这四个中间件会按照abcd的顺序挨个实行
  1. var str string
  2. func A() gin.HandlerFunc {
  3.         return func(c *gin.Context) {
  4.                 str = str + "a "
  5.         }
  6. }
  7. func B() gin.HandlerFunc {
  8.         return func(c *gin.Context) {
  9.                 str = str + "b "
  10.         }
  11. }
  12. func C() gin.HandlerFunc {
  13.         return func(c *gin.Context) {
  14.                 str = str + "c "
  15.         }
  16. }
  17. func D() gin.HandlerFunc {
  18.         return func(c *gin.Context) {
  19.                 str = str + "d "
  20.         }
  21. }
  22. func main() {
  23.         r := gin.New()
  24.         r.Use(A(), B(), C(), D()) //全局引用中间件
  25.         r.GET("/", func(c *gin.Context) {
  26.                 c.JSON(200, gin.H{
  27.                         "str:": str,
  28.                 })
  29.         })
  30.         r.Run(":8080")
  31. }
复制代码
我们访问http://localhost:8080/这个路由的时候网页上显示的就是{"str:":"a b c d "}
这就是基础的中间件利用,假设abcd是四个不同的验证件,其中一个出错就不能继续实行后面的了,而是返回错误信息。这里我们要利用的是c.Abrot() c.Next()两个流程控制函数
c.Next()这个函数的作用就是允许实行后续中间件以及终极处置惩罚函数
c.Abrot()这个函数就是不实行后续的中间件和终极处置惩罚函数
无论是abrot还是next,它们地点的中间件都会完备的实行,除非return了。
  1. var str string
  2. func A() gin.HandlerFunc {
  3.         return func(c *gin.Context) {
  4.                 if str == "" {//判断是否正确,正确则拼接字符串,否则报错
  5.                         str = str + "a "
  6.                         c.Next()
  7.                 } else {
  8.                         c.AbortWithStatus(http.StatusNotAcceptable)                }
  9.         }
  10. }
  11. func B() gin.HandlerFunc {
  12.         return func(c *gin.Context) {
  13.                 if str == "a " {
  14.                         str = str + "b "
  15.                         c.Next()
  16.                 } else {
  17.                         c.AbortWithStatus(http.StatusNotAcceptable)                }
  18.         }
  19. }
  20. func C() gin.HandlerFunc {
  21.         return func(c *gin.Context) {
  22.                 if str == "a b " {
  23.                         str = str + "c "
  24.                         c.Next()
  25.                 } else {
  26.                         c.AbortWithStatus(http.StatusNotAcceptable)
  27.                 }
  28.         }
  29. }
  30. func D() gin.HandlerFunc {
  31.         return func(c *gin.Context) {
  32.                 if str == "a b c " {
  33.                         str = str + "d "
  34.                         c.Next()
  35.                 } else {
  36.                         c.AbortWithStatus(http.StatusNotAcceptable)                }
  37.         }
  38. }
  39. func main() {
  40.         r := gin.New()
  41.         r.Use(A(), B(), C(), D()) //全局引用中间件
  42.         r.GET("/", func(c *gin.Context) {
  43.                 c.JSON(200, gin.H{
  44.                         "str:": str,
  45.                 })
  46.         })
  47.         r.Run(":8080")
  48. }
复制代码
这里的abort有多个版本

  • Abort()
  • AbortWithStatus(状态码)
  • AbortWithStatusJSON(状态码,gin.H{key:value})
前两个访问的时候浏览器都是访问错误,后面的会返回我们的json数据到浏览器上

gin加载HTML

gin设置静态资源目录
r.Static("/static", "./static")
当我们访问/static的时候就是访问的项目中的./static,也就是说可以在浏览器访问一些文件。

加载HTML模板
r.LoadHTMLGlob("templates/*")         加载templates下的全部.html文件
 

返回HTML文件
利用c.HTML(状态码,“html文件”,gin.H{})
这里要注意的是我们如果利用r.LoadHTMLGlob("templates/*") 之后,单独的一个index.html文件着实就是加载的templates/index.html文件
最后的gin.H{}是传入模板的数据,它传递的是key:value的形式,前端html文件可以通过{{.key}}来访问这个value

免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。
继续阅读请点击广告
回复

使用道具 举报

×
登录参与点评抽奖,加入IT实名职场社区
去登录
快速回复 返回顶部 返回列表