如何使用gracefulStop关闭所有grpc服务器流?

2023-12-08

我试图停止从服务器端连接到流服务器的所有客户端。 其实我正在使用GracefulStop优雅地处理它的方法。

我正在等os.Interrupt在通道上发出信号以执行 gRPC 的正常停止。但它被卡住了server.GracefulStop()当客户端连接时。

func (s *Service) Subscribe(_ *empty.Empty, srv clientapi.ClientApi_SubscribeServer) error {
    ctx := srv.Context()

    updateCh := make(chan *clientapi.Update, 100)
    stopCh := make(chan bool)
    defer func() {
        stopCh<-true
        close(updateCh)
    }

    go func() {
        ticker := time.NewTicker(1 * time.Second)
        defer func() {
            ticker.Stop()
            close(stopCh)
        }
        for {
            select {
            case <-stopCh:
                return
            case <-ticker.C:
                updateCh<- &clientapi.Update{Name: "notification": Payload: "sample notification every 1 second"}
            }
        }
    }()

    for {
        select {
        case <-ctx.Done():
            return ctx.Err()

        case notif := <-updateCh:
            err := srv.Send(notif)
            if err == io.EOF {
                return nil
            }

            if err != nil {
                s.logger.Named("Subscribe").Error("error", zap.Error(err))
                continue
            }
        }
    }
}

我预计context在方法中ctx.Done()可以处理它并打破 for 循环。 如何关闭像这样的所有响应流?


创建一个global context用于您的 gRPC 服务。因此,浏览各个部分:

  • 每个 gRPC 服务请求都将使用此上下文(以及客户端上下文)来满足该请求
  • os.Interrupt处理程序将取消全局上下文;从而取消任何当前正在运行的请求
  • 终于发出了server.GracefulStop()- 应该等待所有活动的 gRPC 调用完成(如果他们没有立即看到取消)

例如,在设置 gRPC 服务时:

pctx := context.Background()
globalCtx, globalCancel := context.WithCancel(pctx)

mysrv := MyService{
    gctx: globalCtx
}

s := grpc.NewServer()
pb.RegisterMyService(s, mysrv)

os.Interrupt处理程序启动并等待关闭:

globalCancel()
server.GracefulStop()

gRPC 方法:

func(s *MyService) SomeRpcMethod(ctx context.Context, req *pb.Request) error {

    // merge client and server contexts into one `mctx`
    // (client context will cancel if client disconnects)
    // (server context will cancel if service Ctrl-C'ed)

    mctx, mcancel := mergeContext(ctx, s.gctx)

    defer mcancel() // so we don't leak, if neither client or server context cancels

    // RPC WORK GOES HERE
    // RPC WORK GOES HERE
    // RPC WORK GOES HERE

    // pass mctx to any blocking calls:
    // - http REST calls
    // - SQL queries etc.
    // - or if running a long loop; status check the context occasionally like so:

    // Example long request (10s)
    for i:=0; i<10*1000; i++ {
        time.Sleep(1*time.Milliscond)

        // poll merged context
        select {
            case <-mctx.Done():
                return fmt.Errorf("request canceled: %s", mctx.Err())
            default:
        }
    }
}

And:

