You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

gRPC服务兼容问题:Evans无法识别RPC服务及方法

问题:gRPC服务无法被Evans识别,需补充代码实现向前兼容

相关文件内容

service_myservice.proto

service MyService {
    rpc GetData(GetRequest) returns (GetResponse) {}
}

server.go

type Server struct {
    pb.UnimplementedMyServiceServer
    config util.Config
}

// NewServer creates a new gRPC server.
func NewServer(config util.Config) (*Server, error) {
    server := &Server{
        config: config,
    }

    return server, nil
}

main包中的启动函数

func runGrpcServer(config util.Config) {
    server, err := gapi.NewServer(config)
    if err != nil {
        log.Fatal().Err(err).Msg("cannot create server")
    }

    grpcLogger := grpc.UnaryInterceptor(gapi.GrpcLogger)
    grpcServer := grpc.NewServer(grpcLogger)
    pb.RegisterMyServiceServer(grpcServer, server)
    reflection.Register(grpcServer)

    listener, err := net.Listen("tcp", config.GRPCServerAddress)
    if err != nil {
        log.Fatal().Err(err).Msg("cannot create listener")
    }

    log.Info().Msgf("start gRPC server at %s", listener.Addr().String())
    err = grpcServer.Serve(listener)
    if err != nil {
        log.Fatal().Err(err).Msg("cannot start gRPC server")
    }
}

测试报错信息

localhost:9090> show service
+---------+-----+--------------+---------------+
| SERVICE | RPC | REQUEST TYPE | RESPONSE TYPE |
+---------+-----+--------------+---------------+
+---------+-----+--------------+---------------+
localhost:9090> call GetData
command call: failed to get the RPC descriptor for: GetData: service unselected

解决方法

嵌入pb.UnimplementedMyServiceServer确实是实现gRPC向前兼容的标准方式,但你需要确保以下几点来让服务被Evans识别:

1. 确保proto代码生成正确

必须使用gRPC Go插件重新生成代码,执行以下命令(替换路径为你的实际路径):

protoc --go_out=. --go-grpc_out=. service_myservice.proto

这会生成包含服务描述符、UnimplementedMyServiceServer和注册函数的service_myservice_grpc.pb.go文件,这是服务被反射识别的基础。

2. 补充RPC方法的显式实现(可选但有效)

虽然UnimplementedMyServiceServer已经提供了所有RPC方法的默认实现(返回Unimplemented错误),但显式实现GetData方法可以确保反射服务正确识别到该RPC:
在server.go中添加:

import (
    "context"
    "google.golang.org/grpc/codes"
    "google.golang.org/grpc/status"
)

func (s *Server) GetData(ctx context.Context, req *pb.GetRequest) (*pb.GetResponse, error) {
    return nil, status.Errorf(codes.Unimplemented, "method GetData not implemented")
}

3. 确认反射服务正常工作

你的启动代码中已经调用了reflection.Register(grpcServer),这部分是正确的,但需要确保生成的proto代码中包含完整的服务描述符,这样反射才能正确暴露服务信息给Evans。

完成以上步骤后,重启gRPC服务器,再用Evans测试即可识别到MyService服务。

内容的提问来源于stack exchange,提问作者golobitch

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.08 05:13:20