Golang发送GET网络请求并绑定参数到结构体(gin框架)

golang发送网络请求探索过程

背景:突然有一天,我需要写一个接口给前端同学使用,这个接口是要给第三方接口发送一个网络请求,于是我遍开始从零到一的完成了这个接口。

具体实现

此接口是一个GET请求,需要传递id和token两个参数参数,其中,token不是普通的参数,是请求头header中的参数。以前我发送的所有带有参数的请求都是post请求,并且所有的请求参数的都json格式的数据(额...因为我只会这一种)。但是今天,要写的接口中需要调用第三方GET类型的接口,所以我只好学习如何写GET请求接口,为了就是和调用第三方接口时保持一致。


	//首先,声明一个结构体,根据此结构体创建的对象用来绑定GET请求发送的参数
	//补充:gin框架中一般都是把传递来的参数给绑定到接结构体中,结构体的定义也是根据参数的名称和类型的定义的
	type ResponseCheckOnline struct {
		HornId string `form:"id"`
		HornToken string `header:"token"`//token是存放在header中的,所以此处要打上header的标签
	}
	//声明一个对象
	var req ResponseCheckOnline 
	//接下来开始参数绑定
	c.ShouldBind(&req) //由于我们发送的是一个get请求,所以我们不能使用ShouldBindJson方法,我们应该使用ShouldBind函数,并且需要在结构体后面打上form标签,注意一定要打上from标签,对于GET请求的参数对应的结构体,如果打上的是json标签,那是无法绑定的(此函数功能十分强大,后面补充详细的内容)
	//上面绑定的是url中的param参数,不要忘记,我们还有一个参数是在header请求头里面的,我们也需要拿到这个参数绑定到结构体中
	c.ShouldBindHeader(&req)//最初在这个地方产生了疑惑,后面百度接口,我们使用此方法的同时,需要的上面的结构体中加入header标签(参考博客:https://blog.csdn.net/wohu1104/article/details/121928193)
	//这是参数校验,如果为空就是没绑定上,我们应该返回错误提示
	if req.HornId == "" || req.HornToken == "" {
		global.GVA_LOG.Error("通过喇叭id和token判断喇叭是否在线参数错误")
		return
	}
	//开始请求第三方接口判断喇叭是否在线,需要发送请求给第三方接口
	// 创建各类对象
	var client *http.Client
	var request *http.Request
	var resp *http.Response
	var body []byte

	//`这里请注意,使用 InsecureSkipVerify: true 来跳过证书验证`
	client = &http.Client{Transport: &http.Transport{
		TLSClientConfig: &tls.Config{
			InsecureSkipVerify: true,
		},
	}, Timeout: time.Duration(utils.TimeOut) * time.Millisecond}
	url := "http://xxx?id=" + req.HornId

	request, err := http.NewRequest(http.MethodGet, url, nil)//创建一个请求,第一个参数是请求类型,第二个参数是请求地址,第三个不太了解,好像是请求携带的一些东西吧,可以自行百度一下,此处填写nil即可
	if err != nil {
		log.Println("GetHttpSkip Request Error:", err)
		return
	}
	//加入 token,需要添加到header请求头中
	request.Header.Add("token", req.HornToken)
	//发送请求
	resp, err = client.Do(request)
	if err != nil {
		global.GVA_LOG.Error(fmt.Sprintf("查看喇叭状态失败,喇叭id:%s", req.HornId), zap.Error(err))
		return
	}
	defer resp.Body.Close()
	//读取返回的结果
	body, err = ioutil.ReadAll(resp.Body)
	//把结果绑定到到对象上面并反序列化为json类型
	data := new(appRes.CheckOnlineRes)
	err = json.Unmarshal(body, data)
	fmt.Println(data.DeviceStatus)

	defer resp.Body.Close()
	if err == nil {
		response.OkWithDetailed(data, "查看摄像头状态成功", c)
	} else {
		response.FailWithDetailed(nil, "查看摄像头状态失败", c)
	}
//此结构体后面的json标签都是需要根据我们此接口请求的第三方接口返回来的字段来定义的,如果和第三方接口返回的字段不一致,将无法成功绑定
type CheckOnlineRes struct {
	Code         int    `json:"code"`          //状态码
	Msg          string `json:"msg"`           //请求状态信息
	CheckOnlineResData  `json:"data"`  //摄像头是否在线,1 正常 2掉线 3禁用
}
//此结构体被上面结构体引用,定义此结构体的原因是第三方接口返回的第三个参数是一个数据类型的数据,有10余个,而我们只需要拿到一个即可
type CheckOnlineResData struct {
	DeviceStatus string `json:"deviceStatus"`
}

补充:c.shouldBind()函数

此函数功能十分强大,体现在他可以自动的去绑定多种类型的参数,可以绑定Post请求json类型的参数,如果是 POST 请求,首先检查 content-type 是否为 JSONXML,然后再使用 Formform-data

还可以绑定Get请求Params参数(此时只能使用 Form 绑定引擎Params参数),也就是在结构体后面打上form标签

同时也可以绑定form表单参数。

参考博客:Gin框架介绍及使用 | 李文周的博客 (liwenzhou.com)

说在最后,gin框架的参数大多都是绑定到结构体对象上,这些方法gin都已经实现好了,我们可以拿现成的方法来用,但是处理不同请求的不同类型的参数的时候,有一些要求,这些要求比较琐碎,比较容易忽略,从而导致参数绑定出现问题,所以再绑定参数到结构体上面时,我们需要心思细腻一点。

你可能感兴趣的:(golang,golang,后端,http)