我目前正在根据 DDD 的原则为产品/政党管理系统创建概念证明。其中一项要求是各方数据(客户、经销商)将存储在网络上的 CRM 中,而产品特定数据将存储在本地 SQL 数据库中(见下文)。
CRM 系统(基于 Web)
客户(包含姓名、地址、电子邮件、联系方式等)
经销商(包含姓名、地址、活动状态)
产品系统(本地)
BaseProduct(定义普通产品)
ResellerProduct(定义将由经销商销售的基本产品的定制) CustomerProduct(定义客户注册的产品)。
我一直在对如何实施解决方案的不同方法进行大量研究,但我正在努力理解所有概念以及它们如何应用于我的问题。
我首先将这些区域分成 2 个不同的有界上下文,Party 和 Product。我为这些上下文中的每一个定义了域模型,并且在其他模型中实体引用了概念时,我将它们保留为简单的 Guid Id(即产品域中的 CustomerProduct 将具有相关 Guid 的 CustomerRef 值)。
然后,我实现了一个使用对 Web CRM 的 API 调用的 Party 基础架构实现和一个使用 NHibernate 的 Product 基础架构实现。对于其中的每一个,我都实现了一个 UnitOfWork,这样我就可以控制每个上下文中的事务过程。应用层将在运行时注入两个上下文并使用它们。
例如:
- ApplicationService.RegisterNewProduct(customerId, ProductId)
- 启动每个工作单元的事务(PartyUnitOfWork.Begin()、ProductUnitOfWork.Begin())
- 使用每个上下文的存储库来查找相关的域对象(Party.Customer.Find(Id)、Product.ResellerProduct.Find(Id))
- 执行逻辑以确定客户是否符合条件、产品是否有效等。
- 创建一个新的 CustomerProduct 并保存到产品系统
- 提交每个上下文 UnitOfWork
然后,我开始进一步探索有界上下文,并考虑重构应用程序,以便每个上下文对另一个上下文的概念表示有限,但仅特定于该上下文。即在产品上下文中,我将有一个客户实体,它有一个 ID、名称和活动状态,但可能没有联系偏好等。然后我将使用 DomainEvents 来协调不同系统之间的活动,以保持他们的数据是最新的(即,如果在 CRM 系统中创建了一个新客户,一个事件将由产品系统引发和处理,以更新其客户代表)。因此上面的例子会改变,所以只使用了 Product 上下文。
为了进一步混淆问题,假设“RegisterNewProduct”调用也创建了一个新客户,我是否会在产品系统中创建客户并引发将由 Party 系统处理的“NewCustomer”事件?
我有兴趣收集人们对这些想法的评论吗?