我有两个可用的 gRPC 端点和一个 ServerInterceptor,它应该在抛出异常时拦截异常。
gRPC 服务定义如下:
@GrpcService
public class AccountsResource implements AccountsApiService {
@Inject
AccountsService accountsService;
@Override
public Uni<GetTppPlatformGroupIdResponse> getTppPlatformGroupId(Empty request) {
Context.Key<String> tppIamClientIdKey = Constant.TPP_IAM_CLIENT_ID_CONTEXT_KEY;
String tppIamClientId = tppIamClientIdKey.get(Context.current());
return Uni.createFrom().item(() -> accountsService.getTppPlatformGroupIdResponse(tppIamClientId))
.runSubscriptionOn(Infrastructure.getDefaultExecutor());
}
}
gRPC 服务使用 SmallRye Mutiny Reactive 来处理请求。
其他帖子解释说,onHalfClose
应该重写该方法并插入一个 try/catch 块以捕获自定义异常,然后将其映射到可以使用的 StatusRuntimeException gRPC。我尝试了以下方法:
@ApplicationScoped
@GlobalInterceptor
public class ExceptionInterceptor implements ServerInterceptor {
private static final Logger LOG = LogManager.getLogger(ExceptionInterceptor.class);
@Override
public <ReqT, RespT> ServerCall.Listener<ReqT> interceptCall(ServerCall<ReqT, RespT> serverCall, Metadata metadata, ServerCallHandler<ReqT, RespT> serverCallHandler) {
ServerCall.Listener<ReqT> listener = serverCallHandler.startCall(serverCall, metadata);
return new ExceptionHandlingServerCallListener<>(listener, serverCall, metadata);
}
private class ExceptionHandlingServerCallListener<ReqT, RespT> extends ForwardingServerCallListener.SimpleForwardingServerCallListener<ReqT> {
private ServerCall<ReqT, RespT> serverCall;
private Metadata metadata;
ExceptionHandlingServerCallListener(ServerCall.Listener<ReqT> listener, ServerCall<ReqT, RespT> serverCall, Metadata metadata) {
super(listener);
this.serverCall = serverCall;
this.metadata = metadata;
}
@Override
public void onHalfClose() {
try {
super.onHalfClose();
} catch (Throwable ex) {
handleException(ex, serverCall, metadata);
}
}
@Override
public void onReady() {
try {
super.onReady();
} catch (Throwable ex) {
handleException(ex, serverCall, metadata);
}
}
}
该handleException
方法将 Throwable 映射到 StatusRuntimeException 并抛出 StatusRuntimeException。
到目前为止一切顺利,当运行应用程序并模拟自定义异常时,ExceptionInterceptor 确实进入了该onHalfClose
方法。但是,即使抛出了异常,它也不会进入 catch 块。而是将此错误消息记录到控制台:
2022-01-24 12:07:36,232 WARN [io.qua.grp.run.ServerCalls] (executor-thread-0) gRPC service threw an exception other than StatusRuntimeException
如何解决这个问题?