GRPC: 如何在 gRPC 服务中自动添加 RequestId?-阿里云开发者社区

开发者社区> 尹东勋> 正文

GRPC: 如何在 gRPC 服务中自动添加 RequestId?

简介: 本文将介绍如何在 gRPC 微服务中,为每一个 API 自动添加 RequestId 。
+关注继续查看

介绍

本文将介绍如何在 gRPC 微服务中,为每一个 API 自动添加 RequestId 。

我们将会使用 rk-boot 来启动 gRPC 服务。

请访问如下地址获取完整教程:

安装

go get github.com/rookie-ninja/rk-boot

快速开始

详细文档可参考:

开启了 meta 拦截器之后,每一个请求都会自动包含如下值。

Header 键详情
X-Request-Id拦截器会自动生成请求 ID。
X-[Prefix]-App服务名称。
X-[Prefix]-App-Version服务版本。
X-[Prefix]-App-Unix-Time当前服务的 Unix 时间。
X-[Prefix]-Request-Received-Time接收到请求的时间戳。

1.创建 boot.yaml

为了验证,我们启动了 commonService,commonService 里包含了一系列常用 API,例如 /rk/v1/healthy。

---
grpc:
  - name: greeter                   # Name of grpc entry
    port: 8080                      # Port of grpc entry
    enabled: true                   # Enable grpc entry
    commonService:
      enabled: true                 # Enable common service for testing
    interceptors:
      meta:
        enabled: true

2.创建 main.go

package main

import (
    "context"
    "github.com/rookie-ninja/rk-boot"
)

// Application entrance.
func main() {
    // Create a new boot instance.
    boot := rkboot.NewBoot()

    // Bootstrap
    boot.Bootstrap(context.Background())

    // Wait for shutdown sig
    boot.WaitForShutdownSig(context.Background())
}

3.启动 main.go

$ go run main.go

4.验证

在上面的 boot.yaml 中,我们没有启动 enableRkGwOption,因此,返回的头部当中,会有 Grpc-Metadata 前缀。

$ curl -vs -X GET localhost:8080/rk/v1/healthy
  ...
  < Grpc-Metadata-Content-Type: application/grpc
  < Grpc-Metadata-X-Request-Id: cb8c0c77-39cd-4e15-89d2-66ba30fa7a46
  < Grpc-Metadata-X-Rk-App-Name: rk-demo
  < Grpc-Metadata-X-Rk-App-Unix-Time: 2021-07-10T00:19:58.170222+08:00
  < Grpc-Metadata-X-Rk-App-Version: master-f414049
  < Grpc-Metadata-X-Rk-Received-Time: 2021-07-10T00:19:58.170222+08:00
  ...
  {"healthy":true}
如果我们启动 enableRkGwOption, Grpc-Metadata 将会消失!
---
grpc:
  ...
  enableRkGwOption: true
$ curl -vs -X GET localhost:8080/rk/v1/healthy
  ...
  < X-Request-Id: 2ae18df6-d132-42ce-841c-571f19a88787
  < X-Rk-App-Name: rk-demo
  < X-Rk-App-Unix-Time: 2021-07-10T00:24:10.281868+08:00
  < X-Rk-App-Version: master-f414049
  < X-Rk-Received-Time: 2021-07-10T00:24:10.281868+08:00
  ...
  {"healthy":true}

覆盖 requestId

如果我们希望自定义 requestId,需要添加一个 Header。

func (server *GreeterServer) Greeter(ctx context.Context, request *greeter.GreeterRequest) (*greeter.GreeterResponse, error) {
    // Override request id
    rkgrpcctx.AddHeaderToClient(ctx, rkginctx.RequestIdKey, "request-id-override")
    // We expect new request id attached to logger
    rkgrpcctx.GetLogger(ctx).Info("Received request")

    return &greeter.GreeterResponse{
        Message: fmt.Sprintf("Hello %s!", request.Name),
    }, nil
}
返回的头部中,有两个 X-Request-Id,这是因为,对于同一个 Key 进行设置,GRPC 会融合这些 Value,而非替换。

然而,客户端中,会提取最后一个值。

