@antodippo
Shercode Holmes
Test coverage is a measure used to describe the degree to which the source code of a program is executed when a particular test suite runs
class NuclearReactor
{
public function isDangerous(int $temperature): bool
{
if ($temperature >= 1000) {
return true;
} else {
return false;
}
}
}
class NuclearReactorTest extends TestCase
{
public function testIsDangerous(): void
{
$nuclearReactor = new NuclearReactor();
$this->assertFalse($nuclearReactor->isDangerous(500));
$this->assertTrue($nuclearReactor->isDangerous(2000));
}
}
from
"Tests Coverage is Dead" by Yotam Kadishay
class NuclearReactor
{
public function isDangerous(int $temperature): bool
{
if ($temperature > 1000) {
return true;
} else {
return false;
}
}
}
class NuclearReactorTest extends TestCase
{
public function testIsDangerous(): void
{
$nuclearReactor = new NuclearReactor();
$this->assertFalse($nuclearReactor->isDangerous(500));
$this->assertTrue($nuclearReactor->isDangerous(2000));
}
}
from
"Tests Coverage is Dead" by Yotam Kadishay
Cyclomatic complexity is a quantitative measure of the number of linearly independent paths through a program's source code
\begin{align} C.R.A.P. &= comp(m)^2 ยท (1 - \frac{cov(m)}{100})^3 + comp(m) \end{align}
from "Pardon My French, But This Code Is C.R.A.P." by Alberto SavoiaNot all the units of codeare equally important
Churn is a metric representinghow often a unit of code is modified (ex. number of commits)from "Getting Empirical about Refactoring" by Michael Feathers
Better, but it's still about coverage, not the quality of the tests
Mutation testing
class NuclearReactor
{
public function isDangerous(int $temperature): bool
{
if ($temperature >= 1000) {
return true;
} else {
return false;
}
}
}
class NuclearReactor
{
public function isDangerous(int $temperature): bool
{
if ($temperature > 1000) {
return true;
} else {
return false;
}
}
}
... is risky, so I won't do it
class NuclearReactorTest extends TestCase
{
public function testIsDangerous(): void
{
$nuclearReactor = new NuclearReactor();
$this->assertFalse($nuclearReactor->isDangerous(500));
$this->assertTrue($nuclearReactor->isDangerous(2000));
}
}
https://github.com/antodippo/php-testing-playground
class NuclearReactorTest extends TestCase
{
public function testIsDangerous(): void
{
$nuclearReactor = new NuclearReactor();
$this->assertFalse($nuclearReactor->isDangerous(500));
$this->assertTrue($nuclearReactor->isDangerous(1000));
$this->assertTrue($nuclearReactor->isDangerous(2000));
}
}
https://github.com/antodippo/php-testing-playground
PROS
|
CONS
|
To assess the effectivness of a testsuite!
Setting a minimum MSI in pipeline
While developing, on a small scope
CHANGED_FILES=$(git diff origin/master --diff-filter=AM --name-only | grep src/ | paste -sd "," -);
INFECTION_FILTER="--filter=${CHANGED_FILES} --ignore-msi-with-no-mutations";
infection --threads=4 $INFECTION_FILTER
https://infection.github.io/guide/how-to.html
Ok, I have the tools, now what?
Ship frequently
Monitor
Take educated risks!
Learn from failures
Reduces cost of change
Enables agility: ship and learn
Short feedback loop