我目前正面临处理聚合中实体之间关联的问题。
请考虑以下示例:
现在,我们有一个用户“实体,这也是我的聚合根。他可以只有一个,产品”与他相关,还有很多,别名“。我现在需要的是能力在域模型中按需检索相关的,“产品”和“别名”。用户由UserFactory创建,可以单独使用,也可以在持久性数据中创建实体时在UserRepository中使用。
<?php
class User {
private $id;
private $aliases;
private $product;
public function isEligibleForCompanyPromotion() {
//I need a good way to populate this without a performance bottleneck.
$product = $this->product;
[.. code comparing things between User and Product begins ..]
}
}
之所以这样,是因为我们的业务逻辑(正如你在例子中看到的)很大程度上依赖于对象之间的关联,我想这个与对象之间的关联相关的逻辑应该在域模型中完成(或者这应该是搬出去了?)
我考虑过以下解决方案:
1)只需在构建用户时加载所有内容(关联的产品和别名)。
优点:
缺点:
2)将关系存储库注入域模型
private $productRepository;
private $aliasesRepository;
[...]
}
优点:
缺点:
3)将与关联相关的逻辑委托给域模型(可能是域服务和策略?)
优点:
缺点:
4)创建一个专门的Relationship对象来处理关系:
<?php
class UserFactory {
private $relationshipFactory;
public function createUser($persistenceData) {
$user = new User();
[.. creating of User, populating data etc .. ]
$user->product = $this->relationshipFactory->createUserProductRelationship($user);
}
}
class UserProductRelationship {
private $user;
private $product;
private $productRepository;
[.. productRepository is being injected within relationshipFactory, and user is provided ..]
public function loadProduct() {
[.. load the product based on the relationship criterias ..]
}
[.. calls to this object are proxied to lazy-loaded product via __call, __get etc. )
}
优点:
缺点:
也许我不理解某事。如果有人有任何建议,我会很高兴听到它。
谢谢!
答案 0 :(得分:1)
如果某些责任不属于任何对象,或者域对象需要太多不相关的数据来解决问题,请引入规范对象。
您需要的是EligibleForCompanyPromotionSpecification,如:
class EligibleForCompanyPromotion {
private $productRepository;
private $aliasesRepository;
public function isSatisfiedBy(User user) {
//I need a good way to populate this without a performance bottleneck.
$product = $productRepository.find(user.productId);
[.. code comparing things between User and Product begins ..]
}
class User {
private $id;
private $aliasesId;//only identifiers needed
private $productId;//only identifiers needed
在这种情况下,域逻辑不会泄漏到应用程序层,我们不必将存储库注入用户。