如何在Go-Gin中拦截一个ReST API响应并将其存储在数组中

huangapple go评论75阅读模式
英文:

How to intercept a ReST API response in an array go-gin

问题

我正在使用go-gin服务器在我的golang项目中,并从外部API获取一些数据,该API返回一个数组作为响应。

[
  {
    "Continent": "South America",
    "Countries": [
      {
        "Country": "Argentina"
      }
    ]
  }
]

在我的golang代码中,这是我发送请求和拦截响应的方式:

client := &http.Client{Transport: tr}
rget, _ := http.NewRequest("GET", "http://x.x.x.x/v1/geodata", nil)

resp, err := client.Do(rget)
if err != nil {
    fmt.Println(err)
    fmt.Println("Failed to send request")
}
defer resp.Body.Close()
respbody, err := ioutil.ReadAll(resp.Body)
c.Header("Content-Type", "application/json")
c.JSON(200, string(respbody))

这样可以得到正确的响应,但是我得到的是一个包含整个数组的字符串。所以我得到的响应是:

"[{\"Continent\":\"South America\",\"Countries\":[{\"Country\":\"Argentina\"}] } ]"

如何拦截响应并将其作为数组而不是字符串?
我甚至尝试了以下方法,它确实给了我一个数组,但是是一个空数组。我的响应体中的元素既可以是数组也可以是字符串,所以内容是混合的。

type target []string
json.NewDecoder(resp.Body).Decode(target{})
defer resp.Body.Close()
c.Header("Content-Type", "application/json")
c.JSON(200, target{})
英文:

I am using go-gin server in my golang project and fetching some data from an external API which returns an array as response

[
  {
    "Continent": "South America",
    "Countries": [
      {
        "Country": "Argentina"
      }
    ]
  }
]

In my golang code here is how I am sending request and intercepting response

client := &http.Client{Transport: tr}
rget, _ := http.NewRequest("GET", "http://x.x.x.x/v1/geodata", nil)

resp, err := client.Do(rget)
if err != nil {
	fmt.Println(err)
	fmt.Println("Failed to send request")
}
defer resp.Body.Close()
respbody, err := ioutil.ReadAll(resp.Body)
c.Header("Content-Type", "application/json")
c.JSON(200, string(respbody))

This gives currect response but instead of an array I get a string with the entire array. So the response I get is

"[{\"Continent\":\"South America\",\"Countries\": [{\"Country\": \"Argentina\"} ] } ]"

How can intercept response as array instead of string?
I even tried the following which did gave me an array but a blank one. The elements in my response body may be array as well as strings so the content is mixed.

type target []string
json.NewDecoder(resp.Body).Decode(target{})
defer resp.Body.Close()
c.Header("Content-Type", "application/json")
c.JSON(200, target{})

答案1

得分: 1

你的第一个示例不起作用,因为你试图将一个字符串作为JSON进行编组,这只会转义字符串。
相反,将最后一行改为:

c.String(200, string(respbody))

这不会改变你从第三方接收到的字符串,只会返回它。参见这里的区别。

如果你想检查数据在程序中传输的情况,你首先必须将JSON字符串解码为一个结构体数组,如下所示:

type Response []struct {
    Continent string `json:"Continent"`
    Countries []struct {
	    Country string `json:"Country"`
    } `json:"Countries"`
}
英文:

Your first example does not work because you are trying to marshal a string as JSON which will only escape the string.
Rather, change the last line to

c.String(200, string(respbody))

This won't change the string you are receiving from your third party at all and will just return it. See here for the difference.

If you want to inspect the data as it travels through your program, you have to first decode the JSON string into an array of structs like this:

type Response []struct {
    Continent string `json:"Continent"`
    Countries []struct {
	    Country string `json:"Country"`
    } `json:"Countries"`
}

1: https://play.golang.org/p/ivYmITK6NJ "here"

huangapple
  • 本文由 发表于 2016年11月17日 18:27:06
  • 转载请务必保留本文链接:https://go.coder-hub.com/40652375.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定