Języki i Techniki Programowania II. Wykład 15. Testowanie



Podobne dokumenty
METODY PROGRAMOWANIA

Programowanie poprzez testy z wykorzystaniem JUnit

Całościowe podejście do testowania automatycznego dla programistów. (TDD, BDD, Spec. by Example, wzorce, narzędzia)

Testowanie aplikacji mobilnych na platformie Android - architektura, wzorce, praktyki i narzędzia

Testowanie jednostkowe. Jacek Starzyński, ZETiIS PW

Testy automatyczne. Korzystające z junit

Sexy unit testy. czyli o kilku praktykach w testach jednostkowych

Programowanie zespołowe

Testowanie. Ryszard Beczek & Piotr Miłkowski 1 04/11/07

Całościowe podejście do testowania automatycznego dla programistów. /C#/PHP (TDD, BDD, Spec. by Example, wzorce, narzędzia)

Aplikacje RMI Lab4

Aplikacje RMI

WYKORZYSTANIE JĘZYKA GROOVY W TESTACH JEDNOSTKOWYCH, INTEGRACYJNYCH I AUTOMATYCZNYCH. Mirosław Gołda, Programista Java

Weryfikacja i walidacja. Metody testowania systemów informatycznych

Kompozycja i dziedziczenie klas

Automatyzacja testowania oprogramowania. Automatyzacja testowania oprogramowania 1/36

TESTOWANIE OPROGRAMOWANIA

Wprowadzenie do testów jednostkowych. Marcin Dziedzic, Wiktor Żołnowski

JUnit TESTY JEDNOSTKOWE. Waldemar Korłub. Platformy Technologiczne KASK ETI Politechnika Gdańska

Automatyczne testowanie aplikacji Android

LABARATORIUM 9 TESTY JEDNOSTKOWE JUNIT 3.8

Obiektowe programowanie rozproszone Java RMI. Krzysztof Banaś Systemy rozproszone 1

JUNIT. Terminologia. Organizacja testów

Wieloplatformowe aplikacje sieciowe. dr inż. Juliusz Mikoda mgr inż. Anna Wawszczak

Wywoływanie metod zdalnych

Języki i metody programowania Java. Wykład 2 (część 2)

Testowanie I. Celem zajęć jest zapoznanie studentów z podstawami testowania ze szczególnym uwzględnieniem testowania jednostkowego.

Remote Method Invocation 17 listopada 2010

Zwinna współpraca programistów i testerów z wykorzystaniem BDD i. by Example (JBehave/Spock/SpecFlow)

Podejście obiektowe do budowy systemów rozproszonych

Remote Method Invocation 17 listopada Dariusz Wawrzyniak (IIPP) 1

Oprogramowanie systemów równoległych i rozproszonych Wykład 7

Programowanie obiektowe

Programowanie w języku Java - Wyjątki, obsługa wyjątków, generowanie wyjątków

Programowanie w Javie cz. 1 Wstęp. Łódź, 24 luty 2014 r.

Testowanie aplikacji Java Servlets

Testowanie II. Celem zajęć jest zapoznanie studentów z oceną jakości testów przy wykorzystaniu metryk pokrycia kodu testami (ang. code coverage).

Wykład 2 Wybrane konstrukcje obiektowych języków programowania (1)

Testowanie II. Cel zajęć. Pokrycie kodu

Wywoływanie metod zdalnych

Dokumentacja do API Javy.

Tomasz Dobek.

Remote Method Invocation 17 listopada rozproszonych. Dariusz Wawrzyniak (IIPP) 1

Budowa aplikacji webowej w oparciu o Maven2 oraz przykłady testów jednostkowych. Wykonał Marcin Gadamer

Początki Javy. dr Anna Łazińska, WMiI UŁ Podstawy języka Java 1 / 8

Michał Olejnik. 22 grudnia 2009

Zdalne wywołanie metod - koncepcja. Oprogramowanie systemów równoległych i rozproszonych Wykład 7. Rodzaje obiektów. Odniesienie do obiektu

Zad.30. Czy można utworzyć klasę, która implementuje oba interfejsy?

