Golang Go语言中 net/http 返回状态码是非 200 获取响应体疑问

发布于 1周前 作者 bupafengyu 来自 Go语言

Golang Go语言中 net/http 返回状态码是非 200 获取响应体疑问

net/http 包请求一个 URL 地址,返回状态码是非 200,比如 400,如何获取响应体的内容呢?

测试结果:

  • 使用 postman 、Python requests 库获取内容
{
    "errcode": 4023,
    "errmsg": "认证失败"
}
  • 使用 go net/http 包 获取内容
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
<title>400 Bad Request</title>
<h1>Bad Request</h1>
<p>The browser (or proxy) sent a request that this server could not understand.</p>

net/http 包是否状态码 200 才读响应体的内容呢?


更多关于Golang Go语言中 net/http 返回状态码是非 200 获取响应体疑问的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html

6 回复

net/http 只有在 err 不为 nil 时才不可以读取 resp.Body,底下那个就是 server 返回的消息体。

你可以使用 netcat 监听本地一个端口,对比 postman 或 rewuests 的请求与 net/http 的请求有什么差异。

上面那个是 JSON,底下那个看着像是 HTTP 服务器默认的错误页面。所以你确认 postman 和 go 代码测试的是同一个服务器吗? postman 那个也是 400 错误吗?

你需要补一点 HTTP 特别是 TCP 基础,这样你就明白无论什么 postman 还是 requests 都可以通过 telnet 来替代。

以及你八成还要学学《提问的智慧》,若是可以,还可以搜搜 coolshell 的『 XY 问题』

更多关于Golang Go语言中 net/http 返回状态码是非 200 获取响应体疑问的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


不对的,你两个请求返回内容不一样。
后边的 html 就是 body,显然不是你说的 json,应该是请求的部分错了。

看起来像是个前辈……奇怪……

应该是程序问题( https://github.com/Ropon/newpanel ),新写一个 demo 又是对的。
D:\Seafile\Go\src\test>gor
{“errcode”: 4025, “errmsg”: “this is test”}

找到问题了,是这行引起的
# api = Api(site_bp, default_mediatype=“application/json;charset=utf-8”)
api = Api(site_bp)

在Golang中使用net/http包进行HTTP请求时,如果服务器返回的状态码不是200(即成功响应),直接读取响应体可能会遇到一些问题。这是因为HTTP客户端默认在接收到非200状态码时,会关闭响应体,以防止用户在不检查状态码的情况下错误地读取响应体,从而导致资源泄漏。

要正确读取非200状态码下的响应体,你需要在检查状态码之前,手动检查并保存响应体的读取器(Body字段),然后再进行读取。以下是一个示例代码:

resp, err := http.Get("http://example.com")
if err != nil {
    // 处理错误
}
defer resp.Body.Close()

// 先读取响应体到变量中
bodyBytes, err := ioutil.ReadAll(resp.Body)
if err != nil {
    // 处理错误
}
bodyString := string(bodyBytes)

// 然后检查状态码
if resp.StatusCode != http.StatusOK {
    fmt.Printf("服务器返回错误状态码: %d, 响应体: %s\n", resp.StatusCode, bodyString)
} else {
    fmt.Println("请求成功,响应体:", bodyString)
}

注意,上述代码中使用了ioutil.ReadAll来读取整个响应体到内存中,这在处理大响应体时可能不是最佳实践,因为它可能会导致内存占用过高。对于大文件或数据流,建议使用逐块读取的方式。同时,记得在不再需要响应体时关闭它,以避免资源泄漏。

回到顶部