Hal*_*ard 3 messaging nservicebus message-queue rabbitmq
我最近一直在阅读有关消息传递系统的内容,并专门研究了RabbitMQ和NServiceBus.正如我所理解的那样,如果某条消息由于某种原因而失败,则会再次尝试一次.然后,两个系统都提供了稍后再试的可能性,例如在5秒内.当五秒钟过去后,消息将再次发送多次.
我引用Vaughn Vernon 实现域驱动设计(p.502):
处理此问题的另一种方法是简单地重试发送直到成功,可能使用上限指数退避.在RabbitMQ的情况下,重试可能会失败很长一段时间.因此,使用消息NAK和重试的组合可能是最好的方法.尽管如此,如果我们的流程每五分钟重试三次,那么它可能就是我们所需要的.
对于NServiceBus,这称为二级重试,当重试发生时,它会多次发生.
为什么需要多次发生?为什么不每五分钟重试一次?五分钟后第一次重试失败的可能性是多少,第二次重试(可能是几毫秒后)应该成功的几率是多少?
如果它不需要由于某些配置(是吗?),为什么我发现的所有示例都有多次重试?
我的背景是NServiceBus所以我的回答可能就是这些术语.
对于非常短暂的错误,第一级重试非常有用.死锁就是一个很好的例子.您尝试更改数据库,并选择您的事务作为死锁牺牲品.在这些情况下,第一级重试是完美的.大多数情况下,只需要进行一级重试即可.如果数据库中存在大量争用,则可能会进行2或3次重试.
二级重试适用于不太短暂的错误.考虑诸如Web服务停机10秒或故障转移群集切换中的SQL Server数据库之类的事情,这可能需要30-60秒.如果你在几毫秒之后重试,它对你没有任何好处,但10,20,30秒之后你可能会有一个好的镜头.
然而,问题的关键是在第一次重试5次然后延迟之后,为什么在额外延迟之前再次尝试5次?
首先,在您的第一次二级重试时,您仍然可能遇到死锁或其他非常短暂的错误.毕竟,目标通常不是使系统尽可能慢,因此如果问题确实是暂时的,那么在重试之前不必等待额外的延迟.当然,基础设施无法知道问题的暂时性.
第二个原因是,如果它们完全相同,则更容易配置.每个级别的X级重试次数和Y次尝试次数= X*Y总次数,配置文件中只有2个数字.在NServiceBus中,这是2个值加上退避时间跨度,所以配置如下所示:
<SecondLevelRetriesConfigEnabled="true" TimeIncrease ="00:00:10" NumberOfRetries="3" />
<TransportConfig MaxRetries="3" />
Run Code Online (Sandbox Code Playgroud)
这很简单.试试3次.等10秒钟.试试3次.等20秒.试试3次.等30秒.试试3次.然后你就完成了,然后转到错误队列.
为每个级别配置不同的值需要更复杂的配置故事.