php中DDD的实体构造函数是什么样的?

What does an entity's constructor look like for DDD in php?

我对使用ddd函数的PHP中的构造函数的外观感到困惑。这就是我目前为止所拥有的:

实体

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
class People {

    // Fields
    private $id;
    private $first_name;      // required
    private $middle_name;
    private $last_name;       // required
    private $phone;           // required (or mobile_phone required)
    private $mobile_phone;
    private $email;           // required
    private $alt_email;
    private $something_else;  // required

    public function __construct($fields){

        // Set some properties
        $this->setFromArray($fields);

        // Don't instantiate a new entity object in an invalid state
        // (ie. determines if required fields are given)
        if(!$this->isValid()){  
            throw new Exception("Can't create person");
        }
    }

    // some getters and setters...

    // some other domain methods so entity is not anemic
    ...

存储库

1
2
3
4
5
6
7
8
9
class PeopleRepository {   // <-- Should probably be an interface

    public function get($id){
       ...
    }

    public function save(People $people){
        // Will INSERT or UPDATE based on if an ID is set in $people
    }

简单的例子

1
2
3
4
// a very very simple example
$peopleRepo = new PeopleRepository();
$people = new People($_POST);
$peopleRepo->save($people);

我不想使用任何ORM。在DDD中,我这样做的方式是否是实体构造函数的正确方法?请在PHP中解释并给出实体构造函数在DDD中的外观示例(我很难找到好的示例)。


在构造函数上传递值数组不是一个好主意。如果数组中不存在所需的数据。您的域实体将处于无效状态。

只需将所需字段单独放在构造函数上,这样它就更可读,而且所需字段是显式的。如果您忘记提供所需的数据,那么您将遇到一个错误,这是大多数好的IDE所支持的。

1
__construct($firstName, $lastName, $phone, $email) { }

您可能还需要考虑使用ValueObject对相关数据进行分组,以缩小构造函数的范围。有关ValueObjects的详细信息,请访问此链接。

http://richardmiller.co.uk/2014/11/06/value-objects/

以你的名字为例。将它们封装在ValueObject FullName

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
final class FullName
{
    private $firstName;
    private $middleName;
    private $lastName;

    public function __construct($firstName, $lastName, $middleName = null)
    {
        $this->firstName = $firstName;
        $this->lastName = $lastName;
        $this->middleName = $middleName;
    }

    // getters method ONLY
    // you need to instantiate new FullName if you want to change the fields
}

然后您可以将它传递给EDOCX1的构造函数。

1
__construct(FullName $fullName, $phone, $email) { }

如果您真的有巨大的构造函数,您可以考虑构建器模式。

有多少构造函数参数太多?