func mergeContext(a, b context.Context) (context.Context, context.CancelFunc) {
    mctx, mcancel := context.WithCancel(a) // will cancel if `a` cancels

    go func() {
        select {
        case <-mctx.Done(): // don't leak go-routine on clean gRPC run
        case <-b.Done():
            mcancel() // b canceled, so cancel mctx 
        }
    }()

    return mctx, mcancel
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何使用gracefulStop关闭所有grpc服务器流? 的相关文章

  • 使用cgo时的多重定义

    package main int add int a int b return a b import C import fmt func main func Test1 fmt Println C add 1 3 export Test2
  • 如何使用 Java 原生接口从 Java 调用 Go 函数?

    可以通过以下方式调用 C 方法JNA https en wikipedia org wiki Java Native AccessJava 中的接口 如何使用 Go 实现相同的功能 package main import fmt impor
  • 检查值是否实现接口的说明

    我读过 Effective Go 和其他类似这样的问答 golang接口合规性编译类型检查 https stackoverflow com questions 17994519 golang interface compliance com
  • 构建链代码时 ltdl.h 未找到错误

    我正在尝试使用构建链码go build 当我运行 Go build 命令时它的报告 hyperledger fabric vendor github com miekg pkcs11 pkcs11 g o 29 18 fatal error
  • 仅使用 GRPC 连接到对话流 StreamingDetectIntent,卡在等待 responseStream.MoveNext

    我正在尝试将 DialogFlow API v2 与 Unity 结合使用 由于 Unity 还没有官方 SDK 所以我使用了 Grpc beta unity SDK 以及使用 Grpc 工具中的 Protobuf 和 protoc 创建的
  • 为什么奇数的切片容量与偶数的切片行为不同

    我注意到 当容量为奇数时 切片的容量会以不同的方式表现 更具体地说 当向切片添加元素时 切片的容量为doubled当原始容量为偶数时 但当原容量为奇数时 容量为增加一 然后加倍 例子 s make int 28 28 s append s
  • 是否可以获取有关 Golang 中调用者函数的信息?

    是否可以获取有关 Golang 中调用者函数的信息 例如 如果我有 func foo Do something func main foo 我怎样才能得到那个foo已被呼叫来自main 我可以用其他语言实现这一点 例如在 C 中我只需要使用
  • for 循环初始值设定项中的结构

    知道为什么 for 循环初始值设定项中的这个结构表达式在编译时会出现语法错误吗 在这种情况下 指向结构的指针工作正常 但 ofc 我需要如下所示的局部变量 感谢您的建议 type Request struct id int line byt
  • 如何在 Go 中解组具有多个项目的简单 xml?

    我想从以下 xml 中获取人物 People 的一部分
  • 匿名结构和空结构

    http play golang org p vhaKi5uVmm http play golang org p vhaKi5uVmm package main import fmt var battle make chan string
  • Golang GAE - 小胡子结构中的 intID

    这是一个Example https www dropbox com sh ur2ws1jnik6euef PjVJSwDTUc Blog Golang zip该应用程序的 关键代码在 golang code handler handler
  • 如何将 SQLite 数据库捆绑到 Go 二进制文件中?

    我尝试使用 go bindata 和 packr 但这些包没有显示如何将 SQLite 数据库文件打包到二进制文件中 我不需要以任何方式更新数据库 我只想在启动时从中读取数据 如何将 SQLite 数据库文件嵌入到 Go 二进制文件中 SQ
  • 将 time.Time 转换为字符串

    我正在尝试将数据库中的一些值添加到 string在围棋中 其中一些是时间戳 我收到错误 无法在数组元素中使用 U Created date 类型 time Time 作为类型字符串 我可以转换吗time Time to string typ
  • os.Mkdir 和 os.MkdirAll 权限

    我正在尝试在程序开始时创建一个日志文件 我需要检查是否 log如果不创建目录 则目录存在 然后继续创建日志文件 好吧 我尝试使用os Mkdir 也os MkdirAll 但无论我在第二个参数中输入什么值 我都会得到一个没有权限的锁定文件夹
  • 缺少节点-v59-linux-x64/grpc_node.node

    我正在尝试在我的服务器中使用 Firebase admin SDK 当我部署时 出现错误 我在 firebase admin node module 映射中缺少文件 node v59 linux x64 grpc node node 我在包
  • 如何从 JWT 令牌中提取声明

    我正在使用 dgrijalva jwt go 包 我想从令牌中提取有效负载 但找不到方法 示例 取自 https jwt io https jwt io 对于编码 eyJhbGciOiJIUZI1NiIsInR5cCI6IkpXVCJ9 e
  • RSA OAEP、Golang 加密、Java 解密 -BadPaddingException:解密错误

    我正在尝试解密使用 RSA OAEP 在 Golang 中加密的字符串 但出现 BadPaddingException 解密错误 很难弄清楚我错过了什么 这是Golang加密方法 func encryptString rootPEM io
  • 如何将接口转换为接口切片?

    我的输入是interface 而且我知道它可以是任何类型的数组 我想读取我输入的元素之一 所以我尝试将我的interface 进入一个 interface 但是 go 会给我以下错误 恐慌 接口转换 interface 是 map stri
  • 如何读取大型平面文件

    我有一个平面文件 其中包含 339276 行文本 大小为 62 1 MB 我试图读入所有行 根据我所拥有的某些条件解析它们 然后将它们插入数据库 我最初尝试使用 bufio Scan 循环和 bufio Text 来获取该行 但缓冲区空间不
  • 与通道相比,sync.WaitGroup 的优势是什么?

    我正在开发一个并发 Go 库 我偶然发现了 goroutine 之间两种不同的同步模式 其结果相似 等待组 https play golang org p ZYPLlcp16TZ package main import fmt sync t

随机推荐

  • NSTImer 事件会阻塞主线程吗?

    当我们使用 NSTimer 时 一旦在上述时间间隔后调用回调 UI 是否会被阻塞 那要看 大多数时候 这不会成为问题 If 但是 满足以下两个条件 NSTimer will阻塞UI线程 定时器被安排在NSRunLoop主线程的 每当您通过调
  • php:逆转 mysql_real_escape_string 对二进制文件的影响

    我构建了一个网页 用户可以在其中提交 PDF 然后将其插入到 Mediumblob 中的 MySQL 数据库中 以便稍后检索 这一切都工作正常 除非 PDF 包含图像或嵌入字体 在这种情况下图像会损坏并且使用该字体的任何文本都会消失 Acr
  • 检查mysql连接是否有效

    我有一个长时间运行的 php 脚本 它基本上是一个无限循环监听事件 它是一个 xmpp 机器人 我用以下命令启动脚本nohup php bot php 脚本的原始结构就像 mysqli mysqli connect while 1 if e
  • 如何在 C# 中解除套接字绑定?

    我在制作的测试应用程序中重用服务器套接字时遇到一些问题 基本上 我有一个既实现客户端又实现服务器端的程序 我出于测试目的运行该程序的两个实例 一个实例开始托管 另一个实例连接 这是监听代码 private void Listen Click
  • 如何处理 AngularJS 路由找不到资源

    在传统的数据驱动 Web 应用程序中 我们经常尝试根据 URL 中传递的 ID 加载资源 如果资源不存在 我们将返回 404 页面 我们应该如何在 AngularJS 中实现同样的目标 我已经按照 AngularJS 电话目录教程进行操作
  • 设置WKInterfacePicker颜色(文本或轮廓)

    有谁知道如何设置文本颜色或焦点样式轮廓颜色WKInterfacePicker 我没有看到它的界面生成器 我无法在代码中找到任何可以设置它的属性项 这是IB 您无法更改默认选择器的颜色 But you can manipulate the v
  • C 随机数生成(纯 C 代码,无库或函数)

    我需要用 C 语言生成一些随机数来测试和调试系统 该系统是一个定制硬件 SoC 功能有限 因此我只能使用基本的数学运算 不 我不能在 stdlib 或 math h 中使用随机数生成器 我需要自己写 那么有某种算法可以生成随机数吗 我知道一
  • 通过使用 htaccess 替换空格

    你好 我的 htaccess 中有这段代码
  • 通过正则表达式查找句子中的数字

    我需要一个正则表达式来查找句子中的所有数字 例如 我有3根香蕉和37个气球 我会得到 3 37 时间是20 00 我有7辆坦克 我会得到 20 00 7 将字符串拆分为 0 9 JAVA String numbers yourString
  • 如何同时编辑 ASP.NET ListView 控件中的所有行?

    我想知道如何立即将所有 ListView 行置于编辑模式 我并不是在寻找一次编辑每一行的传统行为 答案可以是 C 或 VB NET 另外 如果可能的话 请提供在编辑所有行后保存每行更改的任何示例代码 可能最简单的方法是仅使用 ListVie
  • Smartgwt selectitem键值问题

    我有一个SelectItem我通过一个填充Map具有此组合的列表网格字段内 所以很好 但是当我选择组合框中的任何项目而不是获取地图的描述或值时 会将键放入列表网格字段中 我怎样才能让我设置值而不是键 现在我尝试使用 AddChangeHan
  • 当 python 访问具有 None 值的二维列表时发出警告

    我想创建一个n npython 中的列表 其中大部分元素都用 None 初始化 然后我将在 for 循环中设置一些元素 但在该行中我将对角线元素设置为0 我得到了一个警告突出显示 j 在 PyCharm 中 说 意外类型 整数 整数 可能的
  • 无法在后台的 while 循环中发布异步任务的进度 - Android

    我想从 doInBackground 更新对话框的下载进度 我正在打印日志并发布进度 他们都没有工作 它最后更新对话框并最后一次打印所有日志值 private class DownloadEReport extends AsyncTask
  • 关键字“current_timestamp”附近的语法不正确 - 但仅限于一个数据库

    我有一个 SQL Server 2008 R2 实例 上面有多个数据库 我正在尝试在其中一个数据库 我们称之为 DB1 上运行表值函数 该函数将日期作为输入并返回相关信息表 我这样运行我的查询 SELECT FROM dbo getAllS
  • R 中的显式公式与符号导数

    我想评估某些函数的高阶导数f in R 我有两种可能性 Either I determine a general expression for f k the k th derivative of f which I can do in m
  • 64 位 Windows 上的注册表重定向

    我运行的是 64 位 Windows 并且我想创建注册表项HKCU Software Classes Wow6432Node CLSID myguid InprocServer32使用 C 我应该告诉它写入哪个注册表项 以便将其重定向到上面
  • 如何在 xslt 1.0 中求平方根

    我想在 xslt 文件中进行一些计算 并且需要在公式中进行一些平方根 有人可以指出是否可能以及如何实现吗 感谢磨坊 一个可以使用sqrt的模板 函数FXSL 一 在 XSLT 1 0 中
  • 使用内连接获取oracle中特定列值计数

    我通过加入两个表获得了一些列和值 Select tbl orderdetails category name tbl orderdetails branch name tbl ordermaster created date tbl ord
  • 有什么好的教程或书籍可以帮助您学习使用 PHP 进行信用卡处理? [关闭]

    Closed 此问题正在寻求书籍 工具 软件库等的推荐 不满足堆栈溢出指南 目前不接受答案 我正在寻找一本很好的教程或书籍来解释如何通过您网站上的表单处理客户的信用卡 我读过一些有关使用curl 的内容 但这不是完整的教程 我正在寻找一个课
  • 如何使用gracefulStop关闭所有grpc服务器流?

    我试图停止从服务器端连接到流服务器的所有客户端 其实我正在使用GracefulStop优雅地处理它的方法 我正在等os Interrupt在通道上发出信号以执行 gRPC 的正常停止 但它被卡住了server GracefulStop 当客