与分销商的NServiceBus管道

时间:2010-04-12 20:45:39

标签: workflow scalability nservicebus pipeline nservicebus-distributor

我正在使用NServiceBus构建处理管道,但我遇到了分发器配置的问题,以使流程中的每个步骤都可以扩展。以下是一些信息:

  • 管道将有一个主进程,为WorkItem显示“OK,time to start”,然后将启动一个类似流程图的流程。
  • 流程图中的每个步骤都可能是计算上昂贵的,因此我希望能够扩展每个步骤。这告诉我每个步骤都需要一个分销商。
  • 我希望以后可以将其他活动挂钩到事件上。这告诉我完成后需要发布()消息,而不是Send()它们。
  • 进程可能需要根据条件进行分支。这告诉我一个进程必须能够发布多种类型的消息。
  • 进程可能需要加入分叉。我想我应该使用Sagas。

希望这些假设很好,否则我比我想象的更麻烦。

为了简单起见,让我们忘记分叉或加入并考虑一个简单的管道,步骤A后跟步骤B,结束步骤C.每一步都有自己的分配器,可以有很多节点处理消息。 / p>

  • NodeA工作者包含IHandleMessages处理器,并发布EventA
  • NodeB worker包含IHandleMessages处理器,并发布Event B
  • NodeC worker包含一个IHandleMessages处理器,然后管道完成。

以下是配置文件的相关部分,其中#表示worker的编号,(即有NodeA.1和NodeA.2的输入队列):

NodeA:
<MsmqTransportConfig InputQueue="NodeA.#" ErrorQueue="error" NumberOfWorkerThreads="1" MaxRetries="5" />
<UnicastBusConfig DistributorControlAddress="NodeA.Distrib.Control" DistributorDataAddress="NodeA.Distrib.Data" >
    <MessageEndpointMappings>
    </MessageEndpointMappings>
</UnicastBusConfig>

NodeB:
<MsmqTransportConfig InputQueue="NodeB.#" ErrorQueue="error" NumberOfWorkerThreads="1" MaxRetries="5" />
<UnicastBusConfig DistributorControlAddress="NodeB.Distrib.Control" DistributorDataAddress="NodeB.Distrib.Data" >
    <MessageEndpointMappings>
        <add Messages="Messages.EventA, Messages" Endpoint="NodeA.Distrib.Data" />
    </MessageEndpointMappings>
</UnicastBusConfig>

NodeC:
<MsmqTransportConfig InputQueue="NodeC.#" ErrorQueue="error" NumberOfWorkerThreads="1" MaxRetries="5" />
<UnicastBusConfig DistributorControlAddress="NodeC.Distrib.Control" DistributorDataAddress="NodeC.Distrib.Data" >
    <MessageEndpointMappings>
        <add Messages="Messages.EventB, Messages" Endpoint="NodeB.Distrib.Data" />
    </MessageEndpointMappings>
</UnicastBusConfig>

以下是经销商配置的相关部分:

Distributor A:
<add key="DataInputQueue" value="NodeA.Distrib.Data"/>
<add key="ControlInputQueue" value="NodeA.Distrib.Control"/>
<add key="StorageQueue" value="NodeA.Distrib.Storage"/>

Distributor B:
<add key="DataInputQueue" value="NodeB.Distrib.Data"/>
<add key="ControlInputQueue" value="NodeB.Distrib.Control"/>
<add key="StorageQueue" value="NodeB.Distrib.Storage"/>

Distributor C:
<add key="DataInputQueue" value="NodeC.Distrib.Data"/>
<add key="ControlInputQueue" value="NodeC.Distrib.Control"/>
<add key="StorageQueue" value="NodeC.Distrib.Storage"/>

我正在使用每个节点的2个实例进行测试,问题似乎出现在Node B的中间。基本上有两件事可能发生:

  1. Node B的两个实例都报告它正在订阅EventA,并且NodeC.Distrib.Data@MYCOMPUTER也订阅了Node B发布的EventB。在这种情况下,一切都很好。
  2. 节点B的两个实例都报告它正在订阅EventA,但是,一位工作人员说NodeC.Distrib.Data@MYCOMPUTER正在订阅TWICE,而另一位工作人员没有提及它。
  3. 在第二种情况下,似乎只是通过分发者路由订阅消息的方式来控制,如果“overachiever”节点处理EventA,一切都很好。如果“未成功者”处理EventA,那么EventB的发布没有订阅者,工作流程就会死亡。

    所以,我的问题:

    1. 这种设置是否可行?
    2. 配置是否正确?除了简单的单级发布者/ 2工作者设置之外,很难找到与分发者配置的任何示例。
    3. 拥有一个执行所有非计算密集型流量警察操作的中央代理进程更有意义,并且只有在任务长时间运行并且必须进行负载平衡时才向分发器后面的进程发送消息?
      • 然后负载均衡的节点可以简单地回复中央代理,这看起来更容易。
      • 另一方面,这似乎与NServiceBus力量的分权相矛盾。
      • 如果这是答案,并且长时间运行的进程已完成事件是回复,那么如何保留发布以便以后对已发布事件进行扩展?

1 个答案:

答案 0 :(得分:2)

您遇到的问题是您的节点没有看到彼此的订阅者列表。您遇到这个问题的原因是您在默认的NServiceBus配置文件(lite)下尝试生产方案(横向扩展),该方案不支持横向扩展,但使单机开发非常高效。

要解决此问题,请使用本页所述的生产配置文件运行NServiceBus主机:

http://docs.particular.net/nservicebus/hosting/nservicebus-host/profiles

这将让不同的节点共享相同的订阅者列表。

除此之外,您的配置正确。