由于没有值对象的存储库,我该如何加载所有值对象?
假设我们正在建模一个博客应用程序,并且有以下类:
- Post(实体)
- Comment(值对象)
- Tag(值对象)
- PostsRespository(存储库)
我知道当我保存新的post时,它的tags会与之一起保存在同一个表中。但是如何加载所有帖子的所有标签呢? PostsRespository是否应该有一种方法来加载所有标记? 我通常这样做,但我想知道其他人的意见。
由于没有值对象的存储库,我该如何加载所有值对象?
假设我们正在建模一个博客应用程序,并且有以下类:
我知道当我保存新的post时,它的tags会与之一起保存在同一个表中。但是如何加载所有帖子的所有标签呢? PostsRespository是否应该有一种方法来加载所有标记? 我通常这样做,但我想知道其他人的意见。
我正在寻找更好的解决方案,然后我发现了这篇文章:
http://gojko.net/2009/09/30/ddd-and-relational-databases-the-value-object-dilemma/
这篇文章非常好地解释了为什么价值对象和数据库之间存在很多混淆。这里有一句话我特别喜欢:
Gojko Adzic给我们提供了三种保存我们的价值对象的替代方法。
这是我对如何解决这类问题的看法,以及我目前在实践领域驱动设计(DDD)时的做法。
如果您正在编辑某个需要添加和删除标签的内容,比如一个帖子,那么标签可能是实体(entities),但也可以作为值对象(value objects)一起加载和保存。我个人倾向于使用值对象,除非需要修改该对象,但我也意识到实体对象建模为只读的“快照”与没有身份标识的实际值对象之间存在区别。棘手的部分在于,有时您通常认为是键的东西可能是值对象的一部分,只要在该上下文中不被用作身份标识,而我认为标签属于这个范畴。
如果您正在编辑标签本身,则可能是一个单独的有界上下文(bounded context),或者至少是一个单独的聚合(aggregate),其中标签本身是聚合根,并通过仓储(repository)进行持久化。请注意,在这个上下文中代表标签的实体类不必与用于帖子聚合的标签实体类相同。
如果您要在显示上列出可用的标签,仅供只读目的,例如提供选择列表,那么这可能是一个值对象列表。这些值对象可以放在领域模型中,但主要是为了支持用户界面而不是实际的领域。
如果有人认为我的想法是错误的,请随时发表意见,但这是我一直以来的做法。