CQRS跟踪用户更改

时间:2012-07-04 14:41:41

标签: .net design-patterns cqrs

我们目前正在研究构建我们(网络)应用程序的新方法,并且一种让人想起的方法是CQRS。我们仍然有几个问题:

如果我理解正确,这可能意味着拥有2个或更多域模型,一个核心域模型和一个webapp读取模型。

此核心域模型不是由webapp直接写入,而是由不同的服务写入。 我们正在考虑使用NServiceBus来创建发布者/处理程序,以便webapp可以发布用户所做的更改。然后,订户将处理该消息并更新核心域模型和读取模型。

我们想要实现的目标:

用户A创建10个新对象,例如书籍。

消息订阅者需要处理大量消息,因此在更新域模型之前需要几分钟。

当用户A刷新页面时,他应该看到他刚创建的10本书。

当用户B刷新页面时,他实际上不必看到这些项目。

您最好将这10个新对象存储在哪里?

将此数据与读取模型中的“旧”数据合并的最佳方法是什么?

假设用户B确实需要查看这些新项目,那么存储这些数据的最佳方式是什么?

同时处理由2个不同用户添加同一本书的最佳方式是什么? (除了图书描述之外,所有数据都是相同的。它仍然是同一本书:)

您可以用哪种方式处理尚未写入核心域模型的10个对象之一的更新,因此没有唯一ID?

1 个答案:

答案 0 :(得分:1)

在我看来 CQRS有许多不同的方面需要考虑。我从中汲取的核心观点是用户行为的分离(命令 - >写模型)和显示信息(查询< - 读取模型)。然后我可以根据应用要求挑选和选择适合这种分离的其他建筑模式。请记住,CQRS并不是顶级架构,您应该从中进行选择并仅在适当时使用。

从您的问题中我得到的印象是您的研究没有太远,所以我推荐以下内容; Initial CQRS documentationRinat Abdullin's BlogJonathan Olivers Blog (read the older stuff)Rinat's CQRS guide (although I've yet to read through this site)

我保证通读CQRS documentation您可以自己回答问题。

也许如果你告诉我们你想要使用的模式/技术,我可以提供更完整的答案。但是为了让你的第一个问题开始,这是非常直接的:

  

你最好把这10个新物品存放在哪里?

答案是,从逻辑上讲,您可以在写入和读取模型中存储数据的部分;物理上,这可以存储在同一个数据存储中,也可以存储在不同的数据存储中,具体取决于您选择的技术和实现(例如,sql-server数据库与键值no-sql解决方案)。

例如,如果您选择使用事件采购,则将事件存储在写入模型中。您的读取模型将存储非规范化的数据,精心设计,以便您的屏幕可以根据读取模型的数据进行组合。但是,正如我所看到的那样,这是正确的模式;您的读取模型可以只存储使用查询服务规范化的数据,对执行数据库执行实际的SQL查询。

编辑后发表评论

我目前正在处理的系统虽然确实使用了事件,但并未使用消息传递。一切都正在进行中。所以命令被处理;在同一工作单元内提出和处理事件。基本上命令处理程序不会完成,直到相应的事件处理程序全部完成。

当读取模型的更多密集/复杂更新时,我们仍在考虑进程外事件处理程序。但是在这个阶段并不需要它,它使事情变得简单。

整个最终的一致性方面只是模式附带的东西。它对于“其他”用户来说永远不会是一个问题,但对于刚刚提交并刷新页面的用户,我可以看到这令人困惑,看不到他们刚刚提交的更新。就个人而言,我不喜欢伪造更新的想法,因为这就像加倍努力一样。相反,我更喜欢重定向到确认页面的选项,为您的应用程序提供更多时间来处理消息。

我个人希望进一步探索的内容是跟踪提交的命令以及相关的进程外事件处理程序。刷新具有尚未完成的消息的页面的用户可以被通知不完整的消息。消息完成处理后,可以将“推送”通知给客户端。我会使这些通知变得微妙,以免分散用户的注意力或者让人感到烦恼和阻碍。