繁体   English   中英

将实体添加到DDD中的聚合根的正确方法

[英]Proper way to add an entity to an aggregate root in DDD

我有一个称为Order的聚合根,我需要在Order添加一个Product

public class Order {
  public void AddProduct(Product p) {
  }
}

我想问一下DDD准则。 我面临两个问题:

  1. Product具有两个属性,其中包括: Product.OrderIDProduct.Order DDD在调用 Order.AddProduct 之前应设置以下哪个属性?

  2. 还是我需要 Order.AddProduct设置这两个属性Order.AddProduct ,例如“ p.Order = this ”;

请注意,我以“ Order和“ Product ”为例。 有人告诉我这种关系可能不合适。 谢谢。

让聚合创建实体。 对于客户来说,这是最简单的解决方案,因为“创建”和“添加产品”没有分开。

public class Order 
{
   private readonly List<Product> _products = new List<Product>();

   public Product CreateProduct(string name, Price price) 
   {
      var product = new Product(new ProductId(), name, price);
      _products.Add(product);

      return product;
   }
}

请注意, CreateProduct的签名可能会根据您的需要而有所不同。 例如,在某些情况下,您将需要从客户端提供ID,而在其他情况下,订单将为产品生成ID。

注意:您可能应该具有Product和OrderItem或ProductOrderItem实体。 OrderItem是将添加到Order中的实体。 当您编辑产品时,OrderItems将不会被修改。

我建议使用工厂方法。 这里是一个例子:

public class Order {
    public Product addProduct(
        ProductId aProductId, 
        String aDescription 
    ) {
        Product product = new Product(
            this.orderId
            aProductId, 
            aDescription
        )

        //Publish event ProductWasAddedToOrder(this.orderId, aProductId) 

        return product;
    }
} 

然后,如果需要,可以让订户(观察员模式)侦听NewItemWa⚓ToOrder事件,例如,它可以显示添加到购物车中的项目或类似的内容。

更新 :我犯了一个大错误,因为我混淆了术语。 当我考虑产品时,我正在想象一个订单商品,它不存在,并且是在向订单中添加新元素时创建的,我认为这是最好的方法。

想象一下,在订单中保存了ProductId(对产品的引用),另一方面,订购该产品的客户为此支付了20欧元。 两个月后,系统管理员更改了同一产品的价格,由于您在订单中保存了对该产品的引用,因此如果您要查看当天客户支付的金额,则可以得到新的价格。 将产品保存在订单中,每当您修改产品时,您也在修改订单。

因此,我将向该订单添加一个新商品,其中包含该商品当时具有的特定信息。 该项目还应包含对产品的引用,以了解给定特定产品已创建了多少个项目。 这里的例子:

public class Order {
    public OrderItem addItem(
        OrderItemId anItemId, 
        ProductId aProductId, 
        Price aPrice, 
        String aDescription 
    ) {
        OrderItem orderItem = new OrderItem(
            anItemId, 
            this.orderId,
            aProductId,
            aDescription, 
            aPrice
        )

        //Publish event NewItemWasAddedToOrder(this.orderId, anItemId) 

        return orderItem;
    }
} 

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM