2010-12-01 257 views
7

我试图让我的手脏学习DDD(通过开发一个样本电子商务网站与实体,如OrderOrderLinesProductCategories等)。 从我能理解的聚合根概念我认为Order类应该是OrderLine的聚合根。DDD - 聚合根 - 示例订单和订单行

事情很顺利,但是我很困惑,它定义了从UI创建订单流。 当我想以一个订单行添加到我的订单对象,我应该怎么弄/创建一个OrderLine对象的实例:

  1. 我应该硬编码的新OrderLine()声明,我的UI /服务类
  2. 是否应我在Order类中定义了一个类似productID,quantity等参数的方法?

另外,如果我想使用DI去除UI或Order类中的硬编码实例,该怎么办。对此最好的方法是什么?

回答

2

从我能感知到约 聚合根概念,我想订购 类应该是一个aggreagrte根 订单行。

是的,OrderLine应该很可能在Order根下,因为OrderLine可能在父Order之外没有任何意义。

我应该硬编码在我的UI /服务类

可能不是新的订单行() 声明,尽管这往往是如何发生的,它是由工作。正如我所看到的那样,问题在于对象构造经常发生在不同的上下文中,并且验证约束根据上下文而不同。

我是否应该在Order类中定义一个包含 参数的方法,如productID,数量等 ?

如:

public OrderLine AddOrderLine(Product product, int Quantity ...) 

这是做这件事。注意我使用了Product类而不是ProductId。有时候一个比另一个更好。我发现我出于各种原因而使用了很多 - 有时候我有这个ID,并且没有很好的理由来拉取聚合根,有时我需要另一个根来验证操作。

我这样做的另一种方法是为孩子实现一个自定义集合。

所以我必须:

order.OrderLines.Add(product, quantity); 

这感觉多了几分自然的或面向对象,特别是如果实体根有它避免了杂波很多孩子集合。

order.AddOrderLine()order.AddXXX()order.AddYYY()order.AddZZZ()

order.OrderLines.Add()order.ZZZs.Add()order.YYYs.Add()

而且,如果我想从UI 删除 硬编码实例或Order类使用DI。什么 将是最好的办法呢?

这将是工厂模式的教科书案例。我将这样一个工厂注入到我的自定义集合中,以支持那些Add()方法中的实例化。

+1

我不认为order.OrderLines.Add是更多的面向对象。有一个OO东西叫封装。如果你的班上有很多XXX,ZZZ,YYY,它可以重新设计它(好的OO设计往往有许多小物体)。你可以谷歌封装集合的好处,避免火车残骸(流畅的接口是另一种情况)。 – 2011-11-29 11:57:39

2

您可以使用OrderLine Factory来获取Orderlines的实例。您将使用传入工厂方法的参数“新建”工厂中的OrderLine对象,然后将新实例返回给Order对象。总是尝试隔离实例化,而不要在UI中执行。有一个问题here使用这种技术。

这是一本很棒的书,你可以在DDD找到有用的书。