TestCase
В простите тестове твърденията могат да следват едно след друго. Понякога обаче е полезно да се затворят твърденията в тестови клас и да се структурират по този начин.
Класът трябва да бъде потомък на Tester\TestCase
, а ние го наричаме
просто testcase.
use Tester\Assert;
class RectangleTest extends Tester\TestCase
{
public function testOne()
{
Assert::same(/* ... */);
}
public function testTwo()
{
Assert::match(/* ... */);
}
}
# Run testing methods
(new RectangleTest)->run();
Можем да обогатим тестовия пример с методите setUp()
и
tearDown()
. Те се извикват преди/след всеки метод за изпитване:
use Tester\Assert;
class NextTest extends Tester\TestCase
{
public function setUp()
{
# Preparation
}
public function tearDown()
{
# Clean-up
}
public function testOne()
{
Assert::same(/* ... */);
}
public function testTwo()
{
Assert::match(/* ... */);
}
}
# Run testing methods
(new NextTest)->run();
/*
Method Calls Order
------------------
setUp()
testOne()
tearDown()
setUp()
testTwo()
tearDown()
*/
Ако се появи грешка във фазата setUp()
или tearDown()
, тестът ще
се провали. Ако в тестовия метод възникне грешка, методът tearDown()
се извиква въпреки това, но с потиснати в него грешки.
Препоръчваме анотацията @testCase да се запише в началото на теста, след което програмата за стартиране на тестове от командния ред ще изпълнява отделните методи на тестовия случай в отделни процеси и паралелно в няколко нишки. Това може значително да ускори целия процес на тестване.
<?php
/** @testCase */
Анотиране на методи
Има няколко анотации, които ни помагат при тестването на методите. Записваме ги в посока на метода за изпитване.
@throws
Това е същото използване на Assert::exception()
в рамките на метод за
изпитване. Но обозначението е по-четивно:
/**
* @throws RuntimeException
*/
public function testOne()
{
// ...
}
/**
* @throws LogicException Грешен ред на аргументите
*/
public function testTwo()
{
// ...
}
@dataProvider
Тази анотация е подходяща, когато искаме да стартираме даден тестови метод многократно, но с различни аргументи. (Да не се бърка с анотацията на файла със същото име).
Като аргумент записваме името на метода, който връща параметрите на тестовия метод. Методът трябва да връща масив или Traversable. Един прост пример:
public function getLoopArgs()
{
return [
[1, 2, 3],
[4, 5, 6],
[7, 8, 9],
];
}
/**
* @dataProvider getLoopArgs
*/
public function testLoop($a, $b, $c)
{
// ...
}
Друга разновидност на анотацията @dataProvider приема като аргумент
пътя до файла INI (относително към тестовия файл). Методът се извиква
толкова пъти, колкото секции има в INI файла. Файл loop-args.ini
:
[one]
a=1
b=2
c=3
[two]
a=4
b=5
c=6
[three]
a=7
b=8
c=9
и метода, използващ файла INI:
/**
* @dataProvider loop-args.ini
*/
public function testLoop($a, $b, $c)
{
// ...
}
По същия начин можем да предадем път до PHP скрипт вместо INI. Тя трябва
да връща масив или Traversable. Файл loop-args.php
:
return [
['a' => 1, 'b' => 2, 'c' => 3],
['a' => 4, 'b' => 5, 'c' => 6],
['a' => 7, 'b' => 8, 'c' => 9],
];