grpc 未处理异常 StatusCode=调用从 proto 文件生成的方法时未知

jul*_*zzz 5 c# protocol-buffers grpc

我有一个C#的客户端和服务器,并得到类型的未处理的异常Grpc.Core.RpcExceptionStatus(StatusCode=Unknown, Detail="Exception was thrown by handler.")调用时,SendMessage在客户端功能(从生成的文件)。

堆栈跟踪是:

Got response: True
RPC failed Grpc.Core.RpcException: Status(StatusCode=Unknown, Detail="Exception was thrown by handler.")
   at Grpc.Core.Internal.AsyncCall`2.UnaryCall(TRequest msg) in T:\src\github\grpc\src\csharp\Grpc.Core\Internal\AsyncCall.cs:line 75
   at Grpc.Core.DefaultCallInvoker.BlockingUnaryCall[TRequest,TResponse](Method`2 method, String host, CallOptions options, TRequest request) in T:\src\github\grpc\src\csharp\Grpc.Core\DefaultCallInvoker.cs:line 46
   at Grpc.Core.Interceptors.InterceptingCallInvoker.<BlockingUnaryCall>b__3_0[TRequest,TResponse](TRequest req, ClientInterceptorContext`2 ctx) in T:\src\github\grpc\src\csharp\Grpc.Core\Interceptors\InterceptingCallInvoker.cs:line 51
   at Grpc.Core.ClientBase.ClientBaseConfiguration.ClientBaseConfigurationInterceptor.BlockingUnaryCall[TRequest,TResponse](TRequest request, ClientInterceptorContext`2 context, BlockingUnaryCallContinuation`2 continuation) in T:\src\github\grpc\src\csharp\Grpc.Core\ClientBase.cs:line 174
   at Grpc.Core.Interceptors.InterceptingCallInvoker.BlockingUnaryCall[TRequest,TResponse](Method`2 method, String host, CallOptions options, TRequest request) in T:\src\github\grpc\src\csharp\Grpc.Core\Interceptors\InterceptingCallInvoker.cs:line 48
   at MessageService.MessageServiceClient.SendMessage(Message request, CallOptions options) in C:\Work\Dev\sphirra\hub-communication\message-hub\Hub-Messenger\MessageGrpc.cs:line 95
   at MessageService.MessageServiceClient.SendMessage(Message request, Metadata headers, Nullable`1 deadline, CancellationToken cancellationToken) in C:\Work\Dev\sphirra\hub-communication\message-hub\Hub-Messenger\MessageGrpc.cs:line 91
Run Code Online (Sandbox Code Playgroud)

所述sendMessage的方法中的原文件如下:

service MessageService{

rpc SendMessage(Message) returns (Empty){}
}

message Message{
    bytes msg = 1;
    int32 senderId = 2;
    int32 receiverId = 3;
}

message Empty {}
Run Code Online (Sandbox Code Playgroud)

SendMessage在客户端的实现:

public void SendMessage(String msg, int receiverId)
            {
                try
                {
                    client.SendMessage(NewMsg(msg, ID, receiverId)); //this is where it gets stuck
                    Log("sending: ", msg);
                }
                catch (RpcException e)
                {
                    Log("RPC failed " + e);
                    throw;
                }
            }
Run Code Online (Sandbox Code Playgroud)

该方法的服务器端实现:

public override Task<Empty> SendMessage(Message request, ServerCallContext context)
        {
            try
            {
                Task<Empty> empty = null;
                messages.Add(request);
                return empty;
            }
            catch (RpcException e){
                Console.WriteLine("Remote procedure call failed: " + e);
                throw;
            }

        }
Run Code Online (Sandbox Code Playgroud)

小智 1

就我而言,问题不是在返回对象时将对象包装在 Task.FromResult() 中。

旧代码:

return new Object{};
Run Code Online (Sandbox Code Playgroud)

更正代码

return Task.fromResult(new Object{});
Run Code Online (Sandbox Code Playgroud)

另外,始终避免 return 语句中的对象为 null 对象或 null 属性。