这是否有意义:
由于我们通常只想测试API(类)而不是实现细节,所以我们通常不需要/想要测试受保护的方法。由于我们不希望代码覆盖率因为我们不测试实现细节而丢弃,因此我们应该对这些受保护的方法使用@codeCoverageIgnore
注释。
答案 0 :(得分:6)
通过公共API测试您的私有和受保护的方法。
规则“不测试您的私有”并不意味着您不应该测试私有方法提供的行为。这意味着您应该通过公共方法测试该行为。如果这样做,您将获得以后更改实现的灵活性(即创建不同的私有方法,或者内联它们)。
显然,您将为您正在测试的单个方法编写多个测试用例。确保将这些方法命名为清楚地说明您的期望。例如:
test_it_reverses_the_name()
test_it_lowercases_characters_in_the_reversed_name()
test_it_throws_an_exception_if_name_is_missing()
请注意,如果您正在测试驾驶公共方法,则通常不会创建私有方法。您宁可将它们作为重构步骤提取出来。稍后您可能还决定在不需要更改测试的情况下内联这些方法。那是因为你只测试了公共行为。
无需使用@codeCoverageIgnore
或@covers
。你会骗自己。
示例强>
Foo.php
:
<?php
class Foo
{
private $name;
public function __construct($name)
{
$this->name = $name;
}
public function getReversedName()
{
$this->foo();
return strrev($this->name);
}
protected function foo()
{
$foo = true;
}
}
FooTest.php
:
<?php
class FooTest extends \PHPUnit_Framework_TestCase
{
public function test_it_reverses_the_name()
{
$foo = new Foo('test');
$this->assertSame('tset', $foo->getReversedName());
}
}
phpunit.xml.dist
:
<?xml version="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="http://schema.phpunit.de/4.1/phpunit.xsd"
backupGlobals="false"
colors="true"
bootstrap="vendor/autoload.php"
>
<php>
<ini name="error_reporting" value="-1" />
</php>
<testsuites>
<testsuite name="Project Test Suite">
<directory>tests</directory>
</testsuite>
</testsuites>
<logging>
<log type="coverage-html" target="build/coverage"/>
</logging>
</phpunit>
答案 1 :(得分:0)
如果一个测试涵盖多个类方法,则可以使用covers annotation as described in the doc here。例如:
/**
* @covers Foo::foo
* @covers Foo::bar
*/
public function testReversed()
{
$this->assertEquals(0, $this->foo->getReversedName());
}
希望这个帮助