问题标签 [aggregateroot]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
c# - 聚合根和聚合的代码示例
我试图了解如何使用聚合根和聚合,但我找不到任何具体信息或示例。
例如,我有以下三个实体:
- 民意调查
- 问题组
- 问题
如果没有Survey或QuestionGroup实体,就不能存在Question实体。所有问题都属于一个 QuestionGroup,所以我的理解是
QuestionGroup 是 Question 的聚合根
QuestionGroup 也不能不作为调查的一部分而存在,因此
调查是 QuestionGroup 的聚合根
上面似乎是嵌套聚合根的情况。
Q1。您如何在 C# 中实际创建聚合根和聚合?这在代码中是什么样子的?您使用内部类还是聚合根拥有引用?我找不到任何好的例子。
Q2。更进一步,如何编写嵌套聚合根?
谢谢!
domain-driven-design - 具有深层层次结构的聚合根在 DDD 中是否合适?
我有一个系统,用户在表单中回答问题。我有代表这个模型的对象,但我不太确定如何根据 DDD 组织这些对象。
- 表格(有自己的列表)部分;
- 部分->(有自己的)组列表;
- 组->(有自己的)问题列表;
- 问题 ->(可以有自己的子问题列表)问题;
- 问题->(有自己的)答案列表;
- 答案 -> (有自己的)Answer_Details 列表;
- Answer_Detail ->(可能有自己的子详细信息列表)Sub_Answer_Details。
每个对象都有超过 15 个属性,如果没有父对象,每个对象都没有意义。根据 DDD,我认为 Form 实体应该是 Aggregate Root 而所有其他对象都应该是值对象。这意味着我只需要一个用于表单实体的存储库。在这种情况下,FormRepository 将被各种用于子对象的 CRUD 方法弄乱。就 DDD 而言,我的推理是否正确?我最终得到一个非常广泛的聚合体可以吗?我相信这种表示很容易导致性能问题。
domain-driven-design - 我们对 DDD 中的域模型中使用的这些类型的对象有何要求?
我试图找到这个命名问题的解决方案,但我在网络上的任何地方都找不到类似的用法。可能是我们在域模型中有一个设计流程,或者我们根本没有为所谓的“ValueObjects”使用适当的名称。
请阅读下文..
我们使用具有 CQRS 模式的领域驱动设计。下面是域模型的设计方式。
PS 不相关,但供您参考,我们的应用程序使用 ASP.NET MVC 和控制器与服务层通信。DTO(数据传输对象)被传入/传出到 MVC 控制器,这不在上图中。
问题是我们没有正确使用“ValueObject”。根据 Martin Fowler 的定义,我们的 ValueObject 不是 ValueObject 的真实表示。 http://martinfowler.com/bliki/ValueObject.html
例如,我们的 ValueObjects 有一个身份。
这些值对象只是在命令、聚合根和域实体之间传送数据。例如,AggregateRoot 只是基于域实体创建 ValueObjects,并将这些 ValueObjects 返回给命令层。
以下不是完整的实现。只是一个简单的例子来展示交互
AggregateRoot 扩展方法:
聚合根:
命令 :
我们正在努力为这些所谓的“ValueObjets”找到合适的名称。它们似乎也不是 DTO,而且我们希望能够与服务层中使用的 DTO 区分开来。具体来说,我们想知道可以为这些类型的对象 (ValueObjects) 调用的适当名称。任何想法都非常感谢。
entity-framework - 从聚合根中删除子
我有一个带有Add、Update、Delete的公共存储库。我们将其命名为CustomerRepository。
我有一个名为Customer的实体(POCO) ,它是一个聚合根,带有Addresses。
我处于分离实体框架 5 场景中。
现在,假设在获得客户后,我选择删除客户地址。我通过Update方法将Customer聚合根提交到存储库。
如何保存对地址所做的修改?
- 如果地址 id 为 0,我可以假设地址是新的。
- 对于地址的其余部分,我可以选择附加所有地址,无论如何都将其标记为已更新。
- 对于已删除的地址,我看不到任何解决方法...
我们可以说这个解决方案是不完整和低效的。
那么应该如何更新聚合根子节点呢?
我是否必须使用AddAddress、UpdateAddress、DeleteAddress等方法完成CustomerRepository?
似乎它会打破这种模式......
我是否在每个 POCO 上设置了持久性状态:
然后在我的CustomerRepository中只有一种方法Save?
在这种情况下,我似乎正在重新发明实体“非 POCO”对象,并将数据访问相关属性添加到业务对象......
domain-driven-design - 为什么允许在以后执行跨越聚合的一致性规则?
从:
不变量是在数据更改时必须维护的一致性规则,将涉及 AGGREGATE 成员之间的关系。任何跨越 AGGREGATES 的规则都不会一直是最新的。通过事件处理、批处理或其他更新机制,可以在某个指定时间内解决其他依赖关系。但是在 AGGREGATE 中应用的不变量将随着每个事务的完成而强制执行。
a)我将其解释为,旨在保持多个聚合之间的一致性的规则不必在这些聚合之一将其更改保存到某些持久性存储时强制执行,而是可以在稍后的某个时间强制执行这个聚合已经用持久存储完成了它的事务?
b)但是为什么可以容忍这种行为,因为它会导致数据不一致/损坏?
谢谢
domain-driven-design - 更新聚合根内的多态子实体
我试图弄清楚在聚合根中更新多态子实体的最佳方法是什么。作为参考,假设我有一个存储对象的ShippingContainer
根实体;Cargo
有许多类型的Cargo
对象,例如 、BigCargo
等HazardousCargo
,每一种都有自己独特的属性。
我正在阅读这个问题:更新聚合中的实体
这个问题的答案似乎表明我应该将该ChangeCargo
方法放在ShippingContainer
采用某种 DTO 参数对象的对象上。我的问题是,当您尝试更新的对象是多态的时,这是否仍然是最佳实践(我现在是否需要镜像 Cargo 对象类型的 DTO 对象层次结构?),还是我应该做其他事情?
c# - DDD - 聚合根 - 处理效率和并发性
首先,我承认我是 DDD 的新手,需要阅读“蓝皮书”。
我正在构建一个具有“匹配”类型的 AggregateRoot 的系统。每个匹配都可以有一个“投票”集合,并且还有一个只读的“投票计数”属性,当用户对匹配进行投票或否决时,该属性会增加。
由于许多用户可能同时对匹配进行投票,因此必须从匹配中添加/删除投票,并且必须将 VoteCount 作为一个涉及写锁的原子操作增加/减少(由数据库处理锁)。(我需要 VoteCount 作为数据库中的静态值,以便其他进程/组件有效地查询。)
在我看来,如果我坚持严格的 DDD,我会这样编码这个操作:
应用程序服务将接收一个投票请求对象,然后该服务将从匹配存储库中检索匹配对象。然后,该服务将调用匹配对象上的某种方法,以将投票添加到集合中并更新 VoteCount。然后,存储库会将 Match 实例保留回数据库。但是,这种方法对我的应用程序不可行,主要有两个原因,正如我所见:
我在后端使用 MongoDB,无法将此读写操作包装到事务中,以防止对 Match 数据及其关联的 Votes 和 VoteCount 的脏读。
这是非常低效的。我拉回整个对象图只是为了添加一个投票并增加投票计数。尽管这在文档数据库中比在关系数据库中更有效,但我仍在执行不必要的读取操作。
将单个 Vote 对象发送到存储库并对 Mongo 执行一个原子更新语句时,问题 1 和 2 不是问题。
在这种情况下,投票是否可以被视为“聚合”并值得拥有自己的存储库和聚合状态?
domain-driven-design - 避免领域驱动设计中的工作单元模式
我读过这篇文章,这让我三思而后行……:
“避免工作单元模式。聚合根应定义事务边界。”
为什么有人应该避免应用领域驱动设计的 UOW 模式?
domain-driven-design - 域驱动设计中每个根聚合实体的一个存储库
如果您遵循存储库模式,他们...说为每个根聚合实体创建一个存储库。
这意味着当我有这个模型时:
客户有订单 订单有产品 产品有供应商
ETC...
这意味着我有 4 个存储库,它们被放入一个存储库中。客户是根实体。
我在这里误解了什么吗?
repository - DDD 和 MVC:Contoller 从工厂而不是存储库获取 AggregateRoot?嗯?
我最近开始了一个使用现有数据库(Oracle)和 MVC 4 的项目。已经发生了很多编码......但代码中没有“策略”......只有 DB -> ORM -> 控制器。因此,我正在尝试为开发添加一些闪光,并练习一些 DDD 开发技术。
我已经定义了几个聚合根,每个都有一个存储库,用于处理保存和删除(及其子)等。这些聚合根中的一个引用了另一个聚合根,它通过它处理它的“子对象”它。
例子:
很好.. 客户 Aggregate Root,采购订单 Aggregate Root。
现在,一些服务也出现了,比如修改采购订单状态的服务,它消除了采购订单AR的负担,而且它很好、干净、有目的(它可以被其他“东西”用来更新采购订单的状态),(也许这应该是采购订单 AR 的一部分?一个小细节..)
存储库目前正在做他们的工作,即从数据库中持久化数据并用数据“填充” AR。当AR “保存”它时,存储库会保存任何需要保存的内容。客户AR使用采购订单存储库,因此客户可以加载它可能包含的任何采购订单。希望我走在正确的轨道上。
现在,进入MVC。所以我也有一些 ViewModel,它们基本上是关于需要向用户输出的内容的显示定义。Automapper 已经证明 frickin AWESOME,所以我可以“自动映射”到视图模型。不需要大脑,完美..
现在,真正让我失望的实施细节..
控制器目前正在通过一个客户端工厂工作,它返回一个客户端AR,然后它可以执行采购订单列表控制器需要做的任何事情,即管理相关的采购订单(作为一个整体,而不是采购订单的详细信息或本例中的数据)。
所以现在我想确保这是正确的..因为我看到的很多例子都有控制器与存储库而不是工厂一起工作,但我也看到工厂被推荐用于创建AR ..这让我相信在示例中,控制器正在处理聚合根,但是需要“消费者”的这种方式必须查询AR才能获取AR:
像:
或者更好:
这可能看起来像:
我觉得在这种情况下,存储库会根据我的需要“填充”ClientAR,所以现在我有了这个 ClientAR 东西,它根据它的使用情况而有所不同,它对我来说很臭……
使用工厂“感觉更好”,因为我只是从工厂创建一个 ClientAR 然后使用它,它不会根据情况而改变.. 它就是这样..
或者也许我完全想念它,我应该这样做::
我错过了事物的规范方面吗?(在这一点上,我还没有足够的能力真正开始使用规范(只是还),因为我需要让这些东西正常工作)
我尽量不陷入实施的细节,因为我的老板当然不会对我是怎么做的..到目前为止,至少在考虑 DDD 的情况下实施事情(希望我得到它)已经证明非常好的可测试性和责任的逻辑“边界”,这是由这种“模式”或“思维方式”产生的,我想我应该说..
那么,我是否正确地接近这个?如果它是有争议的,我可以接受。如果它只是简单的错误,那么指导肯定是值得赞赏的,如果我离得很远,如果背后有充分的理由,建设性的批评不会伤害我的感情。
提前致谢。