PHP/Doctrine2 - 实现一个接口两次


PHP/Doctrine2 - Implement an interface twice

这可能是一个愚蠢的问题。我正在尝试为 Doctrine 2 创建一个通用存储库接口,以便我可以通过直接注入将其传递到我的控制器中:

//TestController.php
public function __construct(TestRepositoryInterface $p_repository){
    //...
}

Doctrine2 中 EntityRepository 的方法签名如下:

class EntityRepository implements ObjectRepository, Selectable{
    //...
}

EntityRepository缺少一些我想在存储库中使用的功能(添加、删除、更新)。因此,我创建了一个基本存储库接口和一个抽象存储库类来封装这些功能:

interface RepositoryInterface {
    public function add($entity);
    public function delete($entity);
    public function update($entity);
}

抽象存储库类从EntityRepository扩展,所以我仍然可以获得EntityRepository的功能。

abstract class AbstractRepository extends EntityRepository{
    public function add($entity){
        //...
    }
    public function add($entity){
        //...
    }
    public function add($entity){
        //...
    }
}

为了将所有内容联系在一起,我做了TestRepositoryInterfaceRepositoryInterfaceObjectRepositorySelectable延伸。

interface TestRepositoryInterface extends RepositoryInterface, ObjectRepository, Selectable{
}

然后我可以通过直接注入传入TestRepositoryInterface的实现:

class TestImplementation extends AbstractRepository implements TestRepositoryInterface{
    //...
}

或者,如果我是单元测试,则很容易创建模拟对象或测试存根。

我唯一关心的是TestImplementation课。它扩展了已经实现ObjectRepositorySelectable(通过EntityRepositoryAbstractRepository,同时TestImplementation还实现了也扩展ObjectRepositorySelectableTestRepositoryInterface。因此,TestImplementation本质上是实施两次ObjectRepositorySelectable(或者它?它编译得很好,但这是一种有效的方法吗?

一个类实现多个接口是完全可以的,这些接口反过来扩展了公共接口。 方法相同,因此没有冲突。

您唯一需要担心的是实现具有相同命名方法但替代参数的接口。

假设你有一个接口,其实现需要迭代。 您可能会让它实现'IteratorAggregate.

现在假设您的实现类扩展ArrayCollection(从 doctrine common)。 因为ArrayCollection也实现了IteratorAggregate所以它会为你处理你自己的一些接口的定义。

在混合接口时,请寻找兼容性问题而不是继承问题。