Aplikacje w środowisku Java

Zagadnienia. Inżynieria Oprogramowania

Instrukcja 10 Laboratorium 13 Testy akceptacyjne z wykorzystaniem narzędzia FitNesse

REFERAT PRACY DYPLOMOWEJ

Programowanie obiektowe

Projektowanie obiektowe oprogramowania Testowanie oprogramowania Wykład 13 Wiktor Zychla 2014

Java - wprowadzenie. Programowanie Obiektowe Mateusz Cicheński

MVC w praktyce tworzymy system artykułów. cz. 1

ZAPOZNANIE SIĘ Z TWORZENIEM

Wprowadzenie. Narzędzia i środowiska programistyczne. Laboratorium 1. Prowadzący: Kierunek: Semestr: Rok: Tomasz Gądek Informatyka Zimowy 2

Test-Driven Development

Klasy. dr Anna Łazińska, WMiI UŁ Podstawy języka Java 1 / 13

Zaawansowane aplikacje internetowe - laboratorium Architektura CORBA.

Programowanie obiektowe

Pierwsze kroki. Algorytmy, niektóre zasady programowania, kompilacja, pierwszy program i jego struktura

Kurs programowania. Wykład 9. Wojciech Macyna. 28 kwiecień 2016

Wyjątki. Streszczenie Celem wykładu jest omówienie tematyki wyjątków w Javie. Czas wykładu 45 minut.

Platformy Technologiczne

JAX-RS czyli REST w Javie. Adam Kędziora

Zaawansowane aplikacje WWW - laboratorium

Zaawansowane techniki programowania C#

JAVA I BAZY DANYCH. MATERIAŁY:

Podejście obiektowe do budowy systemów rozproszonych

Java RMI. Dariusz Wawrzyniak 1. Podejście obiektowe do budowy systemów rozproszonych. obiekt. interfejs. kliencka. sieć

Kurs programowania. Wykład 13. Wojciech Macyna. 14 czerwiec 2017

Programowanie obiektowe

1 Atrybuty i metody klasowe

Java. Wykład. Dariusz Wardowski, Katedra Analizy Nieliniowej, WMiI UŁ

Java: otwórz okienko. Programowanie w językach wysokiego poziomu. mgr inż. Anna Wawszczak

Gdzie jest moja tabela?

Java RMI. Dariusz Wawrzyniak 1. Podejście obiektowe do budowy systemów rozproszonych. obiekt. interfejs. kliencka. sieć

Języki i metody programowania Java INF302W Wykład 3 (część 1)

Rozdział 4 KLASY, OBIEKTY, METODY

Wielowątkowość. Programowanie w środowisku rozproszonym. Wykład 1.

Katalog książek cz. 2

Wprowadzenie db4o - podstawy db4o - technikalia Przydatne wiadomości. Wprowadzenie. db4o. Norbert Potocki. 1 czerwca Norbert Potocki db4o

Programowanie obiektowe

