我知道存根验证状态,模拟验证行为。
如何在 PHPUnit 中进行模拟以验证方法的行为? Phpunit没有验证方法(verify()),而且我不知道如何使moks成为 PHPUnit 。
在文档中,为了创建存根,可以很好地解释:
// Create a stub for the SomeClass class.
$stub = $this->createMock(SomeClass::class);
// Configure the stub.
$stub
->method('doSomething')
->willReturn('foo');
// Calling $stub->doSomething() will now return 'foo'.
$this->assertEquals('foo', $stub->doSomething());
但在这种情况下,我正在验证状态,并说回复。
如何创建模拟和验证行为的示例?
答案 0 :(得分:33)
PHPUnit支持两种创建测试双精度的方法。在传统的PHPUnit模拟框架旁边,它现在支持开箱即用的预言。
createMock
方法用于创建三个主要已知的测试双打。这是配置对象的方式,使其成为虚拟,存根或模拟。
您还可以使用模拟构建器创建测试存根(getMockBuilder
返回模拟构建器)。这只是做同样事情的另一种方式,它允许你使用流畅的界面调整一些额外的模拟选项(更多信息见the documentation)。
Dummy被传递,但从未实际调用过,或者如果它被调用,它会以默认答案(大多数是null
)进行响应。它主要用于满足一系列参数。
$dummy = $this->createMock(SomeClass::class);
// SUT - System Under Test
$sut->action($dummy);
Stubs与查询类似的方法一起使用 - 返回事物的方法,但如果它们实际被调用则不重要。
$stub = $this->createMock(SomeClass::class);
$stub->method('getSomething')
->willReturn('foo');
$sut->action($stub);
模拟与命令类似的方法一起使用 - 调用它们很重要,我们不关心它们的返回值(命令方法通常不会返回任何值)。
$mock = $this->createMock(SomeClass::class);
$mock->expects($this->once())
->method('doSomething')
->with('bar');
$sut->action($mock);
在测试方法执行完毕后,将自动验证期望值。在上面的示例中,如果未在doSomething
上调用方法SomeClass
,或者调用的参数与您配置的参数不同,则测试将失败。
不支持。
PHPUnit现在支持Prophecy开箱即用,因此您可以将其用作传统模拟框架的替代方案。同样,它是您配置对象的方式,使其成为测试双精度的特定类型。
$dummy = $this->prophesize(SomeClass::class);
$sut->action($dummy->reveal());
$stub = $this->prophesize(SomeClass::class);
$stub->getSomething()->willReturn('foo');
$sut->action($stub->reveal());
$mock = $this->prophesize(SomeClass::class);
$mock->doSomething('bar')->shouldBeCalled();
$sut->action($mock->reveal());
$spy = $this->prophesize(SomeClass::class);
// execute the action on system under test
$sut->action($spy->reveal());
// verify expectations after
$spy->doSomething('bar')->shouldHaveBeenCalled();
答案 1 :(得分:0)
假人
首先,看看假人。如果您要求我记住我离开车钥匙的位置,则虚拟对象既是我的外观...也是在phpspec中添加带有类型提示的参数以获取测试双倍值时得到的对象...然后绝对不做任何事情。因此,如果我们得到一个双重测试,并且不添加任何行为,也不对其方法进行断言,则称为“虚拟对象”。
哦,在他们的文档中,您会看到类似$ prophecy-> reveal()的信息。这是我们无需担心的细节,因为phpspec会为我们处理这些细节。得分!
存根
一旦您开始控制一种方法的一种返回值,就可以了!此对象突然称为存根。在文档中:“存根是对象双精度型”-所有这些都称为测试双精度型或对象双精度型-当放在特定环境中时,它们会以特定方式表现。这是一种花哨的说法:一旦我们添加了其中的willReturn()一件事,它就会变成一个存根。
实际上,大多数文档都花在谈论存根以及精确控制其行为的不同方法,包括我们前面看到的Argument通配符。
模拟
如果继续读下去,下一个发现的是“ mo子”。当您调用shouldBeCalled()时,对象将成为模拟对象。因此,如果您想添加一个方法被调用一定次数的断言,并且想将该断言放在实际代码之前-使用shouldBeCalledTimes()或shouldBeCalled()-恭喜!您的对象现在称为模拟对象。
间谍
最后,在底部,我们有间谍。间谍与模拟完全一样,只是在代码后添加期望值(例如,shouldHaveBeenCalledTimes()一样)。
https://symfonycasts.com/screencast/phpspec/doubles-dummies-mocks-spies