我创建了下面的例子测试用例:如何嘲笑在PHP中静态声明的方法时,单元测试
<?php
abstract class Model
{
//...
public static function factory($data)
{
$className = get_called_class();
$obj = new $className($data);
return $obj;
}
}
class User extends Model
{
}
class ExampleController
{
protected $user;
public function __construct(User $user)
{
$this->user = $user;
}
public function create()
{
return $this->user->factory(array('name' => 'Jim'));
}
}
class ExampleTest extends PHPUnit_Framework_TestCase
{
public function testSomething()
{
$user = new User(array('name' => 'Jim'));
$modelStub = $this->getMockBuilder('User')
->disableOriginalConstructor()
->getMock();
$modelStub
->method('factory')
->with(array('name' => 'Jim'))
->willReturn($user);
$example = new ExampleController($modelStub);
$this->assertEquals($user, $example->create());
}
}
不过,我得到以下错误:
1) ExampleTest::testSomething
PHPUnit_Framework_MockObject_BadMethodCallException:
我似乎好工作,当我删除static
关键字,然后我的测试通过。但我想我的模型类中,也允许,在其他情况下,可以选择调用某些方法,而无需先实例:
// when instantiation is required
$userModel = new User();
$user = $userModel->factory(array('name' => 'Jim'));
// called statically, no initial instantiation required
$user = User::factory(array('name' => 'Jim'));
我碰到这个博客里面说的方法静态声明,但动态地叫出来,是好。然而,方法动态申报,但静态调用,将引发严格的错误 - http://www.lornajane.net/posts/2010/declaring-static-methods-in-php
我也用Laravel雄辩之前,看来,这两种方法调用可能有:
// Eloquent example without initial instantiation is possible too
$user = User::find(1);
无论如何,不管无论我的代码是否工作,我希望能够模拟静态声明这些方法。读起来似乎PHPUnit并没有很好地处理静态方法(我读过那里有一个staticExpects方法,但现在不推荐使用PHPUnit 3.8)。所以我即将开始尝试一些其他的测试框架(Codeception和AspectMock,PHPSpec,嘲笑),因为我没有太多的经验与其他人。真的很感谢这个问题的一些建议或者对这个问题的建议,因为在我们公司对遗留应用程序进行单元测试真的有帮助,谢谢
没有工具可以模拟静态方法。尽可能避免静态方法的另一个原因。 –
您正在将该方法声明为static,但将其称为类方法:'return $ this-> user-> factory(array('name'=>'Jim'));' – hek2mgl