gpt4 book ai didi

entity - DDD 聚合 : Entity holding identifier to Non-Root Entity in another Aggregate

转载 作者:行者123 更新时间:2023-12-01 23:03:27 27 4
gpt4 key购买 nike

我试图了解实体和聚合之间关系的最佳实践。

想象一个设计,其中有一个 产品汇总 , 由两个实体组成:

聚合根:产品

子实体:Sku

一个产品可以有很多 Sku 的地方。 Skus 和产品的部件号和名称是不变的,因为更改一个名称必须在事务上确保另一个更新。同样,产品聚合需要确保永远不会有重复的 Sku。

我们还有一个 聚合:StorageLocation .存储 1 个或多个 Sku 的位置。然而,重要的是 StorageLocation 知道它正在存储的特定 Sku。 IE。加拿大的 StorageLocation 应存储该国家/地区本地的 Sku,而不是用于美国市场的 Sku。

这对我来说意味着 StorageLocation 需要保留对 Sku 的引用(因为对 Product Aggregate Root 的引用本身并不能提供足够的信息来确定被存储的 Sku)。

从我的阅读来看,这似乎打破了另一个聚合不应该在另一个聚合中持有对非根实体的引用的原则。所以问题:

  • 在 StorageLocation 聚合中只持有 Product 和 Sku 的标识符是否可以接受?
  • 我知道暂时引用被认为是允许的,但在这种情况下(至少据我所知)需要存储此信息。如前所述,仅存储对 Product(或 ProductId)的引用是不够的。
  • 产品和 Sku 具有自然标识符(部件号、Sku 编号)。这是否为将这些值存储在 StorageLocation 聚合中提供了更大的灵活性,因为它们的意义超出了技术含义。
  • 我是否以错误的方式处理这个问题,需要以不同的方式看待事情。我经常发现很难打破 PK/FK 的心态。

  • 谢谢

    最佳答案

    不存储对子实体的引用的指导是建立在良好的原则之上的,但我相信经常会引起混淆。目标实际上是子实体不一定具有“全局唯一”标识符,并且没有存储库使用这种全局唯一标识符直接访问子实体。

    但是,如果您的 StorageLocation持有 Product 的全局唯一标识符,以及 SKU 可能的本地唯一标识符,那么模式没有任何问题,例如:

    var storageLocation = _storageLocationRepository.Get(id);
    var product = _productRepository.Get(storageLocation.ProductId);
    product.DoSomethingToSku(storageLocation.SkuId);

    关键是通过确保您始终从存储库获取产品,然后通过产品与子实体交互,您可以确保产品有机会保护其自身的不变量。

    所以总结一下:
  • 随意将标识符存储到子实体,只要您还为其聚合根存储全局标识符。
  • 在这种情况下,子实体 id 可能是本地唯一的或全局唯一的 - 只要对子实体的访问是通过聚合根就可以了。
  • 永远不要直接从存储库加载子实体并在其上调用方法 - 因为聚合根没有机会保护其不变量。
  • 事实上,你甚至不应该拥有子实体的存储库
  • 关于entity - DDD 聚合 : Entity holding identifier to Non-Root Entity in another Aggregate,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49201418/

    27 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com