CQRS是传奇/流程管理器同步执行一组相关命令的最佳方法吗?

时间:2018-03-26 06:17:50

标签: .net-core cqrs masstransit saga

我有一个CQRS .NET Core服务,目前每个命令都有一个端点。有时,一系列命令构成系统中的单个动作(例如,创建评估),并且一旦前一个命令将数据提交到db(这是由于遗留数据库设计),就必须同步执行3个左右的命令。

目前,这是由客户端处理的,其中每个命令在之前的依赖命令完成后触发(使用promises)。

值得注意的是,这些命令有时也会单独执行,如果它们被合并到一个命令中,它最终会变得庞大而且很难测试。

我想要做的是创建一个管理像创建评估一样的操作的单一端点,它必须一个接一个地执行以下命令:

  1. UserCreated
  2. AssessmentCreated
  3. AssessmentRegisteredToClient
  4. 我一直在使用MassTransit传奇/状态机/进程管理器的路线,但我对它的工作越多(我的理解越多)我越认为它看起来有点矫枉过正而不是正确方法(因为这些是命令而不是事件,都在一个有界的上下文中)。

    流程管理器是否合适?如果是,那么MassTransit状态机的实现方式是什么,或者我应该查看其他来源?或者我应该只创建一个端点,一次触发一个命令(即在ASP控制器中有这个同步代码)?

2 个答案:

答案 0 :(得分:3)

为了澄清,UserCreated不是命令,而是一个事件。

你有三个选择:

  • 建立反应系统。所以,在CreateUser之后(顺便说一句,这里不是一个非常好的语言,因为你从未创建你的用户,他们在你的系统中注册)你发出UserCreated,这会引起反应发送命令CreateAssessment,依此类推。
  • 使用MT saga作为流程管理员。如果您需要确保您的某些复杂工作流以您期望的方式完成(或失败),状态机非常适合。
  • 使用MT courier功能实现分布式事务。您将拥有一系列活动,行动和补偿行动(逆转)。

我个人会分析我的问题,找出在我回到用户并说“没关系”之前我需要做的最低限度。其余的可以在幕后异步完成。它更多的是域分析而不是技术。

答案 1 :(得分:1)

因为所有命令都由同一个Aggregate处理,所以解决方案是创建第4个组合命令,它是从无处不在的语言命名的,包含3个命令。在内部,Aggregate只调用3个命令方法,因此没有代码重复。

在最简单的解决方案中,也明确,在这个特定的用例中,这些命令在单个事务中按顺序执行:它们都成功或者全部失败。

P.S。正如@AlexeyZimarev所指出的,那些不是命令而是事件