Napisałem klasę, która zarządza adresatami na liście MailChimp, o nazwie MailChimpRecipient. Wykorzystuje klasę MCAPI, która jest zewnętrznym opakowaniem API.
http://apidocs.mailchimp.com/api/1.3/ http://apidocs.mailchimp.com/api/downloads/
Przekazuję obiekt MCAPI do konstruktora obiektu MailChimpRecipient, więc napisałem testy jednostkowe przy użyciu PHPUnit, które testują całą logikę we własnej klasie (nie testuję klasy MCAPI). Mam 100% pokrycia kodu i wszystkie testy są udane. Odbywa się to przez wyśmiewanie i usuwanie obiektu MCAPI.
Następnym krokiem było napisanie testu integracji, również przy użyciu PHPUnit, w którym zbudowałbym urządzenie MailChimpRecipient przy użyciu prawdziwego obiektu MCAPI, skonfigurowanego do używania prawdziwej listy MailChimp.
Napisałem coś, co moim zdaniem jest testem integracyjnym, który w zasadzie uruchamia testy przeciw publicznemu interfejsowi obiektu, na przykład:
public function testAddedRecipientCanBeFound()
{
$emailAddress = '[email protected]';
$forename = 'Fred';
$surname = 'Smith';
// First, delete the email address if it is already on the list
$oldRecipient = $this->createRecipient();
if($oldRecipient->find($emailAddress))
{
$oldRecipient->delete();
}
unset($oldRecipient);
// Add the recipient using the test data
$newRecipient = $this->createRecipient();
$newRecipient->setForename($forename);
$newRecipient->setSurname($surname);
$newRecipient->setEmailAddress($emailAddress);
$newRecipient->add();
unset($newRecipient);
// Assert that the recipient can be found using the same email address
$this->assertTrue($this->_recipient->find($emailAddress));
}
Test „integracji” nie testuje żadnych wewnętrznych elementów klasy - po prostu upewnia się, że dany prawdziwy obiekt MCAPI zachowuje się jak w reklamie.
Czy to jest poprawne? Czy to najlepszy sposób na przeprowadzenie testu międzygranicznego? W końcu elementy wewnętrzne zostały przetestowane za pomocą testu jednostkowego. Czy mam rację, myśląc, że test integracji ma na celu sprawdzenie, czy naprawdę działa, zgodnie ze sposobem, w jaki reklamowane jest jego zachowanie?
Aby pójść o krok dalej, klasa MailChimpRecipient implementuje interfejs, który będzie również implementowany przez inne klasy. Chodzi o to, aby użyć fabryki, aby przekazać różne typy obiektów adresatów list mailowych do mojego kodu, które wszystkie robią to samo, chociaż używają różnych dostawców list mailowych. Ponieważ moje testy integracyjne testują ten interfejs, co powiesz na używanie go we wszystkich klasach, które implementują interfejs? Następnie, w przyszłości, jeśli zaprojektuję nową klasę, która będzie używana zamiennie, mogę uruchomić ten sam test integracji przed wstawieniem jej do projektu.
Czy to brzmi rozsądnie? Testy jednostkowe testują wnętrze obiektu, testy integracyjne upewniają się, że zachowuje się jak w reklamie?
źródło
setUp
funkcji, aby ustalić podstawy do uruchomienia testów. Jeśli dane wejściowe są niezdefiniowane, to nie można tak naprawdę przetestować. Dane wejściowe muszą być precyzyjne, ścisłe i zawsze takie same. Jeśli warunek wstępny testu nie jest spełniony, zamiast tego pomiń test. Następnie przeanalizuj, dlaczego przeskakuje i czy musisz dodać dodatkowe testy i / lubsetUp
nie jest to zrobione dobrze.DataProvider
(to funkcja oferująca dane wejściowe jako parametry testu).Odpowiedzi:
Podczas testowania kodu należy zwrócić uwagę na trzy obszary:
Zwykle ilość testów, które przeprowadzasz w każdej kategorii, miałaby kształt piramidy, co oznacza dużo testów jednostkowych na dole, kilka testów funkcjonalnych na środku i tylko kilka testów scenariuszowych.
W teście jednostkowym wyśmiewasz wszystko, czego używa testowana klasa i testujesz to w czystej izolacji (dlatego ważne jest, aby upewnić się, że wewnątrz klasy odzyskujesz wszystkie zależności poprzez wstrzyknięcie, aby można je było zastąpić testem).
W testach jednostkowych testujesz wszystkie możliwości, a więc nie tylko „szczęśliwą ścieżkę”, ale także wszystkie błędy.
Jeśli masz całkowitą pewność, że wszystkie jednostki działają w izolacji, napisz kilka testów (testów funkcjonalnych), aby upewnić się, że działają one również w połączeniu. Następnie piszesz test scenariusza, który testuje okablowanie między wszystkimi modułami funkcjonalnymi.
Załóżmy na przykład, że testujesz samochód.
Możesz zmontować cały samochód i jako kierowca sprawdzić wszystkie możliwe warunki, ale byłoby to naprawdę trudne.
Zamiast tego przetestowałbyś małą część silnika ze wszystkimi możliwościami (test jednostkowy)
Następnie testujesz cały silnik (oddzielnie od samochodu), co byłoby testem funkcjonalnym.
W ostatnim teście wkładasz klucz, uruchamiasz samochód i jedziesz na parking. Jeśli to działa, wiesz, że wszystkie części (akumulator, paliwo, silnik, ...) są połączone, a ponieważ przetestowałeś je osobno, możesz być całkiem pewien, że cały samochód działa poprawnie.
Więc w twoim przypadku przetestowałeś wszystkie błędy i szczęśliwą ścieżkę w teście jednostkowym i wiesz, że musisz tylko przeprowadzić kompleksowy test z „prawdziwymi komponentami”, aby sprawdzić, czy okablowanie jest prawidłowe.
Kilka innych punktów,
źródło