如何创建一个学说实体的模拟对象?

tom*_*tom 12 php phpunit unit-testing doctrine zend-framework

我正在尝试用phpunit编写一个使用doctrine 2的模型进行单元测试.我想模仿教条实体,但我真的不知道如何做到这一点.任何人都可以向我解释我需要这样做吗?我正在使用Zend Framework.

需要测试的模型

class Country extends App_Model
{
    public function findById($id)
    {
        try {
            return $this->_em->find('Entities\Country', $id);
        } catch (\Doctrine\ORM\ORMException $e) {
            return NULL;
        }
    }

    public function findByIso($iso)
    {
        try {
            return $this->_em->getRepository('Entities\Country')->findOneByIso($iso);
        } catch (\Doctrine\ORM\ORMException $e) {
            return NULL;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

bootstrap.php中

protected function _initDoctrine()
{
    Some configuration of doctrine
    ... 
    // Create EntityManager
    $em = EntityManager::create($connectionOptions, $dcConf);
    Zend_Registry::set('EntityManager', $em);
}
Run Code Online (Sandbox Code Playgroud)

扩展模型

class App_Model
{
    // Doctrine 2.0 entity manager
    protected $_em;

    public function __construct()
    {
        $this->_em = Zend_Registry::get('EntityManager');
    }
}
Run Code Online (Sandbox Code Playgroud)

Jrg*_*gns 15

我有使用Doctrine的单元测试的以下setUp和tearDown函数.它使您能够在没有实际接触数据库的情况下进行学说调用:

public function setUp()
{
    $this->em = $this->getMock('EntityManager', array('persist', 'flush'));
    $this->em
        ->expects($this->any())
        ->method('persist')
        ->will($this->returnValue(true));
    $this->em
        ->expects($this->any())
        ->method('flush')
        ->will($this->returnValue(true));
    $this->doctrine = $this->getMock('Doctrine', array('getEntityManager'));
    $this->doctrine
        ->expects($this->any())
        ->method('getEntityManager')
        ->will($this->returnValue($this->em));
}

public function tearDown()
{
    $this->doctrine = null;
    $this->em       = null;
}
Run Code Online (Sandbox Code Playgroud)

然后,您可以在需要时使用$this->doctrine(或甚至)$this->em.如果要使用remove或需要添加更多方法定义,则需要添加更多方法定义getRepository.

  • 这是创建一个新的EntityManager对象,它只知道如何在测试类中保持和刷新.我相信OP要求的是模拟方法持久化并刷新其ServiceManager中已存在的对象.所以他的服务代码包含persist()和flush(),当它只是一个测试时它触及数据库. (2认同)

Bry*_* M. 8

学说2实体应该像任何旧班一样对待.您可以像PHPUnit中的任何其他对象一样模拟它们.

$mockCountry = $this->getMock('Country');
Run Code Online (Sandbox Code Playgroud)

从PHPUnit 5.4开始,方法getMock()已被删除.请改用createMock()或getMockbuilder().

正如@beberlei所指出的那样,你在Entity类中使用了EntityManager,这会产生许多棘手问题,并且会破坏Doctrine 2的主要目的之一,即Entity并不关心它们自身的持久性.那些'find'方法确实属于一个存储库类.