Domain driven design 聚合根问题

Domain driven design 聚合根问题,domain-driven-design,aggregateroot,Domain Driven Design,Aggregateroot,假设我有两个实体-Foo和Bar。Foo是一个聚合根,包含Bar。据我了解,应该是这样的: public class Foo{ private readonly Bar Bar; } 我想为用户提供从定义的列表中为Foos选择条的功能(并对其进行更改) 若存储库应该只用于聚合根,那个就意味着Bar实体将并没有存储库 这就导致了问题-如果不引用Foo,就无法独立创建/更新工具栏 这是否意味着Bar应该有一个存储库,尽管没有Foo它没有任何意义?您确定Bar需要是一个实体吗?您是否需要在域

假设我有两个实体-Foo和Bar。Foo是一个聚合根,包含Bar。据我了解,应该是这样的:

public class Foo{
    private readonly Bar Bar;
}
我想为用户提供从定义的列表中为Foos选择条的功能(并对其进行更改)

若存储库应该只用于聚合根,那个就意味着Bar实体将并没有存储库

这就导致了问题-如果不引用Foo,就无法独立创建/更新工具栏


这是否意味着Bar应该有一个存储库,尽管没有Foo它没有任何意义?

您确定Bar需要是一个实体吗?您是否需要在域中跟踪和更改它?如果可以将其视为值对象,我建议您从服务获取它,然后将所选值对象“连接”到Foo实体。对于下拉列表中的实例。

如果要从与Foo无关的条列表中进行选择,则这不是聚合根。例如,您无法获取没有订单的OrderItems列表,因此这是单个聚合根(Order),但您可以获取要分配给OrderItems的产品列表,因此产品不属于订单聚合根

请注意,虽然OrderItem是Order聚合根目录的一部分,但您仍然可以独立创建和更新它。但是,如果不考虑订单,就无法得到它。对于您的工具栏也是如此,即使它是Foo的一部分,您也可以获取每个(Foo.Bar)并使用它,或者执行Foo.AddBar(new Bar())。但如果您需要在不使用Foo的情况下获取列表,则Bar不是Foo聚合的一部分。它是一个独立的实体


好吧,这就是我对DDD的看法,但我当然不是Eric Evans。

拥有聚合根的原因是:

  • 它们提供对复合实体的受控和定向访问
  • 他们可以强制执行规则以确保整个聚合是有效的
  • 我的目标: 如果需要选择没有
    Foo
    Bar
    对象,请使用
    BarRepository

    但是… 如果您更新一个
    ,并且它破坏了其父
    Foo
    的验证规则,该怎么办?如果发生这种情况,您应该通过它的父级
    Foo
    访问
    Bar

    但是,如果您需要访问一组
    Bar
    对象(例如批处理作业或报告),并且您知道
    Foos
    不会被破坏,请继续通过
    BarRepository
    访问它们


    请记住,聚合根可以由其他聚合根组成。您可能会发现,
    Bar
    本身就是一个聚合根,这就为
    BarRepository
    :)

    提供了理由,以及为什么不能通过服务获取实体并连接到Foo?在没有实体上下文的情况下,如何创建/更新价值对象?这难道不是将服务掩蔽为存储库,而价值对象不应该拥有它吗?让我解释一下我是如何做到这一点的;我需要一种从持久层获取数据的方法。我可以使用DTO来获取数据,但我更愿意使用value对象,因为这样我就可以在域中使用该对象,而无需从DTO映射到value对象。我使用的对象是聚合根中的一个类,在您的案例栏中。如果我对一个实体这样做,我想我会使用DTO(通过服务获取)来填充列表(组合框等),当我选择了正确的栏时,我会要求存储库从聚合根中获取完整的对象。希望这是有意义的。我想知道这个解决方案是否可以应用于我提出的关于验证和基于数据选择默认值的问题,否则这些数据是聚合外部的。这是有道理的。如果你还有什么要说的,就说吧。:)我学到的东西——在我的领域里有太多的聚合根。有一些实体作为根创建,尽管它们不应该单独更新。更糟糕的是,有些根可以被替换为值对象。我想到的另一个建议是,如果你的条是独立的(可以作为单独的列表显示)和依赖的(在Foo内部工作),那么这里可能实际上有两个实体。一个简短的例子:组{Name,Price}-应该在订单/产品中,并分别显示,但如果将其拆分为组{Name}和产品组{Group,Price},则分别显示组,同时将产品组作为聚合的一部分。@queen3;我相信我理解你的观点,但你能为我澄清一些事情吗。使用另一个例子…客户是一个拥有国家的根。为了设置国家,您需要从国家列表中进行选择…这样,国家也成为一个独立的根…正确吗?好吧,我想说,这使国家成为一个单独的实体。如果它包含其他实体(例如区域),则它将是聚合根。如果我正确理解“聚合根”和“实体”是不同的野兽;-)但它绝对不是客户聚合根的一部分。嗯,在某些情况下,它可能是客户的一部分。。。e、 在用户创建自己国家的虚拟世界游戏中,一个国家可能是“玩家世界”的一部分。但我想这不是你的情况。没有愚蠢的问题,只有愚蠢的答案;)顺便说一句,这个问题对我帮助很大