PHPUnit je framework pro psaní jednotkových testů v programovacím jazyce PHP. Je jedním z rodiny jednotkových testů postavených na architektuře xUnit.

PHPUnit
Logo
Aktuální verze11.0.3 (10. února 2024)
Platformamultiplatformní software
Vyvíjeno vPHP
Typ softwaruframework
LicenceBSD licence
Webphpunit.de
Některá data mohou pocházet z datové položky.

Účel editovat

Jednotkové testy jsou jednou z cest ke zvýšení celkové kvality softwaru. Jsou nejzákladnějším typem testů. Pomáhají ověřit správnost návrhu a odhalit chyby dříve, než se projeví ve funkčních testech nebo dokonce u koncových uživatelů. Tvoří také aplikaci robustnější vůči zanesení chyb nových v rámci dodatečných oprav.

Jednotkové testy editovat

Jednotkové testy se provádějí na úrovni jednotlivých tříd a jejich metod. Cílem je ověřit, že se všechny metody třídy chovají, jak inzerují. To znamená, že cílem by nemělo být pouze ověření, zda na správné vstupy metoda vrátí požadovaný správný výstup, ale také, zda na nesprávné vstupy metoda vrátí požadovaný nesprávný výstup.

V PHPUnit by měla každá testována třída mít svůj „TestCase“, což je třída plnící funkci jakéhosi kontejneru pro jednotlivé testovací metody. PHPUnit zde zavádí trochu nesoulad v pojmu „test case“, neboli testovací případ. Běžně se testovacím případem totiž rozumí jedna metoda, testující určitou funkcionalitu. V PHPUnit je testovacím případem celá sada testovacích případů.

TestCase (Testovací případ) editovat

Příklad testovacího případu:

use PHPUnit\Framework\TestCase;

class UserStoreTest extends TestCase {

  public function setUp() {
  }

  public function tearDown() {
  }

  Public function testGetUser (){
  }

  //…

}

Každá třída testovacího případu musí dědit z třídy „PHPUnit\Framework\TestCase“, která je součástí balíčku PHPUnit. Její název by se měl skládat z názvu třídy, kterou testovací případ testuje a slova „Test“. Použít názvu testované třídy v názvu testovacího případu není vyžadováno. Ovšem je to jmenná konvence v rámci PHPUnit a je tedy dobré ji dodržovat. Stejně tak struktura tříd testovacích případů by měla odrážet strukturu tříd, které testuje. Což usnadní orientací mezi jednotlivými testovacími případy, případně jejích spouštění v příkazové řádce.

setUp() editovat

Každá testovací metoda je spouštěna v izolaci od dalších metod. Není možné tedy volat jednu testovací metodu pro nastavení potřebného stavu pro metodu druhou. Je tedy potřeba mít někde prostor, pro nastavení určitého výchozího stavu pro testovací jedné či více metod. K tomu slouží metoda setUp(). Ta je volána pro každou testovací metodu a umožňuje tak nastavit prostředí, ve kterém se budou jednotlivé testovací metody provádět.

tearDown() editovat

Tato metoda je naopak volána na konci každé testovací metody a slouží k nastavení prostředí pro testovací metody do původního stavu.

testMetoda() editovat

Slouží k provedení samotného testu. Název metody musí obsahovat prefix „test“ a její hlavička by neměla obsahovat žádné vstupní parametry.

Asertační metody editovat

Slouží k ověření předpokladu. Typickým předpokladem, který se ověřuje, je kontrola, zdali metoda testované třídy vrací očekávané hodnoty. Následující příklad demonstruje situaci, kdy se kontroluje, jestli metoda vrací pole obsahující údaje o uživateli:

use PHPUnit\Framework\TestCase;

class UserStoreTest extends TestCase {

  private $store;

  public function setUp() {
    $this->store = new UserStore();
  }

  public function tearDown() {
  }

  public function testGetUser() {
    $this->store->addUser( "bob williams","a@b.com", "12345" );
    $user = $this->store->getUser( "a@b.com" );
    $this->assertEquals( $user['mail'], "a@b.com");
    $this->assertEquals( $user['name'], "bob williams" );
    $this->assertEquals( $user['pass'], "12345" );
  }
}

Samozřejmě metoda asertEquals není jedinou podporovanou metodou v PHPUnit. Kompletní výčet asertačních metod lze nalez v dokumentaci

Provádění testů editovat

Spouštění testů editovat

Spouštění jednotkových testů se provádí skrze příkazovou řádku:

 $ phpunit UnitTest

 UnitTest je název třídy testovacího případu v souboru UnitTest.php. Testy lze však spouštět i hromadně. Místo názvu jednoho testovacího případu se uvede cesta do složky obsahující testovací případy.

Výsledky testů editovat

PHPUnit 4.5.0 by Sebastian Bergmann and contributors.

..

Time: 50 ms, Memory: 4.00Mb

OK (2 tests, 2 assertions)

Následující výpis informuje, že byly úspěšně provedeny 2 testy a 2 assetions. O provedení dvou testů a jejich úspěšném výsledku informují také dvě tečky uvedené nad časem a pamětí, kterou si provedení testu vyžádalo. Tečka značí úspěšné provedení testu. Test, končící selháním je označen písmenem F. Úspěch nebo selhání nejsou jedinými stavy, které PHPUnit rozlišuje. Jejich výčet a popis ukazuje tabulka:

Znak Výsledek operace
. Úspěšné provedení testovací metody
F Selhání asertační metody uvnitř testovací metody
E V případě, že se během provádění testovací metody vyskytne chyba
R V případě, že byl test označen jako riskantní
S V případě, že byl test přeskočen
I V případě, že byl test označen jako nekompletní

PHPUnit se také snaží poskytnout co nejpodrobnější report o selhání testů.

PHPUnit 4.5.0 by Sebastian Bergmann and contributors.

F.

Time: 60 ms, Memory: 4.00Mb

There was 1 failure:

1) UserStoreTest::testFail

Failed asserting that two strings are equal.

--- Expected

+++ Actual

@@ @@

-'sebastian.bergmann@phpunit.de'

+'sebastian@bergmann.phpunit'

\cesta\k\testovacimu\pripadu\UserStoreTest.php:16

FAILURES!

Tests: 2, Assertions: 2, Failures: 1.

Tento říká, že první test skončil selháním. Selhání způsobila nerovnost dvou řetězců. Očekávaný řetězec byl 'sebastian.bergmann@phpunit.de', ale druhým řetězcem v asertační metodě byl řetězec 'sebastian@bergmann.phpunit'. Dále je uvedena cesta k testovacímu případu při jehož provádění selhání nastalo.

Související články editovat

Reference editovat

  1. PHPUnit – The PHP Testing Framework [online]. 2015 [cit. 2015-06-04]. Dostupné z: https://phpunit.de/
  2. ZANDSTRA, by Matt. PHP Objects, Patterns, and Practice. 4th edition. Berkeley, CA: Apress, 2013. ISBN 978-1-4302-6032-5