域驱动设计 – DDD中是否适合具有深度层次结构的聚合根?

前端之家收集整理的这篇文章主要介绍了域驱动设计 – DDD中是否适合具有深度层次结构的聚合根?前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我有一个用户在表单中回答问题的系统.我有代表这个模型的对象,但我不太确定如何根据DDD组织这些对象.

>表格(有自己的清单)部分;
>部分 – > (有自己的列表)组;
>组 – > (有自己的问题清单);
>问题 – >(可以有自己的子问题列表)问题;
>问题 – > (有自己的清单)答案​​;
>答案 – > (有自己的列表)Answer_Details;
> Answer_Detail – > (可能有自己的子细节列表)Sub_Answer_Details.

每个对象都有超过15个属性,如果没有父对象,每个属性都没有意义.根据DDD,我认为Form实体应该是Aggregate Root,所有其他对象应该是值对象.这意味着我只需要一个表单实体的存储库.在这种情况下,FormRepository将与子对象的各种CRUD方法混杂在一起.我的推理是否适合DDD?我最终得到了一个非常广泛的聚合物吗?我相信这样的表示很容易导致性能问题.

是的,DDD中的深层次结构很好.

我最终得到了一个非常广泛的聚合物吗? – 如果现实情况复杂,并且您的领域模型尽可能最好,那么最终会得到一个复杂的聚合根.

是的,Form应该是聚合根.

所有其他对象应该是值对象 – 错误,所有其他对象应该是非聚合根实体(带有Id),而没有用于获取它们的存储库.值对象没有Id,值对象的相等性仅由其属性值确定,而不是由Ids的等式确定(更多信息here).

在这种情况下,FormRepository将混杂着各种用于子对象的CRUD方法 – 不,存储库应仅包含关于聚合根的方法,即Get< T>.,保存< T>其中T:IAggregateRoot,一旦获得聚合根的实例,就可以遍历属性方法来获得所需的内容.例:

var formId = 23;
var form = _formRepository.Get(formId);
var firstGroup = form.Sections.First().Group().First();

或更好

var groupIndex = 1;
var firstGroup = form.GetGroupAt(groupIndex);

哪里

public Group GetGroupAt(int groupIndex)
{
    Sections.First().Group().ElementAt(groupIndex);
}

我相信这样的表示很容易导致性能问题 – 如果你使用CQRS,你将从命令处理程序调用一些Form域方法,如果你使用NHibernate实现持久性,它将默认使用延迟加载,并且只会加载Form从DB,然后它只加载你真正触摸的实体,所以例如Sections.First()将从DB加载所有部分,但不加载组和其余部分.对于查询,您将创建一个FormDto(数据传输对象)和其他可能被展平的dtos来获取所需形式的数据(可能与您的实体结构不同,UI可能会驱动dto结构).有关DDD / CQRS / NHibernate / Repository的信息,请查看我的blog

猜你在找的设计模式相关文章