Go 的 net 包提供了创建监听服务器的能力。然而,由于listen.Accept方法的阻塞性质,优雅地停止这些服务器可能具有挑战性。
停止服务器的一种常见方法是关闭侦听套接字。但是,这可能会导致在连接接受期间无法将错误与真正的错误区分开来。因此,以下代码片段显示了此问题:
// ... // Listen for incoming connections func (es *EchoServer) serve() { for { conn, err := es.listen.Accept() // FIXME: I'd like to detect "use of closed network connection" here // FIXME: but it isn't exported from net if err != nil { log.Printf("Accept failed: %v", err) break } // ... } // ... }
为了解决此限制,我们可以利用 es.done 通道在服务器启动之前发送信号停了下来。以下是代码的改进方法:
// ... // Listen for incoming connections func (es *EchoServer) serve() { for { conn, err := es.listen.Accept() if err != nil { select { case <-es.done: // Server is being stopped, so we can exit without logging the error. default: log.Printf("Accept failed: %v", err) } return } // ... } } // Stop the server by closing the listening socket func (es *EchoServer) stop() { es.done <- true es.listen.Close() }
通过在关闭监听套接字之前向 es.done 通道发送一个值,serve 函数可以确定服务器何时停止并正常退出,而不会记录虚假信息错误。
以上是如何优雅地停止 Go 监听服务器而不出现虚假错误?的详细内容。更多信息请关注PHP中文网其他相关文章!