mirror of
https://github.com/golang/go
synced 2024-11-24 02:00:20 -07:00
net/http: use TCP keep-alives for ListenAndServe and ListenAndServeTLS
Our default behavior for the common cases shouldn't lead to leaked TCP connections (e.g. from people closing laptops) when their Go servers are exposed to the open Internet without a proxy in front. Too many users on golang-nuts have learned this the hard way. No API change. Only ListenAndServe and ListenAndServeTLS are updated. R=golang-codereviews, cespare, gobot, rsc, minux.ma CC=golang-codereviews https://golang.org/cl/48300043
This commit is contained in:
parent
8da8b37674
commit
d6bce32a36
@ -1608,11 +1608,11 @@ func (srv *Server) ListenAndServe() error {
|
||||
if addr == "" {
|
||||
addr = ":http"
|
||||
}
|
||||
l, e := net.Listen("tcp", addr)
|
||||
if e != nil {
|
||||
return e
|
||||
ln, err := net.Listen("tcp", addr)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
return srv.Serve(l)
|
||||
return srv.Serve(tcpKeepAliveListener{ln.(*net.TCPListener)})
|
||||
}
|
||||
|
||||
// Serve accepts incoming connections on the Listener l, creating a
|
||||
@ -1742,12 +1742,12 @@ func (srv *Server) ListenAndServeTLS(certFile, keyFile string) error {
|
||||
return err
|
||||
}
|
||||
|
||||
conn, err := net.Listen("tcp", addr)
|
||||
ln, err := net.Listen("tcp", addr)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
tlsListener := tls.NewListener(conn, config)
|
||||
tlsListener := tls.NewListener(tcpKeepAliveListener{ln.(*net.TCPListener)}, config)
|
||||
return srv.Serve(tlsListener)
|
||||
}
|
||||
|
||||
@ -1837,6 +1837,24 @@ func (tw *timeoutWriter) WriteHeader(code int) {
|
||||
tw.w.WriteHeader(code)
|
||||
}
|
||||
|
||||
// tcpKeepAliveListener sets TCP keep-alive timeouts on accepted
|
||||
// connections. It's used by ListenAndServe and ListenAndServeTLS so
|
||||
// dead TCP connections (e.g. closing laptop mid-download) eventually
|
||||
// go away.
|
||||
type tcpKeepAliveListener struct {
|
||||
*net.TCPListener
|
||||
}
|
||||
|
||||
func (ln tcpKeepAliveListener) Accept() (c net.Conn, err error) {
|
||||
tc, err := ln.AcceptTCP()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
tc.SetKeepAlive(true)
|
||||
tc.SetKeepAlivePeriod(3 * time.Minute)
|
||||
return tc, nil
|
||||
}
|
||||
|
||||
// globalOptionsHandler responds to "OPTIONS *" requests.
|
||||
type globalOptionsHandler struct{}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user