Techniki efektywnego testowania kodu dla programistów Java (Spock

Michał Sierzputowski. Zautomatyzuj swoje testy automatyczne oparte o Selenium

Testowanie oprogramowania. Testowanie oprogramowania 1/34

Narzędzia i aplikacje Java EE. Usługi sieciowe Paweł Czarnul pczarnul@eti.pg.gda.pl

Testowanie aplikacji. Kurs języka Ruby

Słowa kluczowe jak góry lodowe

Język JAVA podstawy. wykład 2, część 2. Jacek Rumiński. Politechnika Gdańska, Inżynieria Biomedyczna

Pico. Wstęp do kontenerów IoC.

Aplikacja wielow tkowa prosty komunikator

Java podstawy jęyka. Wykład 2. Klasy abstrakcyjne, Interfejsy, Klasy wewnętrzne, Anonimowe klasy wewnętrzne.

Program szkolenia: Test Driven Development (TDD) using Spock or JUnit 5

RMI-2. Java Remote Method Invocation (RMI) na podstawie m.in. podręcznika firmy Sun Microsystems SYSTEMY ROZPROSZONE

Programowanie w języku Java. Bazy danych SQLite w Javie

Aplikacja webowa w Javie szybkie programowanie biznesowych aplikacji Spring Boot + Vaadin

Transkrypt:

Języki i Techniki Programowania II Wykład 15 Testowanie

Testy "Beware of bugs in the above code; I have only proved it correct, not tried it." Knuth

Typy Testów Smoke Tests - odpalenie systemu do wykonania prostego zadania, po dokonaniu jakiejkolwiek zmiany Regression Tests test czy funkcjonalność została zachowana. Problem: BARDZO DUŻO PRACY Rozwiązanie: Zautomatyzowanie procesu Continuous Build proces automatycznego budowania i uruchamiania Load Tests sprawdzanie granic maksymalnego obciążenia Stress Tests testy stabilności pod obciążeniem Performance Testing pomiary wydajności

Zakresy Testów Poziomy testów: Acceptance Tests Sprawdzenie zgodności ze specyfikacją (Test Scripts) System Tests Sprawdzenie poprawności współdziałania modułów Sprawdzenie różnych konfiguracji Unit Tests Najprościej: main w każdej klasie Służą jako dokumentacja Warto użyć narzędzi

Kategorie Testów Kategorie testów z punktu widzenia testerów: White Box testing testy developerskie Black Box Testing testy dokonane przez QA Gray Box Testing gdy testerzy mają dostęp do konfiguracji. Kategorie testów z punktu widzenia cyklu życia: Alpha Tests Głównie White Box Testing Beta Tests Gray, Black Box Testing u wybranej grupy użytkowników Gamma Tests nieformalne (świadome wady)

Test Driven Development Pisząc program i tak na bieżąco testujemy Wiara w to że raz poprawiony błąd się nie powtórzy nie jest niczym uzasadniona Powtarzalne czynności można i trzeba automatyzować Koszt automatyzacji zwraca się bardzo szybko

Test Driven Development Testy zwiększają sprawność programisty (ang. mobility) Testerzy na pewno nie stracą pracy Testy są dla ludzi, nie dla programów

Test Driven Development Testy zwiększają sprawność programisty (ang. mobility)... a nie dowodzą poprawności programu Testerzy na pewno nie stracą pracy Testy są dla ludzi, nie dla programów... bo przecież testy nie stanowią części produktu końcowego

Test Driven Development Zautomatyzowane testy: Pomagają lepiej zarządzać koncentracją (ang. flow) Stanowią naturalne rozszerzenie nawyku kompilujuruchom-pisz-kompiluj-uruchom... Pozwalają wcześnie wyeliminować trywialne błędy te najbardziej zniechęcające Powodują że przyjemne programowanie znowu staje się przyjemne Pozwalają odejść od mentalności Jak działa, nie dotykaj - nie musimy już godzić się na kompromisy - Refactor Mercilessly

Reguły Test Driven Development 1. You are not allowed to write any production code unless it is to make a failing unit test pass. 2. You are not allowed to write any more of a unit test than is sufficient to fail; and compilation failures are failures. 3. You are not allowed to write any more production code than is sufficient to pass the one failing unit test. 1. Zaczynamy pisanie od Unit Testu 2. Piszemy tylko tyle ile trzeba, by test mógł przejść (czyli niewiele), przechodzimy do pisania kodu produkcyjnego (brak kompilacji jest traktowany jako niepowodzenie testu) 3. Jeśli tylko test przejdzie, lub się kompiluje przechodzimy do punktu 2

Proces Test Driven Development 1. Stwórz test który sprawdza drobną część funcjonalności 2. Doprowadź do stanu by test się nie powiódł 3. Napisz kod który spowoduje że test przejdzie 4. Zrefaktoruj kod, doprowadzając do najprostszej możliwej struktury (Refactor Mercilessly) 5. Idź do punktu 1.

Proces Test Driven Development Założenia: Interfejsy oraz przekazywanie wiadomości (message passing) czyli wywoływanie metod - są ważniejsze niż kod proceduralny Testuj co się da W Praktyce: test typowej sytuacji, testy warunków brzegowych, testy sprawdzające poprawność usunięcia każdego buga Wszystkie testy muszą zawsze przechodzić

Ograniczenia automatyzacji testów Problemy: Interfejs użytkownika, jego funkcjonalność Interfejs WWW (istnieją do tego narzędzia, ale...) Niedeterministyczne algorytmy heurystyczne algorytmy genetyczne, wyżarzanie (annealing) etc... Systemy rozproszone Testowanie struktury danych (np. zasadniczy element inżynierii Baz Danych)

Problemy automatyzacji testów Dla skutecznego testowania, należy: Mieć architekturę systemu która dobrze wspiera rozdzielenie funkcjonalności oraz korzystanie z MockObject-ów (sugerowane: Inversion of Control) Nie mieć logiki w warstwie prezentacji (niekoniecznie może się udać) Zaplanować bardzo intensywne dziedziczenie testów Przemyśleć strategię testowania co chcemy testować, jakie narzędzie chcemy stosować, jaki mamy styl programowania, jaki będzie cykl życiaprojektu nie ma uniwersalnych rozwiązań

Ograniczenia automatyzacji testów Problemy: Interfejs użytkownika, jego funkcjonalność Interfejs WWW (istnieją do tego narzędzia, ale...) Niedeterministyczne algorytmy heurystyczne algorytmy genetyczne, wyżarzanie (annealing) etc... Systemy rozproszone Testowanie struktury danych (np. zasadniczy element inżynierii Baz Danych)

Automatyzacja testów Testy winny być: Atomiczne kod jest mniej kruchy przy refactoringu Izolowanie i niezależne od porządku uruchomienia Czytelne Proste w konfiguracji Szybkie

Automatyzacja testów Luźne uwagi: Książkowe podejście: Unit=jednostka, czyli dokładnie 1 klasa, metoda itp.... ale w praktyce jest to nie Unit Test - ale Programmer Test - test funkcjonalności, nie jednostki Prędkość wykonania testów jest kluczowa nikt nie będzie czekał 30 minut na jedną kompilację + testy Testy działają w trakcie tworzenia software'u. Nie należy jednak zapominać o wersji produkcyjnej: logi i dobrze zaprojektowane wyjątki są nadal konieczne

Automatyzacja testów Luźne uwagi cd.: Czy 100% pokrycie testami jest konieczne? NIE Jaka jest prędkość kodowania przy zastosowaniu testów? Pod koniec projektu może nawet być ujemna (refactoring)! Wniosek: Bądź elastyczny, nie daj się zastraszyć metodologiom i metrykom jedynym kryterium oceny jest skuteczność

JUnit Twórcy JUnit Kent Beck (XP) i Erich Gamma (GoF Book) Jak stworzyć własny Unit Test: Dziedziczymy po TestCase Przeciążamy runtest Tworzymy własny konstruktor, przekazując String do super(...); Wołamy asserttrue() w metodach testowych metoda testowa musi być: zaczynać się od test (Junit <4.0) publiczna bezparametrowa

} JUnit Tworzymy Fixture (Ustawienie) zestaw testów z okre ślonymi danymi np. Mock Objectem/Stubem Dziedziczymy po TestCase Przeci ążamy runtest Zestaw testów: Tworzymy wasny ł konstruktor, przekazuj ąc String do super(...); setup() tworzy nam dane, teardown() niszczy public static Test suite() { TestSuite suite= new TestSuite(); suite.addtest(new MoneyTest("testMoneyEquals")); suite.addtest(anothermoneytest.class); return suite;

Junit 4 przed każ dym testem wykonywane s ą wszystkie metody oznaczone jako @Before, a po teś cie @After przed wszystkim testami wykonywane s ą wszystkie metody oznaczone jako @BeforeClass, a po teś cie @AfterClass Klasy testów ju ż nie musz ą dziedziczy ć z TestCase Testy stanowi ą metody publiczne bezparametrowe oznaczone poprzez @Test Mo żna kontrolowa ć czas testu @Test (timeout=10) Mo żna kontrolowa ć czy test rzuci ł okre ślony wyj ątek @Test(expected=IndexOutOfBoundsException.class)

Junit 4 import static org.junit.assert.assertequals; //Java 5 magic @Test public void simplequery() throws SQLException { Statement stmt; try { stmt = conn.createstatement();resultset rs = null; rs = stmt.executequery("select 1 from data"); if(rs.next()) assertequals("1",rs.getstring(1)); } catch (SQLException e) { e.printstacktrace(); fail("problems with the database"); } }

JUnit public static void main(string args[]) { } Tak że: junit.textui.testrunner.run(suite()); java junit.awtui.testrunner java junit.swingui.testrunner Podajemy nazw ę klasy z testem

JUnit a Eclipse Eclipse 3.1+ ma wbudowanego JUnit Mo żna dodawa ć do projektu testy dla konkretnych klas Uruchamiamy je poprzez Run As... -> JUnit test

Mock vs Stub Mock Object Obiekt testowy pozwalaj ący sprawdzi ć interakcj ę Stub Object Obiekt testowy pozwalaj ący sprawdzi ć poprawno śc danych Fake Object prawie dziaaj ł ący obiekt Dummy Object zapchajdziura - obiekt nigdy nie wykorzystany

Stub Object public class OrderStateTester extends TestCase { private static String TALISKER = "Talisker"; private static String HIGHLAND_PARK = "Highland Park"; private Warehouse warehouse = new WarehouseImpl(); protected void setup() throws Exception { warehouse.add(talisker, 50); warehouse.add(highland_park, 25); } public void testorderisfilledifenoughinwarehouse() { Order order = new Order(TALISKER, 50); order.fill(warehouse); asserttrue(order.isfilled()); assertequals(0, warehouse.getinventory(talisker)); }

Stub Object public void testorderdoesnotremoveifnotenough() { Order order = new Order(TALISKER, 51); order.fill(warehouse); assertfalse(order.isfilled()); assertequals(50, warehouse.getinventory(talisker)); }

The Golden File Jak testowa ć aplikacje dziaaj ł ące z linii komend? Jeś li aplikacja ma dobrze okre ślenie wej ście i wyj ście (np. plik wej ściowy do parsera i wynik parsowania) stosujemy metod ę The Golden File - nagrany plik z wcze śniejszym wynikiem przetwarzania który test tylkoporównuje ze swoim wynikiem Za: Prawdopodobnie stworzenia najszybszy typ testów do stworzenia Przeciw: Trudne do uogólnienia na inne przypadki.pury ści mog ą powiedzie ć że Golden File to jest smell

Bazy Danych Jak testowa ć aplikacje korzystaj ąc ą z bazy danych? Istnieje kilka rozwi ąza ń: Korzystamy z bazy danych testowej (tak robi RoR) nale ży tylko piel ęgnowa ć jej struktur ę Korzystamy ze Stubów przechowuj ących dane w pliku konfiguracyjnym (korzystaj ąc np. z DBUnit) Tworzymy dla każ dego testu struktur ę bazy w pami ęci (korzystaj ąc np. z Hibernate oraz JavaDB/Derby) prawdopodobnie dziaaj ł ące najszybciej rozwi ązanie

Bazy Danych DBUnit dziedziczymy po DBTestCase public void testme() throws Exception {... IDataSet databasedataset=getconnection().createdataset(); ITable actualtable=databasedataset.gettable("table_name"); IDataSet expecteddataset = new FlatXmlDataSet(new File("expectedDataSet.xml")); ITable expectedtable = expecteddataset.gettable("table_name"); Assertion.assertEquals(expectedTable, actualtable); }

Pattern Mock Object Unit Test z zao ł żenia ma sprawdza ć wy łącznie drobn ą cz ęść systemu. W tym celu wszelka interakcja ze światem zewn ętrznym (pozosta łą częś ci ą systemu) musi zosta ć zast ąpiona przez MockObject MockObject powinien: by ć łatwy do stworzenia, łatwy do skonfigurowania, szybki, deterministyczny, bez interfejsu użytkownika, wy łącznie z metodami dost ępowymi ( get )

Pattern Mock Object NIE TESTUJ MOCKA Wniosek wszystkie elementy systemu musz ą pochodzi ć z fabryk. Żaden obiekt nie mo że tworzy ć elementów z którymi wspópracuje ł ( żeby mo żna byo ł podmieni ć go pod Mock) To si ę nazywa Inversion Of Control (IoC) istniej ą dedykowane kontenery temat wykracza znacznie poza tematyk ę wykadu ł

Mock Object public class OrderInteractionTester extends MockObjectTestCase { private static String TALISKER = "Talisker"; public void testfillingremovesinventoryifinstock() { //setup data Order order = new Order(TALISKER, 50); Mock warehousemock = new Mock(Warehouse.class); //setup expectations warehousemock.expects(once()).method("hasinventory").with(eq(talisker),eq(50)).will(returnvalue(true)); warehousemock.expects(once()).method("remove").with(eq(talisker), eq(50)).after("hasinventory");

Mock Object //exercise order.fill((warehouse) warehousemock.proxy()); warehousemock.verify(); asserttrue(order.isfilled()); } public void testfillingdoesnotremoveifnotenoughinstock() { Order order = new Order(TALISKER, 51); Mock warehouse = mock(warehouse.class); warehouse.expects(once()).method("hasinventory").withanyarguments().will(returnvalue(false)); order.fill((warehouse) warehouse.proxy()); assertfalse(order.isfilled());}

JMock Istniej ą narz ędzia do tworzenia Mock Object jako proxy mniej kruche ni ż rę cznie tworzone (uwaga: nie testuj Mocka) Sprawdzamy funkcjonalno ść Publisher w modelu Publish(er)/Subscribe(r) import org.jmock.*; class PublisherTest extends MockObjectTestCase { public void testonesubscriberreceivesamessage() { Mock mocksubscriber = mock(subscriber.class); Publisher publisher = new Publisher(); publisher.add((subscriber) mocksubscriber.proxy());

JMock final String message = "message"; //oczekiwane warunki mocksubscriber.expects(once()).method("receive").with(0eq(message) ); publisher.11publish(message); } } Jeś li oczekiwane warunki nie zostan ą spenione ł test się nie powiedzie

} Fluent Interface private void makenormal(customer customer) { Order o1 = new Order(); customer.addorder(o1); OrderLine line1 = new OrderLine(6, Product.find("TAL")); o1.addline(line1); OrderLine line2 = new OrderLine(5, Product.find("HPK")); o1.addline(line2); OrderLine line3 = new OrderLine(3, Product.find("LGV")); o1.addline(line3); line2.setskippable(true); o1.setrush(true);

Fluent Interface private void makefluent(customer customer) { customer.neworder().with(6, "TAL").with(5, "HPK").skippable().with(3, "LGV").priorityRush(); }

Fluent Interface Kluczem s ą settery zwracaj ą ce this customer.neworder().with(6, "TAL").with(5, "HPK").skippable().with(3, "LGV").priorityRush(); A czasem inny obiekt (dobre do podpowiedzi w IDE) mock.expects(once()).method("m").with( ); or(stringcontains("hello"),stringcontains("howdy")) W celu walidacji warto mie ć trigger table.select( name ).where( id, equal(6)).query()

Testowanie GUI Dla MVC mo żna testowa ć interakcj ę Modelu i Controllerów. Jeś li View ma zo ł żon ą logik ę to mo żna tworzy ć jego fragmenty i je odpytywa ć w trakcie testu. Istnieje mo żliwo ść nagrania klikni ęć i odtworzenie ich (java.awt.robot) ale jest to bardzo kruche rozwi ązanie Mo żna korzysta ć z istniej ących frameworków do testowania GUI np. Abbot

Testy są super!!! Niech komputer wyr ęczy Ci ę w nudnej robocie Zostaw debugger pisz testy! Rozwi ąż problem zaczynaj ąc od testów Nie daj si ę przyt łoczy ć testowaniem starego kodu: testuj tylko to co konieczne Dokumentuj testami: swój program, użyte API itp. itd. Wypracuj nawyk testowania. Odrzu ć zasad ę jak dziaa, ł nie dotykaj. Refactor Mercilessly. Znajd ź swój styl metody s ą dla ludzi, a nie ludzie dla metody