golang中server.GracefulStop()的行为

golang中server.GracefulStop()的行为,go,server,grpc,goroutine,grpc-go,Go,Server,Grpc,Goroutine,Grpc Go,我有一个gRPC服务器,我已经实现了优雅地关闭我的gRPC服务器 fun main() { //Some code term := make(chan os.Signal) go func() { if err := grpcServer.Serve(lis); err != nil { term <- syscall.SIGINT } }() signal.N

我有一个gRPC服务器,我已经实现了优雅地关闭我的gRPC服务器

fun main() {
    //Some code
    term := make(chan os.Signal)
    go func() {
            if err := grpcServer.Serve(lis); err != nil {
                term <- syscall.SIGINT
            }
        }()

    signal.Notify(term, syscall.SIGTERM, syscall.SIGINT)
    <-term
    server.GracefulStop()
    closeDbConnections()
}
这个案例没有像预期的那样起作用。完成
server.GracefulStop()
后,
closeDbConnections()
可能会运行,也可能不会运行(通常不会运行到完成)。我在测试后一个案例,通过从终端点击Ctrl-C发送SIGINT


有人能解释一下这种行为吗?

我不确定您的问题(请澄清),但我建议您以这种方式重构
main

func main(){
// ...
errChan:=make(chan错误)
stopChan:=接通(切换操作信号)
//将操作系统事件绑定到信号通道
signal.Notify(stopChan、syscall.SIGTERM、syscall.SIGINT)
//在单独的goroutine中运行阻塞调用,通过通道报告错误
go func(){
如果错误:=grpcServer.service(lis);错误!=nil{

errChan您没有提供问题代码的示例,但是如果您没有等待goroutine在
main
中返回,您将在程序完成之前退出该程序。@JimB goroutine正在运行服务器,
main
GracefulStop
完成之前不会返回,因此我看不出有任何问题这里。@agyeya,回答你的问题,这不需要时间。当
main
返回(在函数末尾)时,进程退出。@Adrian:他们说“这很好”,这是我们似乎没有的非工作情况。这听起来像是基本的“goroutines之前退出main”问题。哦,我明白你在说什么-是的,这将是一个假设中的问题(但未显示)代码。添加了有问题的代码。只是试图理解它的问题,我的用例对另一个代码很满意。嗨,我添加了有问题的代码。如果我对goroutines执行的理解有差距,请告诉我。@agyeya我建议您研究我上面提供的代码示例并进行比较这就是我们在后端的工作方式。这种方法经过了很好的测试,是可靠的。
func main() {
    term := make(chan os.Signal)
    go func() {
        signal.Notify(term, syscall.SIGTERM, syscall.SIGINT)
        <-term
        server.GracefulStop()
        closeDbConnections()
    }()
    if err := grpcServer.Serve(lis); err != nil {
        term <- syscall.SIGINT
    }
}