gpt4 book ai didi

http - 如果请求在http.Server中超时,为什么在Firefox中无限期重复请求?

转载 作者:行者123 更新时间:2023-12-01 22:08:51 24 4
gpt4 key购买 nike

我正在使用golang中的超时设置一个简单的服务器。当运行的处理时间超过超时时间时,如果我通过Firefox请求,该请求将无限期重复。但是,如果我使用Postman或curl,则不会重复请求。我想防止浏览器中的重复循环。

我试图手动关闭请求正文或检查上下文是否已取消,但是这些方法均无效。

package main

import (
"fmt"
"net/http"
"time"
)

func main() {
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
defer r.Body.Close()
fmt.Printf("Hello, you've requested: %s\n", r.URL.Path)
time.Sleep(time.Second * 2)
fmt.Fprintf(w, "Hello, you've requested: %s\n", r.URL.Path)
})
s := http.Server{
Addr: ":8080",
Handler: http.DefaultServeMux,
ReadTimeout: 1 * time.Second,
WriteTimeout: 1 * time.Second,
}
s.ListenAndServe()
}

我希望处理程序退出并且不再重复。

最佳答案

以我的理解,您面临的问题是服务器超时突然关闭了底层tcp conn,而没有编写适当的http响应,同时,当firefox检测到conn突然关闭时,它似乎决定重试N次,可能是因为它假定遇到连接问题。

我相信解决方案是使用http.Handler来控制处理程序的处理持续时间,并在超时到期时返回正确的HTTP响应。

服务器超时应该更长,并用于防止异常的客户端行为,而不是处理程序的缓慢。

标准的HTTP包为此提供了TimeoutHandler函数。

package main

import (
"fmt"
"net/http"
"time"
)

func main() {
slowHandler := func(w http.ResponseWriter, r *http.Request) {
defer r.Body.Close()
fmt.Printf("Hello, you've requested: %s\n", r.URL.Path)
time.Sleep(time.Second * 2)
fmt.Fprintf(w, "Hello, you've requested: %s\n", r.URL.Path)
}
http.HandleFunc("/", slowHandler)

var handler http.Handler = http.DefaultServeMux
handler = http.TimeoutHandler(handler, time.Second, "processing timeout")

s := http.Server{
Addr: ":8080",
Handler: handler,
// ReadTimeout: 1 * time.Second,
// WriteTimeout: 1 * time.Second,
}
s.ListenAndServe()
}

关于http - 如果请求在http.Server中超时,为什么在Firefox中无限期重复请求?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/58759303/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com