DDD:域模型命名空间约定

Ben*_*min 10 php domain-driven-design namespaces naming-conventions namespace-organisation

我正在用PHP编写一个域模型的应用程序,我想知道我应该采用哪种命名约定.

假设我有一个Customer,Address在其根集合中有一个.
我也有一个Product,Option在其聚合根中.

我有两个选择:

  1. 将聚合根保留在域模型的根目录中:

    Customer
    Customer\Address
    Product
    Product\Option
    
    Run Code Online (Sandbox Code Playgroud)

    :我可以同时使用Customer,并Product在同一个命名空间
    精读:Customer有引用自己Address作为Customer\Address

  2. 将所有聚合类分组到同一名称空间中,包括聚合根:

    Customer\Customer
    Customer\Address
    Product\Product
    Product\Option
    
    Run Code Online (Sandbox Code Playgroud)

    Pro:Customer可以将其地址引用为Address
    Con:从我的根域名称空间,我必须参考:

    • CustomerCustomer\Customer
    • ProductProduct\Product

Alf*_*wed 5

我刚才写了一个小框架,我选择使用你提出的第一个解决方案.

将聚合根保留在域模型的根目录中:

为什么?

实际上我问自己今天要问的同一个问题,在与我的队友讨论之后,我们同意不重复命名空间中的类名更合乎逻辑.


让我们看看如何用解决方案n°2实现你的类

Customer\Customer
Customer\Address
Run Code Online (Sandbox Code Playgroud)

你必须写:

$customer = new Customer\Customer();
$address = new Customer\Address();
Run Code Online (Sandbox Code Playgroud)

你能看到重复吗?对我来说这种感觉并不合适.在我看来,这就像写作

$customer->getCustomerId();
Run Code Online (Sandbox Code Playgroud)

为什么在方法名称中重复使用Customer?我们知道这是客户的ID,因为我们使用的是Customer对象.

这个模型的另一个"坏事"是不可能使用保留关键字作为类名.

例如,使用pear约定你可以拥有该类

Customer_Abstract
Run Code Online (Sandbox Code Playgroud)

位于Customer/Abstract.php,这对我很好,但如果你尝试使用命名空间翻译它,你将拥有

namespace Customer;

class Abstract {}
Run Code Online (Sandbox Code Playgroud)

这会导致致命错误.因此,您将不得不在类名中重复该域:

namespace Customer;

class AbstractCustomer {}

$customer = new Customer\AbstractCustomer();
Run Code Online (Sandbox Code Playgroud)

现在让我们看看如何使用解决方案1来实现您的类

Customer
Customer\Address
Run Code Online (Sandbox Code Playgroud)

你会写:

$customer = new Customer();
$address = new Customer\Address();
Run Code Online (Sandbox Code Playgroud)

我们不必再重复客户两次以实现Customer类.但是,地址仍然与客户有关.

这就是我选择使用这个模型的原因.

编辑:Zend Framework 2也使用此约定