微服务架构设计模式-(10)事件溯源

事件溯源

  • 使用一系列表示状态变更的领域事件来持久化聚合
  • 好处
    • 保留聚合的历史记录,方便审计、监管
  • 弊端
    • 有学习曲线
    • 查询通常困难,需要使用CQRS
    • 事件演化时,代码的处理变得困难
      • 比如说一次升级之后,处理事件的信息变多了,而之前的事件还没有消费完
        • 解决方法,加载事件时,补充事件信息到最新版本

传统持久化的问题

  • 只保留当前状态
    • 聚合更新后,先前的状态丢失
    • 如果业务需求记录历史,这又是一个耗时的工具,开发人员自己实现
  • 审计繁琐
    • 耗时
    • 容易和业务逻辑偏差
      • 比如新增一个逻辑,但是忘了记录到历史中
  • 无法把自动发送消息作为更新数据库的一部分
    • 就是更新业务数据和发送事件消息同时成功,同时失败
  • 对象和关系“阻抗失调”
    • 面向对象和关系数据库不是相辅相成的
    • 越是复杂的面向对象系统设计,越是难以用关系数据库来表示

事件溯源

  • 以事件为中心,用于实现业务逻辑和聚合的持久化
    • 就是把事件存放在数据库中,并把相关的业务数据存下来
  • 存储信息
    • 唯一事件ID
    • 事件类型
    • 聚合标识
      • 实体类型
        • 聚合根的类型
        • 比如这条记录是以订单为主线
      • 实体ID
        • 聚合根
    • 序列化的事件
      • 通常是大json
      • event_data
  • 事件表示状态的改变
    • 每一个聚合的状态发生变化时,它必须发出一个事件
    • 事件必须包含聚合执行状态变化所需的数据

如何处理并发更新聚合

  • 乐观锁
    • 使用版本列来判断是否已更改
      • 版本可以使用事件ID,也可在事件存储表中

如何使用事件存储表发送事件

  • 轮询
    • 在事件表中加一列,表示事件是否以及发送
  • 事务日志拖尾
    • 从事件表中读取事件,发送到消息代理
    • 由消息代理来保证消息可靠发布

如何回滚事件

  • 使用快照
    • 就是记录一个事件发生前快照

事件消费时,注意幂等

  • 实际上,我觉得这个应该由消费方来保证,因为无法百分百保证不充分发送消息。
  • 一种重复是事件ID重复,一种是业务数据重复(就是两个事件实际上是同一个)

猜你喜欢

转载自blog.csdn.net/u014704998/article/details/128997269