NServiceBus事件在超时队列中结束



我正在使用HandleMyEvent类处理事件

public class HandleMyEvent :  IHandleMessages<MyEvent>
{
    private readonly IBus _bus;
    private readonly IWorkorker _workerTools;

    public HandleProductInstanceEvent( IBus bus, IWorkorker worker)
    {
        _bus = bus;
        _workerTools = worker;
    }
    public void Handle(IProductInstancesUpdatedEvent message)
    {
        var worker = new myWorker(_bus, _worker);
        myWorker.DoWork(message.data);
    }
}

myWorker.DoWork在完成之前最多可以运行5分钟。

当发布者发送单个"MyEvent"时,处理程序似乎在消息在超时队列中结束之前收到了5个事件,我猜它会重试5次,然后放弃。

在日志文件中,我可以找到这个条目

NServiceBus.Unicast.Queuing.FailedToSendMessageException: Failed to send message to address: My.Bus.Service@MyServer ---> System.Messaging.MessageQueueException: Cannot enlist the transaction.
   at System.Messaging.MessageQueue.SendInternal(Object obj, MessageQueueTransaction internalTransaction, MessageQueueTransactionType transactionType)
   at NServiceBus.Transports.Msmq.MsmqMessageSender.Send(TransportMessage message, Address address) in c:work3206e2123f54fce4srcNServiceBus.CoreTransportsMsmqMsmqMessageSender.cs:line 59

为什么我会出现此错误?

您收到该错误是因为在NServiceBus中处理MSMQ消息,默认情况下,在超时为1分钟的事务中运行。

一旦您通过了事务超时,任何新的操作,如发送消息或在数据库中存储内容,都将在中失败

无法登记事务。

您应该将事务超时增加到超过预期处理时间的时间,或者关闭此端点上的事务。

请注意,运行5分钟的消息处理程序是很长的时间。在如此长的一段时间内,针对事务资源进行事务并锁定并不是最优的。

一旦消息处理失败,事务就会回滚,将消息放回队列。然后,无论您配置了多少次一级重试尝试,都会重试它。在你的场景中最有可能是5。之后,它将移动到二级重试。

.timeout队列是负责处理二级重试的超时管理器的输入队列。如果没有立即从该队列中提取消息,则说明您没有在该端点上运行超时管理器。

最新更新