正确实施CQRS / ES



最近我期待在我的微服务中实现带有事件源的CQRS/ES模式。

我一直在阅读这些模式,但我有一些问题,我找不到答案:

  1. 当做CQRS/ES时,每个微服务应该有自己的本地服务吗数据库(在微服务中)?

    我知道将会有一个用于写的事件存储和一个只读投影数据库,我完全理解它们的目的,但是微服务需要吗他们自己的本地数据库吗?(优点/缺点)

    示例:订单微服务可以有本地订单数据库、项目服务和项目本地数据库等…

  2. 如何验证之前微服务中是否存在某些数据实际发出命令?

    假设我想下一个新订单,所以我假设首先我必须检查该项目是否仍在库存中,然后执行另一个操作/s。

    然而,如果我想检查一个项目是否仍在库存中,我在哪里查询该数据,它是投影(只读)数据库,还是每个微服务都有一个本地数据库?

在这一点上我读了很多关于CQRS/ES的文章,但其中大多数只是解释了概念,而不是真正深入到现实生活中的场景/解释如何实现它。如果你有什么建议,我将不胜感激。

感谢

一般来说,在处理微服务时,建议(无论您是否使用CQRS/ES)没有两个微服务使用相同的数据库,或者至少没有两个微服务写入相同的数据库。这允许每个微服务控制自己的模式,只有当微服务需要时才需要改变模式。这样做的另一个好处是数据库被完全封装在服务中:它纯粹是一个实现细节。

实现读模型的微服务完全有可能没有数据库:它可能能够将所有状态保存在内存中(一个例子可能是为监视基础设施公开指标的读模型),或者它可能只是将事件从写模型转换为命令到另一个服务(因此它的所有状态只是它在事件流中的位置)。

如果我想检查一个项目是否仍在库存中,我在哪里查询该数据,它将是投影(只读)数据库,还是每个微服务拥有的本地数据库?

在事件源系统中,每个不是事件流的视图都是投影。因此,根据您的需求,您的服务可以查询另一个服务或基于事件维护自己的视图。

请注意,在任何给定的时刻,可能存在一个已经发布到事件流的事件(即它已经无可争议地发生了),但也存在一个尚未处理该事件的投影:投影最终与事件流一致。因此,任何关于商品是否有库存的检查都只能告诉你该商品在过去的某个时间点有库存(没关系,用Greg Young的例子来说,没有库存数据可以保证仓库里没有东西被盗,除非小偷在带着赃物出去的时候碰巧更新了库存数据)。在你的查询之后的纳秒内,它可能会在你下订单之前收到一个事件的消息,使它缺货。

因此,它可能只是值得发送一个命令,让它拒绝你的订单,如果该项目没有库存。写端(它是系统中一致性更强的部分,但要记住,在许多情况下,一个组件的事件是另一个组件的命令)没有义务接受每个命令;"command"在这种情况下,真正的意思是"礼貌地请求将事件发布到符合我期望的宇宙状态的事件流"。

相关内容

  • 没有找到相关文章

最新更新