在使用事件采购的分布式系统中存储事件的位置?

时间:2011-06-04 18:42:11

标签: messaging cqrs event-sourcing

鉴于您有多个系统,这些系统由事件集成,并且所有系统都使用事件源。你在哪里存储活动?

在我的情况下,我有三个系统:

  • 一个网站,这是一个商店
  • 网站后端管理客户,产品等。
  • 会计系统

每当在其中一个系统中发生域事件时,事件就会被发布,并且可以由其他系统处理。所有系统都使用事件采购。

我想知道你会在哪里保存这些活动。当然,每个系统都必须存储它处理的所有事件,因为它正在使用事件源,因此它依赖于它曾经处理过的事件。

但是那些不需要的其他事件又因此系统没有订阅呢?我正在努力解决需求可能发生变化的问题,这样系统就必须处理过去没有持续存在的事件。如果系统需要处理它们在发生时未订阅的事件,您会从哪里获得这些事件?

我认为此时不使用事件源的系统存在很大差异。如果你必须在依赖于数据的系统A中实现一个功能,这个功能在A中是不可用的,而在另一个系统B中,并且你通过像NHibernate这样的ORM工具持久保持当前状态,你可以简单地将数据从A导入到B 。由于使用事件源的系统依赖于事件来获取当前状态,因此您必须导入过去错过但现在需要的所有事件。

对我来说,这个问题有几种不同的方法。

  1. 每个系统都会保存发布的所有事件。这使您能够在需要时重新发布事件或将其导入另一个系统。
  2. 每个系统都会保存所有发生的事件,甚至是那些不需要处理的事件。
  3. 来自所有系统的所有事件都存储在中央事件日志中。如果您需要处理过去发生但未订阅的事件,可以从此处导入。
  4. 你如何处理这种情况?你在哪里保存你的活动?

    修改

    感谢Roy Dictus的回答。我仍然不确定如何处理以下情况:

    该网站发布事件CustomerRegistered,CustomerPurchasedProduct和CustomerMarkedProductAsFavorite。 在当前版本的后端中,客户需要显示并且必须显示他们的购买。在该版本的系统中,标记为收藏的客户不感兴趣。因此,后端仅订阅了CustomerRegistered和CustomerPurchasedProduct。

    现在营销部门还希望在客户详细信息页面上显示有关喜爱产品的信息。由于后端未订阅CustomerMarkedProductAsFavorite,因此后端不提供此信息。我从哪里获得这些信息?

2 个答案:

答案 0 :(得分:7)

  1. 每个系统都存储自己的事件。每个系统都是自己的CQRS系统,或者至少是它自己的独立服务,因此负责自己的数据。
  2. 每个系统还将其事件发布到服务总线。此服务总线确定保存这些事件的位置。通常是在交易排队系统中。
  3. 每个系统都订阅它消耗的外部事件。它不存储这些传入事件,只存储由它们产生的事件。当它消耗传入事件时,服务总线知道它可以从该服务的传入队列中删除该事件。
  4. 编辑以容纳您的额外问题:

    如果另一个应用程序突然对额外信息感兴趣,则必须将侦听器添加到它现在感兴趣的事件中。

    此外,这些事件的所有来源都可以重播这些事件。重放是事件驱动系统的一个强大功能,允许这样的场景。因此,事件源仅重放所选事件(例如,过去6个月中的所有CustomerMarkedItemAsFavorite事件)。已经消耗了这些事件的系统应该认识到重放的事件是“旧”事件(即它已经处理过的事件)并忽略它们。

    这样,任何更新为使用来自其他子系统的额外信息的子系统都可以获取该信息,并在单个批处理操作中获取所有信息。

答案 1 :(得分:0)

WRT您的编辑:是否真的需要访问历史CustomerMarkedProductAsFavorite数据。更改后端以订阅新数据,然后继续前进。如果确实需要,您可以找出如何将缺失的数据作为单独的问题回填。

Roy已经概述了一种可能的架构,可以确保您将来可以使用CustomerMarkedProductAsFavorite数据进行回填。