写点什么

从零开发区块链应用 (七)--gin 框架参数获取

  • 2022 年 1 月 25 日
  • 本文字数:4045 字

    阅读完需:约 13 分钟

一、获取 query 参数

query 指的是 URL ? 后面携带的参数,例如 user/info?username=张三 &password=123。获取请求的 query 参数的方法如下:


  • 当使用DefaultQuery时,如果没有获取到浏览器输入的 username,则返回设置 defaultValue


username := ctx.DefaultQuery("username", "杰哥的技术杂货铺")
复制代码


  • 当使用Query时,如果没有获取到浏览器输入的 password,则默认返回""空串


password := ctx.Query("password")
复制代码


完整示例如下


浏览器输入为:


http://127.0.0.1:8000/user/info?username=张三&password=123456
复制代码


服务端返回为:


{"message":"success","password":"123456","username":"张三"}
复制代码


后端处理逻辑如下:


package main
import ( "github.com/gin-gonic/gin" "net/http")
func main() {
//设置gin模式 gin.SetMode(gin.ReleaseMode) //创建一个新的路由引擎 r := gin.New() // GET:请求方式; /user/info:请求的路径 r.GET("/user/info", func(ctx *gin.Context) { // 当使用DefaultQuery时,如果没有获取到浏览器输入的username,则返回设置defaultValue给username username := ctx.DefaultQuery("username", "杰哥的技术杂货铺") // 当使用Query时,如果没有获取到浏览器输入的password,则默认返回""空串 password := ctx.Query("password") // 返回json给浏览器 ctx.JSON(http.StatusOK, gin.H{ "message": "success", "username": username, "password": password, }) }) // 启动HTTP服务,默认在8080端口启动服务,也可以设置为其他端口如8000 r.Run(":8000")}
复制代码


注:一般使用 Query 方法

二、获取 form 表单参数

当前端请求的数据通过 form 表单提交时,例如向/user/info 发送一个 POST 请求,获取请求数据的方式如下:


完整示例如下


后端处理逻辑如下:


package main
import ( "github.com/gin-gonic/gin" "net/http")
func main() { //设置gin模式 gin.SetMode(gin.ReleaseMode) //创建一个新的路由引擎 r := gin.New() // POST:请求方式; /user/info:请求的路径 r.POST("/user/info", func(ctx *gin.Context) { //提交单个表单数据时 //如果没有在请求中获取到表单参数,则返回默认值"张三" username := ctx.DefaultPostForm("username", "张三") //如果没有在请求中获取到表单参宿,则返回""空串 password := ctx.PostForm("password") //提交复选框多个数据时 info := ctx.PostFormArray("info") // 输出json结果给调用方 ctx.JSON(http.StatusOK, gin.H{ "message": "success", "username": username, "password": password, "info": info, }) }) // 启动HTTP服务,默认在8080端口启动服务,也可以设置为其他端口如8000 r.Run(":8000")}
复制代码


注:一般使用 PostForm 方法

三、获取 JSON 参数

当前端请求的数据通过 json 提交时,例如向/user/info 发送一个 POST 请求,则获取请求参数的方式如下:


  • 使用 postman 配置 json 请求如下:



  • 后端处理逻辑如下:


package main
import ( "github.com/gin-gonic/gin" "net/http")
type User struct { // 如果想要指定返回的json为其他别名,则可以使用`json:"username"`定义json格式的别名 UserName string `json:"username"` PassWord string `json:"password"`}
func main() { //设置gin模式 gin.SetMode(gin.ReleaseMode) //创建一个新的路由引擎 r := gin.New() // POST:请求方式; /user/info:请求的路径 r.POST("/user/info", func(ctx *gin.Context) { // 创建一个json结构体实例并与请求json参数绑定 userBody := &User{} err := ctx.BindJSON(&userBody) // 判断json请求数据结构与定义的结构体有没有绑定成功 if err != nil { ctx.JSON(200, gin.H{ "err_no": 400, "message": "Post Data Err", }) } else { ctx.JSON(http.StatusOK, gin.H{ "username": userBody.UserName, "password": userBody.PassWord, }) } }) // 启动HTTP服务,默认在8080端口启动服务,也可以设置为其他端口如8000 r.Run(":8080")}
复制代码


  • 返回结果如下所示:

四、获取 path 参数

请求的参数通过 URL 路径传递,例如/user/info/张三/123456。获取请求 URL 路径中的参数的方式如下。


  • 浏览器输入为:


127.0.0.1:8080/user/info/张三/123456
复制代码


  • 后端处理逻辑如下:


package main
import ( "github.com/gin-gonic/gin" "net/http")
func main() { //设置gin模式 gin.SetMode(gin.ReleaseMode) //创建一个新的路由引擎 r := gin.New() // GET:请求方式; /user/info:请求的路径 r.GET("/user/info/:username/:password", func(ctx *gin.Context) { // 如果没有获取到相关路径参数,则返回""空串 username := ctx.Param("username") password := ctx.Param("password")
//返回结果给调用方 ctx.JSON(http.StatusOK, gin.H{ "message": "success", "username": username, "password": password, }) }) // 启动HTTP服务,默认在8080端口启动服务,也可以设置为其他端口如8000 r.Run(":8080")}
复制代码


  • 返回结果如下:


{"message":"success","password":"123456","username":"张三"}
复制代码


注意如下请求路由定义方式是不合法的,如果想要定义两个类似的请求路由,可以加入版本号进行区分,如/user/v1/info/——>/user/v2/info/,版本号从 v1 到 v2。


错误写法:


// GET:请求方式; /hello:请求的路径r.GET("/user/info/:username/:password", func(c *gin.Context) {    })r.GET("/user/info/:username/:password", func(c *gin.Context) {    })
复制代码


正确写法:


  r.GET("/user/v1/info/:username/:password", func(ctx *gin.Context) {    // 如果没有获取到相关路径参数,则返回""空串    username := ctx.Param("username")    password := ctx.Param("password")
//返回结果给调用方 ctx.JSON(http.StatusOK, gin.H{ "message": "success", "username": username, "password": password, }) })
r.GET("/user/v2/info/:username/:address", func(ctx *gin.Context) { // 如果没有获取到相关路径参数,则返回""空串 username := ctx.Param("username") address := ctx.Param("address")
//返回结果给调用方 ctx.JSON(http.StatusOK, gin.H{ "message": "success", "username": username, "address": address, }) })
复制代码

五、参数绑定

为了能够更方便的获取请求相关参数,提高开发效率,我们可以基于请求的 Content-Type 识别请求数据类型并利用反射机制自动提取请求中 QueryString、form 表单、JSON、XML 等参数到结构体中。 下面的示例代码演示了.ShouldBind()强大的功能,它能够基于请求自动提取 JSON、form 表单和 QueryString 类型的数据,并把值绑定到指定的结构体对象。


  • 通过 query 方式请求,此时输入 url,不需要其他配置:


  • 通过 json 方式请求,输入 url,输入 json body,输入 Content-Type=application/json。


  • 后端处理逻辑如下:


package main
import ( "github.com/gin-gonic/gin" "net/http")
// Login Binding from JSONtype Login struct { UserName string `form:"username" json:"username" binding:"required"` Password string `form:"password" json:"password" binding:"required"`}
func main() { //设置gin模式 gin.SetMode(gin.ReleaseMode) //创建一个新的路由引擎 r := gin.New() // 绑定JSON的示例 ({"username": "张三", "password": "123456"}) r.POST("/loginJSON", func(ctx *gin.Context) { // 创建一个结构体类型实例 login := Login{} if err := ctx.ShouldBind(&login); err == nil { ctx.JSON(http.StatusOK, gin.H{ "message": "login with json query", "username": login.UserName, "password": login.Password, }) } else { ctx.JSON(http.StatusBadRequest, gin.H{ "err_no": err.Error(), }) } })
// 绑定form表单示例 (user=张三&password=123456) r.POST("/loginForm", func(ctx *gin.Context) { login := Login{} // ShouldBind()会根据请求的Content-Type自行选择绑定器 if err := ctx.ShouldBind(&login); err == nil { ctx.JSON(http.StatusOK, gin.H{ "message": "login with form query", "username": login.UserName, "password": login.Password, }) } else { ctx.JSON(http.StatusBadRequest, gin.H{ "error": err.Error(), }) } })
// 绑定QueryString示例 (/loginQuery?user=张三&password=123456) r.GET("/loginQuery", func(ctx *gin.Context) { login := Login{} // ShouldBind()会根据请求的Content-Type自行选择绑定器 if err := ctx.ShouldBind(&login); err == nil { ctx.JSON(http.StatusOK, gin.H{ "message": "login with querystring query", "username": login.UserName, "password": login.Password, }) } else { ctx.JSON(http.StatusBadRequest, gin.H{ "error": err.Error(), }) } })
// 启动HTTP服务,默认在8080端口启动服务,也可以设置为其他端口如8000 r.Run(":8080")}
复制代码


ShouldBind 会按照下面的顺序解析请求中的数据完成绑定:


  • 如果是 GET 请求,只使用 Form 绑定引擎(query)。

  • 如果是 POST 请求,首先检查 content-type 是否为 JSON 或 XML,然后再使用 Form(form-data)。


至此,我们学会了 gin 框架如何获取请求参数的方式。

发布于: 刚刚阅读数: 2
用户头像

还未添加个人签名 2020.11.21 加入

还未添加个人简介

评论

发布
暂无评论
从零开发区块链应用(七)--gin框架参数获取