Go HTTP空闲连接池和http trace

我有一个长时间运行的 GO 程序(版本 1.18),它使用 RESTY 每秒同时发送数百个 GET 请求到远程https://api.abcd.com。每个 GET 请求都是一个单独的 go-routine,它使用相同的 RESTY 客户端。


远程服务器https://api.abcd.com是nginx/1.19.2(HTTP/2),IP地址是11.11.11.11和22.22.22.22。是的,这个远程服务器有多个 IP 地址。


我在设置 RESTY 客户端时使用主机名 SetBaseURL("https://api.abcd.com")


传输配置是 RESTY 中的默认配置。


TraceInfo() 在 RESTY 客户端启用。跟踪信息中有一个“IsConnReused”字段。这个IsConnReused实际上来自于GO httptrace包中的struct GotConnInfo:


type GotConnInfo struct {

    Conn net.Conn


    // Reused is whether this connection has been previously used for another HTTP request.

    Reused bool


    // WasIdle is whether this connection was obtained from anidle pool.

    WasIdle bool


    // IdleTime reports how long the connection was previously idle, if WasIdle is true.

    IdleTime time.Duration

}

问题 1:GO httptrace 根据主机名(api.abcd.com)或 IP 地址确定“连接重用”?


问题2:GO http包空闲连接池其实就是一个map,key是一个struct类型的connectMethodKey。此结构中的地址字段是主机名还是 IP 地址?


type connectMethodKey struct {

    proxy, scheme, addr string

    onlyH1              bool

}

这是我在 TraceInfo() 中找到的。程序一开始运行时,所有的请求都发送到11.11.11.11:443。几分钟后,所有请求都发送到 22.22.22.22,不再是 11.11.11.11。然后,几分钟后,所有请求再次开始发送到 11.11.11.11,这次没有发送到 22.22.22.22。


问题3:当请求开始发送到22.22.22.22时,到11.11.11.11的套接字连接是空闲的,为什么GO http不再使用空闲连接了?我不认为那些空闲连接已经超时。


慕盖茨4494581
浏览 139回答 1
1回答

蓝山帝景

问题 1:GO httptrace 根据主机名(api.abcd.com)或 IP 地址确定“连接重用”?httptrace.GotConnInfo.Reused跟踪 TCP 连接是否用于另一个 HTTP 请求。它是每个 IP 地址。问题2:GO http包空闲连接池其实就是一个map,key是一个struct类型的connectMethodKey。此结构中的地址字段是主机名还是 IP 地址?addr是hostname如果您将请求发送到类似的东西,则可能是一个 IP http://127.0.0.1/。问题3:当请求开始发送到22.22.22.22时,到11.11.11.11的套接字连接是空闲的,为什么GO http不再使用空闲连接了?我不认为那些空闲连接已经超时。如果您使用 HTTP 1,它的工作方式可能会有所不同。有了它,每个请求都需要自己的 TCP 连接。后续请求可能会重用TCP连接,但如果要并行运行请求,则需要建立多个TCP连接。每个连接都会使用不同的 IP 地址,您会看到流量均匀分布。使用 HTTP/2,单个 TCP 连接可用于多个并行请求。该连接使用单个 IP 地址。这是 GO 计算新请求是否可以使用开放连接的方式:https://cs.opensource.google/go/x/net/+/69896b71:http2/transport.go;l=881;drc=69896b714898bee1e3403560cd2e1870bcc8bd35;bpv=1;bpt=1使用这些婴儿车在多个 TCP 连接之间分配流量。
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go