为什么sagas不能查询读取方?

mag*_*nus 8 domain-driven-design cqrs event-sourcing

在CQRS域驱动设计系统中,常见问题解答说传奇不应该查询读取端(http://cqrs.nu).但是,一个saga监听事件以执行命令,并且因为它执行命令,它本质上是一个"客户端",所以为什么saga不能查询读取模型?

use*_*727 6

Sagas 不应查询读取端(预测)以获取完成其任务所需的信息。原因是您无法确定读取端是否是最新的。在最终一致的系统中,您不知道投影何时会更新,因此您不能依赖其状态。

这并不意味着传奇不应该保持状态。在许多情况下,saga 确实需要跟踪状态,但是 saga 应该负责创建该状态。在我看来,这可以通过两种方式完成。

它可以通过从事件存储中读取事件来建立其状态。当它接收到应该触发的事件时,它会从存储中读取它需要的所有事件,并以与聚合类似的方式构建其状态。这可以通过创建新流在Event Store 中提高性能。

另一种方式是它不断地侦听来自事件存储的事件并建立状态并将其存储在一些数据存储中,就像投影一样。请注意这种方法。你不能用与投影相同的方式来回答传奇。如果您需要更改存储状态的方式并希望重建它,请确保不要执行您已经执行过的命令。

  • 如果 SAGA 被视为客户端并像其他投影一样按顺序/同步接收事件,则它使用的投影数据将始终保持同步。或者我错过了什么? (2认同)

the*_*Dmi 3

Sagas 使用命令模型来更新系统的状态。命令模型包含业务规则,并且能够确保更改在给定域内有效。为此,命令模型拥有它所需的所有可用信息。

另一方面,读取模型具有完全不同的目的:它构造数据以便适合提供信息,例如在网页上显示。

由于 saga 通过命令模型拥有所需的所有信息,因此不需要读取模型。 更糟糕的是,使用传奇中的读取模型会引入额外的耦合并显着增加系统的整体复杂性。

这并不意味着您绝对不能使用读取模型。但如果您这样做,请确保您了解后果。对我来说,这个门槛相当高,而且我总是找到不同的解决方案。