如何使变量可用于 gRPC 服务器上的所有 gRPC 请求处理程序?

时间:2021-06-10 09:24:31

标签: go grpc

我正在像这样启动我的 gRPC 服务器:

func Run(...) ... {
    // this is variable I want to add to all my request handler's context
    foo := "bar"

    grpcServer := grpc.NewServer()
    grpc_health_v1.RegisterHealthServer(grpcServer, health.NewServer())
    pb.RegisterMyServer(grpcServer, newServer())
    signal.Notify(sigChan, syscall.SIGTERM, syscall.SIGINT)

    go func() {
        if err := grpcServer.Serve(lis); err != nil {
            errChan <- err
        }
    }()

    return grpcServer, nil
}

这里是“ping”请求的处理程序示例:

func (s *myServer) Ping(
    ctx context.Context,
    pingRequest *pb.PingRequest,
) (*pb.PingResponse, error) {
    return &pb.PingResponse{}, nil
}

您可以在 Run() 中看到我有一个变量 foo,我希望以某种方式可供我的所有请求处理程序使用。此变量不以任何方式依赖于客户端的请求,它只需要在请求处理程序中可用。

实现这一目标的最佳方法是什么?

  • 使用单例
  • 使用全局变量
  • 以某种方式将其添加到 gRPC 请求上下文中?

1 个答案:

答案 0 :(得分:2)

将您的自定义实现用于 GRPC 服务器。

type GrpcServer struct {
    Foo string
}

func (g *GrpcServer) Ping(ctx context.Context, pingRequest *pb.PingRequest, ) (*pb.PingResponse, error) {
    fmt.Println(g.Foo)
    return &pb.PingResponse{}, nil
}

并注册您自定义的 grpc 服务器实现。

func Run() {
    
    foo := "bar"

    grpcServer := grpc.NewServer()
    grpc_health_v1.RegisterHealthServer(grpcServer, health.NewServer())
    pb.RegisterMyServer(grpcServer, &GrpcServer{Foo: foo})
    signal.Notify(sigChan, syscall.SIGTERM, syscall.SIGINT)

    go func() {
        if err := grpcServer.Serve(lis); err != nil {
            errChan <- err
        }
    }()

    return grpcServer, nil
}