$ curl -vs -X GET "localhost:8080/v1/greeter?name=rk-dev"
...
< X-Request-Id: 4e858644-f2e2-48b2-adec-a1d329497abf
< X-Request-Id: request-id-override
< X-Rk-App-Name: rk-demo
< X-Rk-App-Unix-Time: 2021-07-10T00:29:19.030555+08:00
< X-Rk-App-Version: master-f414049
< X-Rk-Received-Time: 2021-07-10T00:29:19.030555+08:00
...
{"Message":"Hello rk-dev!"}
如果我们启动了日志拦截器,那我们会看到如下的日志。
2021-07-10T00:29:19.030+0800    INFO    basic/main.go:40        Received request        {"requestId": "request-id-override"}
------------------------------------------------------------------------
endTime=2021-07-10T00:29:19.030673+08:00
startTime=2021-07-10T00:29:19.030535+08:00
elapsedNano=138133
timezone=CST
ids={"eventId":"request-id-override","requestId":"request-id-override"}
app={"appName":"rk-demo","appVersion":"master-f414049","entryName":"greeter","entryType":"GrpcEntry"}
env={"arch":"amd64","az":"*","domain":"*","hostname":"lark.local","localIP":"10.8.0.2","os":"darwin","realm":"*","region":"*"}
payloads={"grpcMethod":"Greeter","grpcService":"api.v1.Greeter","grpcType":"unaryServer","gwMethod":"GET","gwPath":"/v1/greeter","gwScheme":"http","gwUserAgent":"curl/7.64.1"}
error={}
counters={}
pairs={}
timing={}
remoteAddr=localhost:58601
operation=/api.v1.Greeter/Greeter
resCode=OK
eventStatus=Ended
EOE

覆盖 header 前缀

---
grpc:
  - name: greeter
    ...
    interceptors:
      meta:
        enabled: true        # Enable meta interceptor/middleware
        prefix: "Override"   # Override prefix which formed as X-[Prefix]-xxx
$ curl -vs -X GET localhost:8080/rk/v1/healthy
...
< X-Override-App-Name: rk-demo
< X-Override-App-Unix-Time: 2021-07-10T00:34:59.974205+08:00
< X-Override-App-Version: master-f414049
< X-Override-Received-Time: 2021-07-10T00:34:59.974205+08:00
< X-Request-Id: 4deded12-2d39-42a5-b740-b4f74dd73c90
...
{"healthy":true}

版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。

相关文章
PostgreSQL 双节点流复制如何同时保证可用性、可靠性(rpo,rto) - (半同步,自动降级方法实践)
PostgreSQL 双节点流复制如何同时保证可用性、可靠性(rpo,rto) - (半同步,自动降级方法实践)
447 0
Jenkins 多服务器自动部署,发布到多台服务器
目的:多台服务器代码自动上传部署 能用FTP的绝对不用命令,能用拖动文件的,绝对不手写字母,能用工具实现代码上传打包编译的,绝对不用手动打包编译,能自动化的,绝对不用原始工具。 风来了.呆狐狸 环境 CENTOS 6.6 lanmps环境套装(www.lanmps.com) php5.2.x mysql10.0.x nginx1.7.x jenkins 2 台linux 1.
5277 0
PostgreSQL 如何让心跳永远不死,支持半同步自动同步、异步升降级 - udf 心跳
PostgreSQL 如何让心跳永远不死,支持半同步自动同步、异步升降级 - udf 心跳
391 0
阿里云服务器端口号设置
阿里云服务器初级使用者可能面临的问题之一. 使用tomcat或者其他服务器软件设置端口号后,比如 一些不是默认的, mysql的 3306, mssql的1433,有时候打不开网页, 原因是没有在ecs安全组去设置这个端口号. 解决: 点击ecs下网络和安全下的安全组 在弹出的安全组中,如果没有就新建安全组,然后点击配置规则 最后如上图点击添加...或快速创建.   have fun!  将编程看作是一门艺术,而不单单是个技术。
3954 0
通过阿里云容器服务K8S Ingress Controller实现gRPC服务访问
gRPC是Google开源的一个高性能RPC通信框架,其通过Protocol Buffers作为其IDL,可以在不同语言开发的平台上使用,同时基于HTTP/2协议实现,继而提供了连接多路复用、头部压缩、流控等特性,极大地提高了客户端与服务端的通信效率。
6972 0
PostgreSQL 如何让心跳永远不死,支持半同步自动同步、异步升降级 - udf 心跳
标签 PostgreSQL , 同步 , 半同步 , 流复制 , 心跳 , 自动降级 , 自动升级 , dblink , 异步调用 背景 在心跳时,通过自定义UDF,实现心跳永远不被堵塞,并且支持更加当前的配置自动的进行同步、异步模式的升降级。实现半同步的功能。 UDF输入 1、优先模式(同步、异步) 2、同步等待超时时间 当优先为同步模式时,假设当前为同步配置,如果备库异常导致
772 0
+关注
尹东勋
点目科技创始人
57
文章
0
问答
文章排行榜
最热
最新
相关电子书
更多
文娱运维技术
立即下载
《SaaS模式云原生数据仓库应用场景实践》
立即下载
《看见新力量:二》电子书
立即下载