Azure 服务总线 - 避免并行处理来自同一设备的消息

Azure Service Bus - avoid processing messages from same device in parallel

许多设备正在发送消息,这些消息最终出现在单个 Azure 服务总线队列(或主题)中。我们希望并行处理多条消息,但我们希望避免在任何给定时间同时处理同一设备的两条消息。

以下图片说明了目标。有 3 个处理线程(实际上可能有几十个,分布在多个服务器之间)。每个方框表示一条消息的处理时间,颜色表示它属于哪个设备。

您可以看到在任何时间点都不会出现来自同一设备的两条或更多重叠消息。

由于涉及到多台处理服务器,我可以想象,防止并发处理的唯一方法就是以设备ID为分区键对消息进行分区,然后每个分区只有一个消费者:

因此,来自 "yellow device" 的所有消息都进入分区 1,依此类推。

我还是想在单进程中运行多处理线程。现在,我们做一些简单的事情,比如

var client = QueueClient.CreateFromConnectionString(connectionString, queueName);
var options = new OnMessageOptions { MaxConcurrentCalls = x };
client.OnMessage(m =>
    {
        // Process...
        m.Complete();
    });

如何将并发限制合并到此类代码中?

我可以想象一些基于参与者或其他并发机制的客户端解决方案。但是有没有办法在 Broker 级别解决这个问题?

这看起来是利用 ASBs Sessions feature. You will be able to useOnMessage` API 的一个很好的候选者,但是给定会话的处理将仅由单个消费者完成,而不是由多个消费者完成。此外,您还可以同时 运行 处理负载。

一个好的起点是查看 QueueClient.AcceptMessageSessionAsync API. If you want a solid documentation with explanation how it works, this sample is the best doco.