CQRS/ES - 我理解正确吗?
CQRS/ES - do I understand It correctly?
我想总结一下我对CQRS/ES的了解。一段时间前我开始阅读这个主题,因为我是年轻的开发人员,所以我不理解这个概念的各个方面。我将尝试在一些示例流程中描述我对 CQRS 的理解。因此,定义该架构的一般步骤我们有以下流程:
用户向我们的控制器提出请求。在该控制器方法中,我们创建指定的 Command(例如 CreateOrder)并将其传递给 Handler.
全局消息总线(或处理程序)负责将命令路由到指定的命令处理程序。所以在这里我们将命令传递给 CreateOrderHandler
在处理程序中,我们创建 聚合根(在本例中为 OrderAggregate)并应用来自 事件存储。在 EventStore 中,我们只保留与指定聚合(由全局 id 定义)相关的事件数据。所以在这一步之后我们在当前状态下聚合。
创建聚合后,我们将命令传递给它,并在方法中验证命令是否可以执行。如果我们可以 运行 这个命令,我们将创建 Event(在本例中为 OrderCreated)。
如果没有任何异常我们把Event保存在EventStore中(我觉得NoSql DB简单易用,保存事件简单)
现在处理程序将保存的事件传递给我们的 Denormalizer class 这是创建 View Models 的网关.因此,如果非规范化器得到一些事件,它 updates/creates 我们应用程序中的所有 ViewModels。我们将 ViewModel 保存在单独的数据库中。
用户可以查询更新的视图模型。
所以我这个是我对CQRS/ES的理解的简化版。请在每一层上纠正我。我的问题是:
在第 4 步中我们创建了聚合,我们应该将这个聚合保存在数据库中吗?保持当前状态。我在这里错过了什么吗?我们创建聚合只是为了检查创建事件的可能性?
我应该有实体吗?如果我在第 5 步中正确,我可以更新聚合实体并在我的视图模型中使用它们。我在这里有最大的困惑。
感谢所有的回答 ;)
In 4-th step we created aggregate should we save this aggregate in DB?
To keep current state. Am I missing something here? We created
aggregate only for checking possibility to create event?
如果您使用 EventStore,ES 本身会保存您的聚合状态。您在命令处理程序中谈论 "create" 聚合,但通常最好说在命令处理程序中聚合是从 ES 中重新水合的。
聚合使用在 ES 中应用的命令(或其数据)和引发(域)事件来跟踪聚合的状态变化,并且相同的事件由事件处理程序(如非规范化器)处理。
在通常描述的流程中,我在第 3 步之前有一个命令验证步骤。
无论如何,前段时间我试图描绘components of a typical CQRS/ES flow;网上有好几个,也许有用
聚合状态源自应用于它的过去事件。所以你不需要存储它的状态,因为它是从事件流派生的。话虽如此,您可能希望创建快照以避免很长的事件历史记录。在设计快照系统之前,值得测试重新应用以前事件列表的速度有多快。
当您向聚合发出命令时,它会分两个阶段进行处理。第一阶段实质上是检查它是否可以运行。如果是这样,它会构建一个或多个事件来表示更改,然后再将它们应用于自身。这里的关键是事件的产生可以而且经常确实需要应用域逻辑。换句话说,它不仅仅是一个事件制作者。
如果您觉得它有帮助,我在我的博客上有一个典型 CQRS 应用程序的更详细的概述。您可以在这里找到它:CQRS – A Step-by-Step Guide to the Flow of a typical Application
我想总结一下我对CQRS/ES的了解。一段时间前我开始阅读这个主题,因为我是年轻的开发人员,所以我不理解这个概念的各个方面。我将尝试在一些示例流程中描述我对 CQRS 的理解。因此,定义该架构的一般步骤我们有以下流程:
用户向我们的控制器提出请求。在该控制器方法中,我们创建指定的 Command(例如 CreateOrder)并将其传递给 Handler.
全局消息总线(或处理程序)负责将命令路由到指定的命令处理程序。所以在这里我们将命令传递给 CreateOrderHandler
在处理程序中,我们创建 聚合根(在本例中为 OrderAggregate)并应用来自 事件存储。在 EventStore 中,我们只保留与指定聚合(由全局 id 定义)相关的事件数据。所以在这一步之后我们在当前状态下聚合。
创建聚合后,我们将命令传递给它,并在方法中验证命令是否可以执行。如果我们可以 运行 这个命令,我们将创建 Event(在本例中为 OrderCreated)。
如果没有任何异常我们把Event保存在EventStore中(我觉得NoSql DB简单易用,保存事件简单)
现在处理程序将保存的事件传递给我们的 Denormalizer class 这是创建 View Models 的网关.因此,如果非规范化器得到一些事件,它 updates/creates 我们应用程序中的所有 ViewModels。我们将 ViewModel 保存在单独的数据库中。
用户可以查询更新的视图模型。
所以我这个是我对CQRS/ES的理解的简化版。请在每一层上纠正我。我的问题是:
在第 4 步中我们创建了聚合,我们应该将这个聚合保存在数据库中吗?保持当前状态。我在这里错过了什么吗?我们创建聚合只是为了检查创建事件的可能性?
我应该有实体吗?如果我在第 5 步中正确,我可以更新聚合实体并在我的视图模型中使用它们。我在这里有最大的困惑。
感谢所有的回答 ;)
In 4-th step we created aggregate should we save this aggregate in DB? To keep current state. Am I missing something here? We created aggregate only for checking possibility to create event?
如果您使用 EventStore,ES 本身会保存您的聚合状态。您在命令处理程序中谈论 "create" 聚合,但通常最好说在命令处理程序中聚合是从 ES 中重新水合的。
聚合使用在 ES 中应用的命令(或其数据)和引发(域)事件来跟踪聚合的状态变化,并且相同的事件由事件处理程序(如非规范化器)处理。
在通常描述的流程中,我在第 3 步之前有一个命令验证步骤。 无论如何,前段时间我试图描绘components of a typical CQRS/ES flow;网上有好几个,也许有用
聚合状态源自应用于它的过去事件。所以你不需要存储它的状态,因为它是从事件流派生的。话虽如此,您可能希望创建快照以避免很长的事件历史记录。在设计快照系统之前,值得测试重新应用以前事件列表的速度有多快。
当您向聚合发出命令时,它会分两个阶段进行处理。第一阶段实质上是检查它是否可以运行。如果是这样,它会构建一个或多个事件来表示更改,然后再将它们应用于自身。这里的关键是事件的产生可以而且经常确实需要应用域逻辑。换句话说,它不仅仅是一个事件制作者。
如果您觉得它有帮助,我在我的博客上有一个典型 CQRS 应用程序的更详细的概述。您可以在这里找到它:CQRS – A Step-by-Step Guide to the Flow of a typical Application