【问题标题】:Event sourcing - error handling when events are not created事件溯源 - 未创建事件时的错误处理
【发布时间】:2018-08-21 23:13:16
【问题描述】:

据我了解,在事件溯源中,会记录事件。但是,这也意味着首先发生状态更改,然后我们记录该事件。例如,假设:

  1. 客户端向服务器发送命令以“创建用户”。
  2. 服务器验证命令并创建用户,即存储新用户 数据库中的用户。
  3. 然后服务器记录/存储Created User 事件。即事件 采购。
  4. Created User 事件传播给订阅者

在上面的场景中,我们如何处理步骤(2)成功但步骤(3)由于网络故障、数据库离线等而失败的场景?既然创建了一个新用户但该事件从未被记录,整个系统将处于不确定状态。我们如何减轻这些类型的故障?还是我上面列出的步骤不是进行事件溯源的方法?

谢谢!

【问题讨论】:

    标签: event-sourcing


    【解决方案1】:

    这并不是在事件溯源中发生的事情,甚至在普通的 CQRS 中也不会发生。

    在事件溯源中,在验证命令后,域事件由源(DDD 中的聚合)生成,然后在第一步中将它们附加到事件存储中。之后,订阅者(读取模型、投影、Sagas、外部系统)接收并处理新的领域事件。

    在 CQRS 中,域事件生成后,它们被应用于聚合,然后聚合的状态和新事件被持久化在同一个本地事务中,作为第一步。只有在那之后,订阅者才会收到事件。

    所以你看到了吗?您的情况不会发生:步骤 2 和 3 以原子方式持续存在,它们一起成功或失败。

    【讨论】:

    • 澄清一下,在事件溯源中,您是说没有创建新用户(即没有发生状态更改)但记录了事件 User created
    • @user3240644 我是说在 ES 中没有用户被持久化,只有域事件。相比之下,在普通 CQRS(没有 ES)中,用户和新事件被持久化但在同一个事务中。
    • @user3240644 与事件溯源相同,您只保留域事件。您可以进行一种称为“快照”的优化,您可以在其中保存每个 n 事件、聚合(在您的情况下为 user),但只有在性能太低时才这样做。
    • 非常感谢。所以换句话说,对于 CQRS,底层技术(即数据库类型)很重要,因为例如,对于 dynamo db,我需要 2 个表(一个用于命令/事件,一个用于状态)而 dynamo db 不需要保证对不同表的原子写入。在这种情况下,什么技术是一个不错的选择?
    • @user3240644 我不知道,有交易。我不使用普通的 CQRS。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2019-02-20
    • 2013-03-09
    • 1970-01-01
    • 2023-03-24
    • 1970-01-01
    • 2016-04-25
    • 1970-01-01
    相关资源
    最近更新 更多