检查mock类中的嵌套数组结构

时间:2013-03-07 18:03:09

标签: mocking phpunit multidimensional-array

我写了一个基本上看起来像这样的方法:

public function collectData($input, FooInterface $foo) {
   $data = array();
   $data['products']['name'] = $this->some_method();
   if(empty($input['bar'])) {
       $data['products']['type'] = "Baz";
   }
   // hundreds of calls later
   $foo->persist($data);
}

现在,我想对collectData方法进行单元测试,以检查$data中的值是否为某些输入设置。对于对象参数,我通常使用这样的模拟:

$mock = $this->getMock('FooInterface');
$mock->expects($this->once())
             ->method('persist')
             ->with($this->identicalTo($expectedObject));

但是我如何测试某些嵌套数组键(例如,如果$data['products']['prices']['taxgroup']为1),忽略可能在数组中的所有其他键? PHPUnit或Mockery是否提供此类检查?或者他们可以轻松扩展以提供这样的支票吗?

或者我现在正在做的事情更好:创建我自己的FooClassMock类来实现FooInterface并只将数据存储在persist调用中?

2 个答案:

答案 0 :(得分:1)

事实证明,有一种方法 - 我可以创建自己的constraint class。之后,很容易:

$constraint = new NestedArrayConstraint(
    array('products', 'prices', 'taxgroup'),
    $this->equalTo(1)
);
$mock = $this->getMock('FooInterface', array('persist'));
$mock->expects($this->once())
             ->method('persist')
             ->with($constraint);

答案 1 :(得分:1)

您还有一个选项,但仅当您使用PHPUnit> = 3.7时。有一个回调断言,您可以像这样使用它:

$mock = $this->getMock('FooInterface', array('persist');
$mock->expects($this->once())
         ->method('persist')
         ->with($this->callback(function($object) {
             // here you can do your own complex assertions

             return true|false;
         }));

以下是更多详情:

https://github.com/sebastianbergmann/phpunit/pull/206