以下是该方案:
Publisher #1 ═══╗ ╔═══ Round Robin ═══╦═══ Subscriber #1 (Service 1)
║ ║ ╚═══ Subscriber #2 (Service 1)
╠═══ Topic ═══╣
║ ║ ╔═══ Subscriber #3 (Service 2)
Publisher #2 ═══╝ ╚═══ Round Robin ═══╩═══ Subscriber #4 (Service 2)
我有一条消息需要由多个订阅者处理,但每个服务只有一个(每个服务都会运行多个实例)。
消息#1需要由订户#1和#3处理。消息#2需要由订户#2和#4处理。消息#3,订户#1和#3再次。基本上,每条消息应循环到订阅每条消息的每个负载均衡服务,按连接的每个服务进行分组。如果不创建多个主题,这可能吗?
即使它不是循环说法,我也会尽最大努力在多个服务之间实现负载均衡。这可能吗?
答案 0 :(得分:6)
主题是一种发布/分发机制,它将按订阅(订阅者)发送一次消息。
主题订阅类似于接收发送到主题的消息副本的虚拟队列。从订阅接收消息的方式与从队列接收消息的方式相同......
订阅支持本节前面关于队列描述的相同模式:竞争消费者,时间解耦,负载均衡和负载平衡。
来源:MSDN Article
您需要在竞争消费者(服务实例)中重复使用主题订阅才能实现您的方案。
Publisher #1 ═══╗ ╔═══ Subscription 1 ═══╦═══ Service 1-instance 1
║ ║ ╚═══ Service 1-instance 2
╠═══ Topic ═══╣
║ ║ ╔═══ Service 2-instance 1
Publisher #2 ═══╝ ╚═══ Subscription 2 ═══╩═══ Service 2-instance 2
string connectionString = "<Secret>"
var namespaceManager =
NamespaceManager.CreateFromConnectionString(connectionString);
if (!namespaceManager.SubscriptionExists("TestTopic", "Inventory"))
{
namespaceManager.CreateSubscription("TestTopic", "Inventory");
}
MessagingFactory factory = MessagingFactory.Create(uri, tokenProvider);
MessageReceiver receiver = factory.CreateMessageReceiver("TestTopic/subscriptions/Inventory");
使用多个Queues
也可以适合您的特定情况。每个具有多个竞争使用者(实例)的Queue
只会将消息传递给第一个请求并成功处理它的客户端。
然后设计成为:
Publisher #1 ═══╗ ╔═══ Service 1 Queue ═══╦═══ Subscriber #1 (Service 1)
║ ║ ╚═══ Subscriber #2 (Service 1)
╠═══ASB═══╣
║ ║ ╔═══ Subscriber #3 (Service 2)
Publisher #2 ═══╝ ╚═══ Service 2 Queue ═══╩═══ Subscriber #4 (Service 2)
答案 1 :(得分:1)
我想尽最大努力在多个服务之间实现负载均衡。这可能吗?
根据您的描述,您似乎正在尝试在任何给定服务的多个实例之间进行负载平衡,而不是单个服务。您可以通过ASB支持的竞争消费者模式获得开箱即用的功能。不是你需要工作的东西。
我正在尝试解决的问题是,我只希望每个服务中有一个消费者在一个主题上消费消息。这可能与ASB有关吗?
是的,这是可能的。如果您有一个共享主题,每个服务订阅(不是实例)并且包含始终评估为true的规则SqlFilter
(1 = 1
)。然后每个订阅者将获得该消息的副本。从本质上讲,您将向所有服务广播消息。感谢竞争消费者,每个服务只有一个实例会收到该消息。
要定位特定服务,您需要创建一个附加规则,用于过滤掉属性(标准属性或自定义属性)上的消息。例如,它可以是服务名称。
如果您不想专注于微服务的中间件,可以查看为您执行此操作的框架。此类框架通常也倾向于提供其他功能。例如,查看NServiceBus或MassTransit。
完全免责声明 - 我正在开发NServiceBus及其ASB传输。