如何检测GRPC ServerInterceptor中onError方法是否被调用?
问题描述
我想把服务调用包装在隐式事务里,不用显式使用TransactionTemplate包裹现有调用。我在ServerInterceptor类中添加了大量日志语句,但无法检测到服务中的onError方法是否被调用。
拦截器代码实现
@Component @RequiredArgsConstructor @Slf4j public class TransactionProviderGrpcInterceptor implements ServerInterceptor { private final JpaTransactionManager transactionManager; @Override public <R, Q> ServerCall.Listener<R> interceptCall( final ServerCall<R, Q> call, final Metadata headers, final ServerCallHandler<R, Q> next) { return new ForwardingServerCallListener.SimpleForwardingServerCallListener<>( next.startCall(call, headers)) { private TransactionStatus tx; /** 调用取消时标记事务仅回滚 */ @Override public void onCancel() { log.error( "onCancel setRollbackOnly tx={}", TransactionSynchronizationManager.isActualTransactionActive()); tx.setRollbackOnly(); log.error( "onCancel before super tx={}", TransactionSynchronizationManager.isActualTransactionActive()); super.onHalfClose(); log.error( "onCancel after super tx = {}", TransactionSynchronizationManager.isActualTransactionActive()); } @Override public void onMessage(final R message) { log.error( "onMessage before super tx = {}", TransactionSynchronizationManager.isActualTransactionActive()); super.onMessage(message); log.error( "onMessage after super tx = {}", TransactionSynchronizationManager.isActualTransactionActive()); } @Override public void onComplete() { log.error( "onComplete before super tx = {}, tx={}", TransactionSynchronizationManager.isActualTransactionActive(), tx); super.onComplete(); log.error( "onComplete after super tx = {}", TransactionSynchronizationManager.isActualTransactionActive()); } /** * 已获取客户端所有消息,即将关闭连接,此时提交事务。 * 必须在此处执行,因为到{@link #onComplete()}时事务已不可用。 */ @Override public void onHalfClose() { log.error( "onHalfClose before super tx = {}", TransactionSynchronizationManager.isActualTransactionActive()); super.onHalfClose(); log.error( "onHalfClose after super tx = {} headers={}", TransactionSynchronizationManager.isActualTransactionActive(), headers); if (TransactionSynchronizationManager.isActualTransactionActive()) { transactionManager.commit(tx); log.error( "onHalfClose after commit tx = {}", TransactionSynchronizationManager.isActualTransactionActive()); } } @Override public void onReady() { log.error( "onReady before getTransaction tx = {}", TransactionSynchronizationManager.isActualTransactionActive()); tx = transactionManager.getTransaction( new DefaultTransactionDefinition(PROPAGATION_REQUIRED)); log.error( "onReady after getTransaction tx = {}", TransactionSynchronizationManager.isActualTransactionActive()); } }; } }
问题现象
当onError触发时,onHalfClose()并未抛出任何异常,而这里是事务仍处于活跃状态的唯一位置。日志输出如下:
onReady before getTransaction tx = false onReady after getTransaction tx = true onMessage before super tx = true onMessage after super tx = true onHalfClose after super tx = true headers=Metadata(content-type=application/grpc,user-agent=grpcurl/v1.8.7 grpc-go/1.48.0) onHalfClose after commit tx = false onComplete before super tx = false, tx=org.springframework.transaction.support.DefaultTransactionStatus@68f8b4ba onComplete after super tx = false rpc.server.RequestLoggingGrpcInterceptor [64e90719856c7e2e906849013c6b53e2,906849013c6b53e2,] INFO com.devhaus.rpc.Greeter/SayHello 7ms cancelled=false
内容的提问来源于stack exchange,提问作者Archimedes Trajano
相关产品推荐
相关产品推荐

