我正在尝试将 Transactionnal RabbitMQ 通道与 Spring-AMQP 一起使用,但我想真正吞下异常来记录它们并能够恢复它们。
使用 channelTransacted=true 会强制 Channel 也加入当前 transactionManager(在我的情况下为 Hibernate),这会导致提交异常被重新抛出 @Transactionnal 边界,导致上层失败而无法捕获并记录它。
我还尝试手动将发布附加到事务,以便仅在提交成功后执行:
public void publishFailSafeAfterSuccessfulTransaction(final String routingKey, final String message) {
TransactionSynchronizationManager.registerSynchronization(new TransactionSynchronizationAdapter() {
@Override
public void afterCommit() {
try {
rabbitTemplate.convertAndSend(routingKey, message);
} catch (Exception exception) {
logger.error("Error while publishing message to RabbitMQ ");
}
}
});
以这种方式使用:
Entity entity = save(entity);
publishFailSafeAfterSuccessfulTransaction("routingkey", "Entity was updated");
但在那种情况下,我不能使用 channelTransacted=true 因为它会将 registeringSynchronization 嵌套在另一个 registeringSynchronization 中并且根本无法调用......
有没有办法做到这一点?
更新:理想情况下,我想覆盖 ConnectionFactoryUtils 类中使用的 RabbitResourceSynchronization,但它是一个没有工厂实例化的私有类
TransactionSynchronizationManager.registerSynchronization(new RabbitResourceSynchronization(resourceHolder, connectionFactory, synched));