当我在处理https://nhooyr.io/websocket时,我注意到当从Hijack返回的连接关闭时,r.Context()会被取消。这种行为很奇怪,因为在Hijack之后,net/http不应该取消请求上下文。毕竟,它怎么能知道连接已经关闭了呢?
我追踪到了问题的根源,那就是Hijack返回的bufio.Reader。当读取出错时,会导致r.Context被取消。
在我的项目中,我使用了从Hijack返回的所有bufio.Reader进行读取。当一个goroutine关闭连接时,另一个goroutine会从连接中读取数据,因此由于这行代码,上下文会被取消。
我认为最好的做法是不让bufio.Reader上的读取操作导致r.Context被取消,因为在Hijack之后,net/http应该完全不参与进来。
7条答案
按热度按时间ie3xauqp1#
https://golang.org/cl/179458提到了这个问题:
net/http: never ever cancel r.Context() after Hijack
ghhaqwfi2#
感谢你报告这个问题@nhooyr!
你是否可以尝试解决一个可复现的问题,以便我们将其转换为测试用例,就像@bradfitz在你的CL中要求的那样?
我已经启动了一个种子测试用例https://play.golang.org/p/gidrGk8M5Dq,但只是为了长时间的事件而关闭了我的电脑。请帮助我继续进行测试,这样可以使你的复现(或在下面内联)
jbose2ul3#
问题的本质在于劫持连接,关闭它,然后从由Hijack返回的bufio Reader中读取并观察上下文。上下文被取消了。
zpqajqem4#
好的,谢谢你@nhooyr!所以也许https://play.golang.org/p/k5S0LVVXFhb对于你的测试来说已经足够了
它产生了
pw9qyyiw5#
嘿,@nhooyr,我记得在一个问题中你评论说我会继续做这件事。@clairerhoda想要接手这件事,所以她会继续进行并提交给Go1.14。
cgvd09ve6#
https://golang.org/cl/200437提到了这个问题:
net/http: don't cancel hijacked connection's request context
csbfibhn7#
#27408 似乎相关