cqrs - 重放事件 - 验证转换

标签 cqrs event-sourcing

我想知道在使用某些事件源解决方案重放事件时将事件应用于状态时应该包含什么逻辑。

具体来说,我想知道验证,假设我有实体可以处于以下状态之一:

  • 已登录
  • 活跃
  • 关闭
  • 已取消

  • 并且进度需要是Logged->Active->Close或Logged->Active->Cancelled,我们不能直接从Logged跳转到Close。

    现在,我明白了,验证应该包含在命令中:UpdateState将检查实体当前状态是否允许转换到所需的状态,并会产生适当的事件 StatusUpdated这将被持久化到事件存储中。

    问题是,回放时我应该怎么做?我应该只是更新状态,还是应该执行相同的验证(这样如果状态转换要求发生变化,除非我们添加一些额外的逻辑,否则将无法加载一些以前更新的实体),以确保我们不会以不满足我们当前逻辑的实体?

    附注。我想我在理解它时遇到了问题,因为在我的理解中,事件本质上只是关于“宣布”已经发生的事情(并且发送者状态已经被修改),以便感兴趣的各方可以做出相应的 react 。并且在事件加载/重播的情况下,您需要更改所述状态而不是实际“宣布”任何内容......

    最佳答案

    重放事件流时不需要执行任何验证。

    命令为将来要做的事情建模:您要求系统为您做某事。是否执行由系统决定,例如基于业务规则和验证。

    相反,事件模拟已经发生的事情。在现实中,你无法改变过去。

    所以,这意味着,当一个事件被持久化时,它是一个在处理它的时间点被认为有效的命令的结果。重放事件流只是意味着查看过去发生的事情,您无法更改这一点。

    因此,您无需再次运行任何验证。

    而且,这意味着如果有一天你的业务逻辑发生了变化,所有过去发生的事情(商业事故!)仍然发生了,所以它们一定不能改变。因此,您不能使用任何验证逻辑,因为它今天可能与您存储事件时不同。

    再说一遍:你不能(也不应该)改变过去:-)

    例子

    假设您有一种验证信用卡号的方法。客户来到您的商店,付款,根据您当前的规则,您认为他/她的卡是有效的,一切都很好。

    然后,有一天信用卡机构改变了信用卡号的计算方式,因此您有另一种验证算法。

    当您现在回放过去的事件时,付款已经发生,无论是否有新的验证规则——而且您无法改变它已经发生的事实!如果您愿意,您必须创建一个新交易以将钱汇回客户。同样,这将导致一个新事件,而不是与过去不同的事件。

    所以,长话短说:不要根据任何事情验证事件。它们根据定义是有效的,正如他们之前发生的那样 .

    关于cqrs - 重放事件 - 验证转换,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16348561/

    相关文章:

    user-interface - 用户界面如何知道允许对聚合根执行哪些命令?

    .net - CQRS - 读取模型 DTO 混淆

    oop - DDD、对象图和事件溯源

    cqrs - 事件存储 : learning how to use

    azure - Azure SQL 数据库中的主键

    ruby-on-rails - 在 CQRS 和 DDD 流程中创建值对象的位置

    cqrs - 具有不一致事件行为的事件溯源

    domain-driven-design - 事件溯源重构

    event-sourcing - 聚合间通信

    c# - WebApi 中的微服务设计部分