Ddt dizajn vođen testiranjem final
-
Upload
amina-curovac -
Category
Documents
-
view
425 -
download
3
description
Transcript of Ddt dizajn vođen testiranjem final
UNIVERZITET U SARAJEVU
Fakultet za saobraćaj i komunikacije
Predmet: Informacioni sistemi u saobraćaju i komunikacijama
- Design-driven testing (Dizajn vođen testiranjem) -
- - -seminarski rad---
Mentor: Studenti:
mr. Alem Čolaković, dipl.ing. Minela Hasanović, 6545
Predmetni nastavnik: Irma Hodžić, 6531
Doc.dr. Mugdim Bublin Merima Omerika, 6516
Anela Lavić, 6541
Lemana Korić, 6664
Amina Ćurovac, 6665
Sarajevo, novembar 2012.
SADRŽAJ
1
Uvod 3
1. Dizaj vođen testiranjem u teoriji4
1.1. Različite vrste testiranja 5
1.2. Vođenje test slučajeva iz dijagrama robusnosti 9
1.3. Korištenje agilnog dodatka za ICONIX/EA 11
1.4. Vođenje test jedinica sa test slučajeva 13
1.5. Kratki uvod u JUnit 14
1.6. Pisanje efektivnih testova jedinica 17
2. Dizaj vođen testiranjem u praksi 18
2.1. Testovi jedinica za Internet knjižaru 18
2.2. Testiranje Prikaz Početne Stranice 20
2.3. Pokretanje testova iz test paketa 25
2.4. Testiranje Preuzmi Detalje Knjige Kontrolor 26
2.5. Testiranje Prikaži Detalje Knjige Kontrolor 32
2.6. Testiranje Prikaz Stranica Knjiga Nije Pronađena Kontrolor 40
3. Deset najvećih grešaka dizajna vođenog testiranjem 45
Zaključak 46
Bibliografija
Popis slika i tabela
UVOD
2
Lahko je pogledati u programski modul, i reći „Eto, to je završeno“, ali osjećaj završetka može
biti varljiv. Kako možemo znati sigurno da je kod završio sve „use case“ (korištene slučajeve)
scenarije, a ne samo osnovne kurseve, već i alternativne takođe?
DDT (design-driven testing) – dizaj vođen testiranjem pruža neprobojnu metodu za proizvodnju
test slučajeva, kako bi verifikovali da su svi naznačeni scenariji završeni. Možemo takođe,
koristiti ovaj proces da napišemo izvršne testove iz testnih slučajeva.
Testiranje je proces koji bi trebao početi mnogo prije kodiranja. Počinjanje testiranja proizvoda
poslije nakon što je navodno „završen“ je marginalno bolji, ali bi testni proces trebao početi
mnogo prije nego što se uopće počne kodirati. Priprema za testiranje počinje u toku faze analize,
identifikovanjem testnih slučajeva uz korištenje robusnih dijagrama (robustness diagrams).
Ranim testiranjem, moguće je eliminirati mnogo više kvarova, prije nego što se uopće pojave.
Testiranje slijedi ubrzo nakon preliminarnog dizajna, a onda pisanje jedinica test kodova tokom
implementacije. Moramo biti sigurni da su testovi povezani zajedno za zahtjevima. Ne iz razloga
da svaki test bi trebao biti praćen unazad ka zahtjevima, ali bi trebao bar postojati test da
„dokaže“ da je svaki zahtjev proveden tačno. Proces koji ćemo opisati u ovom poglavlju je jedna
metoda za rađenje upravo toga: pokretanje testova jedinica iz korištenih slučajeva.
1. Dizaj vođen testiranjem u teoriji
3
Počet ćemo ovo poglavlje osvrtanjem na pretpostavke i osnovne teorije DDT. Pokazat ćemo par
primjera kroz rad, koje ćemo kasnije prenijeti u podpoglavlje „Dizajn vođen testiranjem u
praksi“, ali svakako potrebno je da se prvobitno osvrnemo na teoriju. Principi koje ćemo
prodiskutovati u ovom poglavlju mogu biti sumirani u listu smjernica. Naša lista „top 10“ :
10. Usvojiti testiranje gdje se svaki pronalazak kvara prihvata kao pobjeda, a ne poraz. Ako
pronađemo ( i popravimo) kvar u testiranju, korisnici ga neće ponaći u konačnom proizvodu.
9. Razumijevanje različitih vrsta testiranja, kako i to kada se oni koriste. Upoznavanje sa
različitim vrstama testova koje ćemo opisati u ovom poglavlju i primjena svakog testa u pravo
vrijeme, a isto tako važno, korištenje isporuka koje kreiramo na putu za pripremu svakog testa u
unaprjeđenju.
8. Kada testiranje jedinica kreira jedan ili više testova za svaki kontroler na svakom robusnom
dijagramu, također kreira jedan ili više jediničnih testova za svaku operaciju na svakoj klasi sa
dizajnom.
7. Za realne sisteme, koristimo elemente dijagrama stanja kao osnovu za testove slučajeva.
Na primjer, test odgovara različitim elementima koji pokreću promjene stanja. Tokom ove vrste
testiranja, pratimo promjene u osobinama objekata kako bi testirali interakcije između objektnih
metoda. Možemo koristiti elemente dijagrama stanja kao bazu za testove slučajeva.
6. Uraditi provjeru nivoa zahtjeva , provjeravajući svaki zahtjev koji smo identificirali.
5. Koristiti matricu slijedivosti kao pomoć u provjeri zahtjeva.
4. Uraditi scenario nivoa pihvatljivosti za svaki korišteni slučaj.
3. Proširiti teme u testnim scenarijima za pokrivanje kompletnog puta, kroz odgovarajući dio
osnovnog kursa i dodanog kursa u testiranju scenarija.
2. Koristiti okvir testiranja kao što je JUnit, za pohranjivanje i oganizovanje testova jedinica.
1. Održavanje testova jedinica dobro preciziranim.
1.1. Različite vrste testiranja
4
Treba li bi posmatrati testiranje kao skup interativnih i inkremantalnih razvojnih ciklusa, ne samo
kao nešto što se povremeno radi nakon što izdvojite hrpu kodova? Razlog za to je jednostavan:
test dokazuje da proizvod odgovara specificiranoj namjeni.
Testovi samo po sebi trebaju biti veoma čvrsto povezani sa zahtjevima, na mikroskopskom
nivou. Ako su testovi usko povezani sa zahtjevima, onda se prolaskom testa dokazuje da softver
odgovara svojoj specificiranoj namjeni, a ako testovi nisu povezani sa zahtjevima onda prolazak
testa, samim po sebi je beznačajan.
Ključ za testiranje je razumijevanje različitih vrsta testova, i posebno kada u ciklusu života
softvera, koja vrsta testa treba biti upotrijebljena. Slika 1. pokazuje koji testovi trebaju biti
izvedeni za svaku fazu u ICONIX Process-u.
Tako, za testove koji su preliminarno dizajnirani i provedeni zadovoljavavajuće sa
specifikacijama, provodimo integracione testove, pa nadalje. Pripreme za svaku vrstu testa
mogu početi dobro unaprijed. Na primjer, sve dok je poslovni ugovor (u suštini ugovor između
kompanije i kupca) nepotpisam, QA može početi špekulaciju izvedenih testova, baziranim na
sadržaju poslovnog slučaja. Slično, sve dok je korišteni slučaj napisan, softver testeri mogu
početi pisati testove za taj korišteni slučaj.
Mnogi od testova višeg nivoa mogu biti napisani u obliku testova jedinica. Na primjer, kao što
ćemo vidjeti kasnije u ovom radu, poželjno je da izvodimo testove jedinica i metode, direktno iz
kontrola u preliminarnom dizajnu, koji su u suprotnom, izvođeni od korištenih slučajeva.
5
Slika 1. „V“ model softverskog testiranja primjenjljivog u ICONIX Procces-u
Tabela 1. opisuje različite vrste testova prikazane u slici 1.
6
Test Kada (i zašto) bi trebali ih izvoditi
Test jedinicaTestiranje individualnih softverskih komponenti. Može se koristiti za simulaciju inputa i outputa komponente, tako da može raditi u samostalnom načinu
Testiranje jedinica počinje prije integracije.Testiranje jedinica se izvršava na svakoj izgradnji softvera, kroz razvojne faze ( uključujući fazu popravka kvarova, nakon što je softver pušten u testiranje sistema)
Integracioni testTestiranje se vrši da se otkriju greške u sučeljima i u interakciji između integrisanih komponenti.Za razliku od testova kompatibilnosti, klase su dio ukupnog sistema dizajna
Vrši se nakon testiranja jedinica
Test kompatibilnostiTestiranje da sistem sarađuje dobro sa ostalim „vanjskim“ sistemima, sa kojima se zahtjeva da komunicira.
Nije isti kao integracioni test, iako se oba rade u isto vrijeme
Test sistemaFunkcionalni i behioralni dizaj test slučaja. Selekcija test slučaja koja je bazirana na analizi specifikacija komponenti bez upućivanja na unutarnje djelovanje. Funkcionalno testiranje sastoji se od mnogih korištenih slučajeva i poslovnih procesa ispitivanja, ali uključuje i testiranje funkcionalnih zahtjeva.
Vrši se nakon integracionog testa.Test sistema, teži da bude fokusiran na razvoj. Njegova namjena je da dokaže da sistem koji je naznačen je i dostavljen
Test prihvatljivostiFormalno testiranje provedeno od strane kupca, da se utvrdi da li sistem zadovoljava zahtjeve naznačene u ugovoru
Test prihvatljivosti provodi se u istoj liniji sa testom sistema ali je isticanje drugačije. Iznosi se da bi se utvrdilo da sistem isporučuje ono što je stvarno traženo.
Beta testingProvodi se od strane krajnjeg korisnika koji nije drugačije uključen u razvoj.
Provodi se prije testa prihvatljivosti, u okruženju što bližem proizvodnom okruženju.
Test puštanjaProvjera da završeni proizvod precizno odražava poslovni slučaj
Radi se u tački u kojoj softver treba biti isporučen kupcu, da se osigura da je proizvod razvijen u skladu sa specifikacijama i da u potpunosti postiže ciljeve.
Tabela 1. Različite vrste testova i kada ih primjeniti
Kao dodatak navest ćemo neke vrste testova koje prolaze kroz razvojni proces ili nisu bazirane
na specifičnoj isporuci (Tabela 2.).
7
Test Kada (i zašto) bi trebali ih izvoditi
Nefunkcionalni test zahtjeva
Testiranje onih zahtjeva koji nisu vezani za
funkcionalnost (izvođenje, korisnost,...)
Ovaj test treba se provoditi kroz životni ciklus
softvera, gdje je god moguće ( čak i na nivou
testa jedinica).
Test izvodljivosti
Testiranja provedena za procjenu popustljivosti
sistema ili komponenti sa specificiranim
zahtjevima izvođenja.
Ovaj test može ( i treba) biti izveden u svakoj
prilici ali se uglavnom izvršava nakon testa
sistema.
Test regresije
Retestiranje prethodno testiranog programa
slijedeći modifikacije da osigura da neuspjesi
nisu uvedeni ili neotkriveni kao rezultat
napravljene promjene.
Ovo testiranje se izvršava nakon što kod bude
pušten u test sistema. Test jedinica je forma
regresijskog testa ako se izvede pravilno.
Test otpornosti na stres
Testiranja provedena za evaluaciju sistema ili
komponente na granici ili izvan svojih granica,
specificiranih zahtjevima.
Ovaj test se izvodi nakon testa izvodljivosti.
Test zapremine
Ispitivanje gdje je sistem podvrgnut velikim
količinama podataka.
Izvodi se nakon testa sistema.
Tabela 2. Testovi koji prolaze kroz razvojni proces
1.2. Vođenje test slučajeva iz dijagrama robusnosti
8
Sa ICONIX Procces-om, ulažemo trud kako bi napisali korištene slučajeve, i identifikujemo
objekte koji sudjeluju u korištenom slučaju kao i funkcije koje ti objekti obavljaju na dijagramu
robusnosti (funkcije su prikazane kao kontroleri). Pošto smo uložili trud u identifikaciju logičnih
softverskih funkcija, bilo bi dobro kada bismo dobili paket test slučajeva koji nas podsjećaju da
testiramo sve funkcionalnosti korištenog slučaja. Slika 2. prikazuje pregled DDT, u kojoj test
slučajevi su kreirani direktno od kontrolera na dijagramu robusnosti.
Kako slika 2. prikazuje, možemo automatski transformisati dijagram robusnosti u sekvencijalni i
dijagram test slučajeva korišteći jednostavnu skriptu. Test kod može biti naknadno generiran za
test jedinica okvira kao što su JUnit or NUnit.
Sada ćemo to detaljnije objasniti kroz korake na primjeru. Kada definiramo logične funkcije sa
kontrolorima korištenih slučajeva, potrebno je te funkcije testirati. Radom sa dijagramom
robusnosti, možemo kreirati dijagram test slučaja, koji prikazuje test slučaja za svakog
kontrolora. To ćemo uraditi tako što ćemo kopirati sve kontrolore sa dijagrama robusnosti na
novi dijagram, i onda povezati sa testom slučaja korištenjem <<realize>> konektora. To ćemo
ubrzo prikazati i na primjeru.
9
Slika 2. Pregled DDT-a
Svaki test slučaja sadrži više scenarija. Da bi identifikovali test scenario za svaki kontrolor/test
slučaj, trebamo slijediti slijedeće korake:
1.Ponovo pročitati tekst korištenog slučaja da se podsjetimo sadržaja u kojem je kontroler
korišten
2. Za svaki test slučaj, kreirati test scenario za svaki korišteni scenario (osnovni i alternativni
kursevi)
10
3. Imenovati svaki test scenario nakon orginalnog korištenog scenarija. Na primjer, za kontroler
“Preuzeti detalje knjige”( Retrieve Book Details), alternativni scenario nazvan “Knjiga nije
pronađena” (Book Not Found), će dovesti do test scenarija “Knjiga nije pronađena” u test slučaju
nazvanim “Preuzeti detalji knjige”.
1.3. Korištenje agilnog dodatka za ICONIX/EA
Trebamo naglasiti da ICONIX Process radi jednako dobro sa bilo kojim objektno-orjentiranim
programskim jezikom, CASE alatom itd. Enterprise Arhitect (EA) ima poseban dodatak koji
automatizira mnogo “prijelaznog” posla kada premještamo između dijagrama u ICONIX
Process-u. Na primjer, dodatak će automatski kreirati set robusnih dijagrama za dijagram
korištenog slučaja (slika 3. ), i dodatak će popuniti sekvencijalni dijagram koristeći granice,
entitet i kontroler objekte na robusnom dijagramu, što je veoma velika ušteda na vremenu.
Slika 3. Korištenje Agilnog ICONIX/EA dodatka za generiranje dijagrama
11
Slika 4. Generacija test slučajeva u EA
Za potrebe testiranja, dodatak automatski kreira dijagram test slučaja od kontrolora na robusnom
dijagramu (slika 4.). Onda je moguće napisati izvršni test jedinica za svaki test slučaj.
Primjećujemo da je svaki test slučaja povezan sa kontrolorom. Drugim riječima, postoji jedan
test slučaj po kontroloru. Veza između test slučaja i kontrolera je “realizes” (ostvaruje), ista veza
koja je korištena da pokaže klase implementacije/realizacije sučelja.
Desnim klikom na svaki test slučaj možete dodavati individualne scenarije.(slika 5.)
12
Slika 5. Dodavanje test scenarija u EA
1.4. Vođenje test jedinica sa test slučajeva
Da podsjetimo, moramo modelirati test slučaj na kontrolora iz svog robusnog dijagrama-da svaki
kontroler dobija tačno jedan test slučaj, i za svaki test slučaj, kreirati jedan ili više test scenarija.
Jednom kada kreiramo test slučaj i alociramo test scenarijo na svaki, vrijeme je da kreiramo
kostur test jedinica.
13
Uputstva za vođenje test jedinica iz test slučajeva:
Za svaki test slučaj, kreiramo jednu klasu test jedinica. Na primjer, ako se test slučaja
zove “Test Preuzimanja Detalja Knjige”, onda kreirate klasu JUnit testa nazvanu
TestPreuzimanjaDetaljaKnjige.
Za svaki test scenario, kreiramo jednu testnu metodu u klasi testova jedinica. Na primjer,
ako je test slučaj nazvan Knjiga Nije Pronađena, kreiramo test metodu nazvanu
testKnjigaNijePronađena().
Napisati test jedinica sa ugla posmatranja objekta, tj kontrolora.
Ako otkrijemo nove alternativne tečaje dok razmišljamo o scenariju test slučaja, što je
moguće, ne treba oklijevati da ih dodamo u korišteni slučaj.
Proći ćemo kroz neke primjere kreiranja testova jedinica iz testova slučajeva.
1.5. Kratki uvod u JUnit
Za kodiranje primjera kasnije u ovom poglavlju koristit ćemo JUnit, popularnu Java-baziranu
okvirnu test jedinicu. JUnit dio je xUnit porodice koja uključuje cppUnit za C++, n Unit za
C#/.NET i DUnit za Borlan Delphi. Iako se izvorni kod može razlikovati ovisno o
jeziku/implementaciji, principi razmatrani u ovom poglavlju su u osnovi isti, bez obzira koji
okvir test jedinica koristimo.
Sa JUnit, pišemo test slučaj gdje svaki test slučaj je pojedinačna Java klasa. Unutar ove klase,
pojedinačne metode ispitivanja slijedite konvenciji imenovanja testa XYZ, gdje XYZ je ime
našeg testa. Ova konvencija imenovanja dozvoljava JUnit da automatski otkrije i pokrene test
metode, bez njihovog “proglašavanja” (npr. u vanjskom XML fajlu). Korištenje JUnit 4.0, test
metode može također biti identifikovano korištenjem Java 5 tvrdnji.
Unutar test metode, možete napisati Java kod koji poziva metode u klasama da budu testirane i
tvrdi da je rezultat upravo ono što se i očekivalo. Za dio tvrdnji , JUnit pruža broj različitih
metoda tvrdnji(npr., tvrditi da je vrijednost istinita, ili da vrijednost nije-nula, ili da dvije
vrijednosti su jednake). Test klasa može sadržavati bilo koji broj test metoda, iako je generalno
dobra ideja držati broj ispod pet. Slično, dobro je ograničiti svaku test metodu na jednu tvrdnju.
14
Ovo čuva test scenarij fokusiranim na testiranje jedne stvari. Ako imamo potrebu da dodamo
više od jedne tvrdnje, vjerovatno tražimo više od jednog test scenarija stisnute u jednu test
metodu, tako da ne treba oklijevati da ih podijelimo.
Imamo primjer klase testa jedinica:
package test.com.iconixsw.bookstore.web;
import junit.framework.*;
public class AddToShoppingCartTest extends TestCase {
public AddToShoppingCartTest (String testName) {
super(testName);
}
public void testShoppingCartEmpty() throws Exception {
ShoppingCart cart = new ShoppingCart();
assertEquals("Cart should be empty", 0, cart.getNumItems());
}
public void testItemAdded() throws Exception {
ShoppingCart cart = new ShoppingCart();
LineItem item = new LineItem();
cart.addItem(item);
assertEquals("Cart should contain 1 item",
1, cart.getNumItems());
}
}
Test slučaj DodajUKorpuKupovineTest sadrži dvije test metode. Prva metoda je brza, razumna
provjera da se uvjerimo da ako je nova KorpaKupovine kreirana, počinje prazna.
15
Druga test metoda provjerava da ako je jedan artikal dodan u korpu, onda korpa sadrži tačno
jedan artikal. U oba slučaja koristimo asserEquals(), koji ima tri argumenta:
• Koristan opis koji se pojavi ako test ne izvrši uslove
• Vijednost koja predstavlja kakva očekivana vrijednost treba biti
• Rezultat testiranog koda, koji bi naravno, riješio samu vrijednost drugog argument.
Obje test metode postavljaju objekat KorpaKupovine. Zapravo, uzeći u obzir da je test slučaj sve
o dodavanju artikla u KorpaKupovine, imalo bi smisla za oba testa da koriste istu postavku koda.
Srećom, JUnit omogućava a setUp() metodu samo za ovu namjenu. Da demonstriramo ovo,
pokazat ćemo novu verziju DodajUKupovnuKorpuTest, koji koristi setup() da eliminiše duple
kodove. Novi kod je prikazan u crvenoj boji:
package test.com.iconixsw.bookstore.web;
import junit.framework.*;
public class AddToShoppingCartTest extends TestCase {
private ShoppingCart cart;
public AddToShoppingCartTest (String testName) {
super(testName);
}
public void setUp() {
cart = new ShoppingCart();
}
public void testShoppingCartEmpty() throws Exception {
assertEquals("Cart should be empty", 0, cart.getNumItems());
}
public void testItemAdded() throws Exception {
LineItem item = new LineItem();
cart.addItem(item);
16
assertEquals("Cart should contain 1 item",
1, cart.getNumItems());
}
}
SetUp() metoda se pokreće automatski, odmah prije početka svake test metode. Vrijedno je istaći
tačku da se ne pokreće samo jednom za cijeli test slučaj. Umjesto toga, pokreće se jednom za
svaku posebnu test metodu, tako da za svaku test metodu, garantiramo, dobar, svjež primjer
KupovneKorpe. Postoji takođe teardown() metoda koja radi obrnuto od setup() i korisna je za
zatvaranje vanjskih izvora kao što su veze baza podataka ili inpu/output tokovi. TearDown() se
pokreće odmah nakon svake pojedinačne metode.
Kroz veći dio ostatka ovog rada, proći ćemo kroz primjere da pokažemo kako pokretati testove
jedinica direktno i test slučajeva, koji su pokretani od strane kontrolora sa robusnih dijagrama a
koji su pokretani sa korištenih slučajeva. Naš cilj je da pružimo detaljno razumijevanje kako da
povežemo te testove zajedno sa zahtjevima na mikroskopskom nivou.
1.6. Pisanje efektivnih testova jedinica
Prije nego počnemo na primjeru, vrijedno je istaći neke najbolje prakse za pisanje dobrih testova
jedinica. Cijela knjiga je posvećena testovima jedinica, ali tehnike efektivnih testova jedinica sa
perspective dizajnom-vođenog testiranja mogu se sažeti veoma jezgrovito:
• Čuvanje testova jedinica precizno. Generalno, trebamo pokriti jedan test slučaj jednom
klasom testova jedinica i različitom permutacijom ili tvrdnjom test slučaja u svakoj test
metodi.
• Uvjeriti se da svaka test metoda testira tačno jednu stvar.
• Povezati testove jedinica sa klasama i metodama koju testiramo.
• Povezati testove jedinica sa objektima u preliminarnom dizajnu.
• Podjednako tretiranje koda test jedinica sa istim poštovanjem kao sa proizvodnim kodom.
17
• Izbjegavanje duplikata u testu.
• Uvjeriti se da se testovi izvode 100% uspješno.
• Koristiti mock objects(lažne predmete), ali se ne oslanjati previše na njih.
U slijedećem poglavlju proći ćemo kroz primjer Internet knjižare, sve od dijagrama robusnosti,
do JUnit testova.
2. Dizaj vođen testiranjem u praksi
U ovom dijelu, ilustrirat ćemo teoriju iz prvog dijela ovog poglavlja, korištenjem projekta
Internet knjižare. Podsjetili smo se na detaljni dizaj iz 9 poglavlja i ovaj put, bez direktnog
prelaska na kodiranje, prvo testiramo neke test slučajeve direktno is robusnih dijagrama, i
spajamo ih sa detaljnim dizajnom. Onda koristimo test slučajeve da potvrdimo da:
• detaljni dizajn se poklapa sa korištenim slučajem
• kod se poklapa sa detaljnim dizajnom i čini ono za šta je namijenjen
2.1. Testovi jedinica za Internet knjižaru
Da napišemo test jedinica za Internet knjižaru, uzet ćemo kontrolore sa robusnih dijagrama za
korištene slučajeve Prikaži Detalje Knjige (Show Book Details) i Napiši korisničku recenziju
(Write Customer Review), proizvesti test slučajeve za njih i onda napisati test jedinica baziran na
test slučajevima. Ovaj korak bi trebali uraditi prioritetno za pisanje koda, tako da kada kodiramo,
imamo dovoljan set testova jedinica da sastavimo i testiramo ponovo. Slika 6. prikazuje dijagram
test slučaja. Ovaj dijagram je proizveden sa robusnog dijagrama za Prikaži Detalje Knjige.
18
Slika 6. Generirani test slučaj za prikaži detalje knjige korišteni slučaj
Prikaži Stranicu Knjiga Nije Pronađena i test slučaj su prikazani crvenom bojom jer se radi o
alternativnim kursevima.
Da podsjetimo, svaki kontroler sa robusnog dijagrama dobija svoj test slučaj, i u svakom test
slučaju smo kreirali jedan ili više test scenarija. Za svaki test slučaj, kreiramo klasu testova
jedinica i za svaki test scenario kreiramo metodu test jedinica. Proći ćemo kroz ovaj process
jednom za svaki test slučaj (prikazan u slici 6.)
19
2.2. Testiranje Prikaz Početne Stranice
U ovom dijelu, kreirat ćemo test scenario za Kontrolora Prikaz Početne Stranice,
najjednostavnijeg u grupi, i onda ćemo napisati JUnit test klasu.
Slijedi dio teksta korištenog slučaja koji je vezan za ovog kontrolora:
Kupac upiše u URL adresu za internet knjižaru početnu stranicu. Sistem prikaže listu knjiga iz
kataloga na početnoj stranici u obliku linkova koje možete otvoriti.
Test slučaj za ovog kontrolora je jednostavan, zapravo, trebamo samo jedan test scenario za ovaj
test slučaj zato što postoji malo toga što može krenuti “naopako”. Da dodamo test scenario u EA,
dvoklik na test slučaj i onda u prozorčiću Postavke kliknemo Scenario tab.(slika 7.) Postoji
samo jedan test scenario za ovaj test slučaj, tako da možemo očekivati da vidimo jednu test
metodu u klasi testa jedinica.
Slika 7. Dodavanje test scenarija za test slučaj Prikaz početne stranice
20
Slijedi kostur JUnit testa za ovaj test slučaj:
package test.com.iconixsw.bookstore.web;
import junit.framework.*;
public class DisplayHomePageTest extends TestCase {
public DisplayHomePageTest(String testName) {
super(testName);
}
public void testDisplayHomePage() throws Exception {
}
}
Test proširuje TestSlučaj, klase JUnit. U JUnit, bilo koja metoda čije ime počinje sa test, je
automatski prepoznata kao test metoda, tako da u ovom slučaju imamo samo jednu test metodu,
testPrikazPočetneSTranice() koja je izvedena iz test scenarija prikazanog na slici 7. Ako test
slučaj ima na primjer tri test scenarija, onda ćemo vidjeti tri test metode umjesto samo jedne.
Slika 8 prikazuje izvedeni sekvencijalni dijagram PrikazDetaljaKnjige koji je vezan za ovaj test
slučaj.
Slika 8. Izvod iz sekvencijalnog dijagrama Prikaži početnu stranicu
21
U ovom slučaju PočetnaKontroler se testira, i predmet poziva granični objekt, DispečerServlet.
Test jedinica mora potvrditi da rezultati sa nosiocZahtjeva() je ono što očekujemo, s obzirom da
se vrijednosti prenose. Metoda je:
public void testDisplayHomePage() throws Exception {
HomeController homeController = new HomeController();
ModelAndView modelAndView =
homeController.handleRequest(null, null);
assertEquals("Should be viewing home.jsp",
"home",
modelAndView.getViewName());
}
Sada kada imamo test, dobro je vježbati i pokušati učiniti ga neuspješnim, to će dokazati da će
raditi kada nastupi i stvarni neuspjeh u budućnosti. Možemo to uraditi pisajući praznu
nosiocZahtjeva() metodu:
package com.iconixsw.bookstore.web;
// import . . .
public class HomeController implements Controller {
public ModelAndView handleRequest(
HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException {
22
return new ModelAndView("");
}
}
Ova verzija PočetnaKontroler, vraća prazno ime. Ako pokrenemo ponovo test jedinica dobit
ćemo slijedeće:
____________________________________________________________________________
.F
Time: 0.015
There was 1 failure:
1) testDisplayHomePage
(test.com.iconixsw.bookstore.web.DisplayHomePageTest)
junit.framework.ComparisonFailure:
Should be viewing home.jsp. expected:<home> but was:<>
at test.com.iconixsw.bookstore.web.
DisplayHomePageTest.testDisplayHomePage
(DisplayHomePageTest.java:17)
FAILURES!!!
Tests run: 1, Failures: 1, Errors: 0
______________________________________________________________________
23
To pokazuje da test mehanizam radi, pa možemo implementirati nosiocZahtjeva “pravilno”:
public ModelAndView handleRequest(
HttpServletRequest request,
HttpServletResponse response)
throws ServletException, IOException {
return new ModelAndView("home");
}
Pokretanjem testa trebali bi dobiti slijedeće :
_____________________________________________________________________________
.
Time: 0.016
OK (1 test)
______________________________________________________________________
U test metodi loše kreiranje je stvaranje resursa koji bi trebali biti kreirani u setup() metodi koja
se poziva prije svake test metode. Refaktorisani kod sada izgleda ovako:
package test.com.iconixsw.bookstore.web;
// import statements omitted
public class DisplayHomePageTest extends TestCase {
private HomeController homeController;
public DisplayHomePageTest(String testName) {
super(testName);
}
public void setUp() throws Exception {
24
homeController = new HomeController();
}
public void tearDown() throws Exception {
homeController = null;
}
public void testDisplayHomePage() throws Exception {
ModelAndView modelAndView = homeController. handleRequest
(null, null);
assertEquals("Should be viewing home.jsp.",
"home",
modelAndView.getViewName());
}
}
Preokrenuli smo početnaKontroler u privatnu varijablu i premjestili kod koji kreira u setUp()
metodu. Takođe smo dodali teardown() metodu da podesimo početnaKontrolor nazad na
početak. Ovo nije neophodno ali je dobro radi uštede radne memorije u budućnosti. Povratak na
test pokazuje da ni jedna tvrdnja nije netačna. Proći ćemo kroz isti process za ostale kontrolore
prikazane u korištenom slučaju Prikaži Detalje knjige.
2.3. Pokretanje testova iz test paketa
Nismo još uvijek pokazali kako da pokrenemo sve testove iz jednog pokušaja. To je jednostavno
s JUnit-om. Moguće je grupirati sve klase testova jedinica zajedno u samo jedan test paket, i
pokrenuti ga:
package test.com.iconixsw.bookstore;
import test.com.iconixsw.bookstore.web.*;
import junit.framework.*;
25
public class BookstoreTestSuite {
public static Test suite() {
TestSuite suite = new TestSuite();
suite.addTestSuite(DisplayHomePageTest.class);
// add more tests here . . .
return suite;
}
public static void main(String[] args) {
junit.textui.TestRunner.run(suite());
}
}
Ako pokrenemo InternetKnjižaraTestPaket iz komande, glavna metoda bit će nazvana paket(),
koji će skupiti sve individualne test slučajeve zajedno, i vratiti ih zajedno u jedan predmet. Ovo
će onda biti prebačeno u JUnit TestPokretač, koji proizvodi “OK” i “Neuspjeh” (“failures”) tekst
rezultate koje ćemo vidjeti u primjeru.
Kako pišemo više test klasa, dodajemo ih u test paket da bi se onda mogle pokrenuti zajedno.
Ako se testovi izvode dovoljno brzo, to znači da možemo pokrenuti sve testove svaki put kada
promijenimo nešto ili dodamo nešto novo.
2.4. Testiranje Preuzmi Detalje Knjige Kontroler (Retrieve Book Details
Controller)
U ovom dijelu, kreiramo test scenario za Preuzmi Detalje Knjige Kontroler, i onda pišemo i
pokrećemo njegovu JUnit test klasu. Ako spojimo Preuzmi Detalje Knjige Kontroler sa
slijedećim tekstom:
Kupac odabere link na početnoj stranici i sistem preuzme detalje knjige od odabrane knjige
26
onda ovo sugerira da bi test trebao potvrditi da su knjige preuzete tačno iz baze podataka.
Da dodamo test slučaj u EA, dvoklikom otvorimo prozorčić Postavke i odaberemo Scenario tab.
Onda možemo dodati osnovni i alternativni scenario u test slučaj. Slika 9 prikazuje dva test
scenarija koja smo dodali za Preuzmi Detalje Knjige kontrolor/test slučaj.
Slika 9. Test scenario za Preuzmi detalje Knjige
Sada kada smo dodali test scenario potrebno je nadograđivanje korištenog slučaja, robusni
dijagram kako bi nacrtali sekvencijalni dijagram. Slijedeća etapa je kreiranje kostura testa
jedinica za ovaj test slučaj, korištenjem scenarija koji smo dodali. Sada ćemo pokazati kostur test
27
scenarija za Preuzmi Detalje Knjige kontroler/test slučaj. Stvarna test metoda (izvedena iz
scenarija test slučaja) prikazana je crvenom bojom:
package test.com.iconixsw.bookstore.dao;
import junit.framework.*;
/**
* Test case for the Retrieve Book Details controller.
*/
public class RetrieveBookDetailsTest extends TestCase {
public RetrieveBookDetailsTest(String testName) {
super(testName);
}
public void setUp() throws Exception {
}
public void tearDown() throws Exception {
}
public void testBookIdFound() {
}
public void testBookIdNotFound() {
}
}
Metode testIdKnjigaPronađena() (testBookIdFound()) i testIdKnjigaNijePronađena()
(testBookIdNotFound()) su izvedene direktno iz dva scenarija prikazana na slici 9. Kao što smo
ranije rekli, želimo da testiramo ID Knjiga pronađena (ili nije pronađena) direktno iz baze
podataka. Zlatno pravilo za testove jedinica je to da oni trebaju imati mogućnost brzog
pokretanja. Ako testovi jedinica se ne pokreću brzo, onda se programeri neće uopšte truditi da ih
28
pokreću tokom programiranja. Iz ovog razloga, dobra je praksa pokušati izbjeći pisanje testova
koji ostvaruju vezu sa vanjskim izvorima (npr. baza podataka). Povezivanje sa bazom podataka
(čak i lokalnom) i pokretanje upita ili nadogradnji može učiniti testove jedinica da se pokreću
neproporcionalno sporo, posebno kada je ista postavka ili kod ponovljen više od stotinu puta.
Ali, ako ne možemo uključiti kod baze podataka u brzi test, kako da zapravo testiramo bilo šta?
Jedan odgovor je da koristimo tzv. mock objekte (lažne). Na primjer, možemo zamijeniti naš
JDBC specifične DAO klase sa “lažnom” verzijom, čija je osnovna misija da osigura iste
podatke test jedinica, iznova i iznova, čak veoma brzo.
Dodat ćemo neke kodove u testnu klasu da preuzmemo ID Knjige i da potvrdimo da je primljen:
private BookDao bookDao;
public void testBookIdFound() {
Book book = bookDao.findById(1);
assertNotNull("ID 1 should be found", book);
}
Ako pokušamo da pokrenemo test jedinica sada, dobit ćemo NullPointerException, zbog toga što
BookDao (knjiga osigurana) nije učitan:
public void setUp() throws Exception {
bookDao = new MockBookDao();
}
Očito se ovo neće sastaviti iz razloga što ne postoji MockBookDao, i sada je dobro vrijeme da ga
ubacimo:
package com.iconixsw.bookstore.dao.mock;
// import statements omitted . . .
public class MockBookDao implements BookDao {
29
private HashMap booksById;
public MockBookDao() {
initData();
}
public List findAll() throws DataAccessException {
return (List) booksById.values();
}
public Book findById(int bookId) throws DataAccessException {
return (Book) booksById.get(new Integer(bookId));
}
private void initData() {
Book favWidgets = new Book();
favWidgets.setId(1);
favWidgets.setTitle("My Favorite Widgets");
Book uncommon = new Book();
uncommon.setId(2);
uncommon.setTitle("The Uncommon Event");
booksById = new HashMap();
booksById.put(new Integer(1), favWidgets);
booksById.put(new Integer(2), uncommon);
}
}
30
BookDao čini najjedonostavniju moguću stvar, a to je kreiranje par objekata Knjiga i stavljanje
tih objekata u HashMap, ključem po ID knjige. Podaci se nikada ne spašavaju na vanjski disk
već u internoj memoriji.
Sada kada imamo sastavljen test, trebali bi ga pokrenuti kroz JUnit, ali bi prvobitno trebali
vidjeti neuspjeh testa kako bi potvrdili da test radi. Da bi to uradili samo ćemo kratko promijeniti
initData() metodu na slijedeći način:
Book favWidgets = new Book();
favWidgets.setId(5);
favWidgets.setTitle("My Favorite Widgets");
Jednostavno smo promjenili 1 u 5 tako da lažni DAO ne vrati knjigu sa ID oznakom 1.
Pokretanje testa sada će donijeti slijedeće rezultate:
_____________________________________________________________________________
.F
Time: 0
There was 1 failure:
1) testBookIdFound
(test.com.iconixsw.bookstore.dao.RetrieveBookDetailsTest)
junit.framework.AssertionFailedError:
ID 1 should be found
at test.com.iconixsw.bookstore.dao.
RetrieveBookDetailsTest.
testBookIdFound(RetrieveBookDetailsTest.java:29)
FAILURES!!!
Tests run: 1, Failures: 1, Errors: 0
____________________________________________________________________
31
Na ovaj način možemo se uvjeriti da će test raditi ispravno kada dođe do stvarnog neuspjeha
testa. Sada kada vratimo vrijednost ponovo 1 i uradimo ponovo test dobit ćemo slijedeće
rezultate:
______________________________________________________________________________
.
Time: 0
OK (1 test)
______________________________________________________________________
Trenutno testiramo samo jedan način, odnosno Knjiga pronađena, trebamo to uraditi i za
KnjigaNijePronađena:
public void testBookIdNotFound() {
Book book = bookDao.findById(-1);
assertNull("ID -1 should not be found", book);
}
2.5. Testiranje Prikaži Detalje Knjige Kontrolor
Tekst u korištenom slučaju povezan za ovaj test slučaj je:
… sistem preuzima detalje knjige za izabranu knjigu i prikazuje ih na Pogledaj Detalje Knjige
stranici….
Slika 10 prikazuje test scenario koji je dodat u EA za ovaj test slučaj.
32
Slika 10. Test scenario za Prikaži Detalje knjige kontrolor/test slučaj
Tu su tri scenarija: “Stranica prikazana”, “Detalji knjige pronađeni” i “Detalji knjige nisu
pronađeni”… Jedan od ovih scenarija nije u redu. Vraćanjem u test slučaj prikazan u slici 6,
uviđamo da tamo već postoji podjeljen alternativni test za test slučaj gdje detalji knjige nisu
pronađeni.
Tako za ovaj test slučaj, zapravo postoje dva test scenarija: “Prikazana stanica” i “Detalji knjige
pronađeni”. Oba ova su osnovni test scenario, što ima smisla, zato što test slučaj sam po sebi, je
za jednog kontrolora u osnovnom slučaju korištenog slučaja. Slika 11. prikazuje izvod iz
sekvencijalnog dijagrama Prikaži Detalje Knjige.
33
Slika 11. Izvod iz sekvencijalnog dijagrama Prikaži Detalje Knjige
Zapamtimo da trebamo pisati test sa tačke gledišta objekta zvanog kontrolor. Pozivajući objekt je
uglavnom granični objekt, iako može takođe biti i drugi kontrolor. Želimo da pozivi idu u
kontrolor koji se testira. Kao što možemo vidjeti u slici 11, to znači testiranje dvije metode:
rukovati() (handle()) i provjeriKnjigaPronađena() (checkBookFound()).
Slijedi kostur test klase za Prikaži Detalje Knjige kontrolor/test slučaj (test metode su prikazane
crvenom bojom):
package test.com.iconixsw.bookstore.web;
import junit.framework.*;
/**
* Test case for the Display Book Details Page controller.
*/
public class DisplayBookDetailsPageTest extends TestCase {
public DisplayBookDetailsPageTest(String testName) {
34
super(testName);
}
public void setUp() throws Exception {
}
public void tearDown() throws Exception {
}
public void testPageDisplayed()throws Exception {
}
public void testBookDetailsFound()throws Exception {
}
}
Provjeravanjem slike 11, željet ćemo da kreiramo DetaljiKnjigeKontrolor objekat da poguramo i
podstaknemo, i imalo bi smisla da to stavimo u setup() tako da isti osnovni kod bude podijeljen
od strane obje test metode:
public void setUp() throws Exception {
bookDetailsController = new BookDetailsController();
bookDetailsController.setBookDao(new MockBookDao());
}
private BookDetailsController bookDetailsController;
U setUp(), sada kreiramo novi DetaljiKnjigeKontrolor:
public void setBookDao(BookDao bookDao) {
this.bookDao = bookDao;
}
private BookDao bookDao;
35
Naredni kod pokazuje početak prve metode:
testPageDisplayed():
public void testPageDisplayed() throws Exception {
Book command = new Book();
command.setId(1);
ModelAndView modelAndView =
bookDetailsController.handle(null, null, command, null);
// assert...
}
Sada možemo dodati handle()-rukovati metodu u DetaljiKnjigeKontrolor:
protected ModelAndView handle(
HttpServletRequest request,
HttpServletResponse response,
Object command,
BindException errors) throws Exception {
return null;
}
U početku to nas vraća nuli, zato što želimo da budemo u mogućnosti da prvo pokrenemo test i
vidimo neuspjeh. Nazvat ćemo metodu “test” tako da kasnije znamo da je za test jedinica:
public ModelAndView testHandle(Book command)
throws Exception {
return handle(null, null, command, null);
}
36
Jedini parametar koji je zapravo važan je Knjiga. Sada možemo ponovo napisati test metodu za
korištenje ove nove metode:
ModelAndView modelAndView =
bookDetailsController.testHandle(command);
Provjerom sekvencijalnog dijagrama u slici 11., vidimo da druga metoda
provjeraKnjigaPronađena(), je zapravo privatna metoda nazvana rukovati() (Handle()) tako da ne
trebamo pisati specifičnu metodu za to. Umjesto toga, izlaz iz provjeraKnjigaPronađena() će
doprinijeti eventualnim izlazima iz rukovanje(), koji trebamo testirati. Sada možemo sastaviti
ostatak, i očekivati neuspjeh.
Slijedeći korak je da napišemo stvarni kod za rukovanje() metodu, osim ako nismo dodali neku
tvrdnju u dvije metode još uvijek, tako da trenutno ne testiramo ništa. To je veliki skup kodova
sa mnogo duplikata, koje ćemo kasnije pretvoriti u nešto kompaktnije.
public class DisplayBookDetailsPageTest extends TestCase {
public DisplayBookDetailsPageTest(String testName) {
super(testName);
}
public void setUp() throws Exception {
bookDetailsController = new BookDetailsController();
bookDetailsController.setBookDao(new MockBookDao());
}
private BookDetailsController bookDetailsController;
public void tearDown() throws Exception {
bookDetailsController = null;
}
37
public void testPageDisplayed() throws Exception {
Book command = new Book();
command.setId(1);
ModelAndView modelAndView =
BookDetailsController.testHandle(command);
assertEquals("The bookdetails page should be displayed",
"bookdetails",
modelAndView.getViewName());
}
public void testBookDetailsFound() throws Exception {
BookDetailsCommand command = new BookDetailsCommand();
command.setId(1);
ModelAndView modelAndView =
bookDetailsController.testHandle(command);
Map model = modelAndView.getModel();
Book book = (Book) model.get("book");
assertEquals("The book should have been found",
1,
book.getId());
}
}
Kao što možemo vidjeti, svaka test metoda radi manje ili više iste stvari : postavlja komandni
objekt Knjiga, dodjeljuje mu ID, koji onda prenosi u DetaljiKnjigeKontrolor i dobija
ModelIPogled objekat nazad. Dvije metode testStranicaPrikazana() i
testDetaljiKnjigePronađeni() dodjeljuju ID broj 1, postojeći ID knjige iz razloga što su obje
metode u osnovi iste. Čini se da bi imalo smisla da prebacimo kod u setUp().
38
Stavljanjem koda u setUp(), dali bi do znanja da je ovo test postavka koda, a ne test kod, pa zbog
toga, prebacujemo ga u odvojene metode. Evo rezultirajućeg test koda (refaktorisani kod je
prikazan crvenom bojom):
private Book command;
public void setUp() throws Exception {
command = new Book();
command.setId(1);
}
public void testPageDisplayed() throws Exception {
ModelAndView modelAndView = callTestHandle();
assertEquals("The bookdetails page should be displayed.",
"bookdetails",
modelAndView.getViewName());
}
public void testBookDetailsFound() throws Exception {
ModelAndView modelAndView = callTestHandle();
Map model = modelAndView.getModel();
Book book = (Book) model.get("book");
assertEquals("The book should have been found.",
1,
book.getId());
}
private ModelAndView callTestHandle() {
return bookDetailsController.testHandle(command);
}
39
Pokretanjem ove klase testova, dobijamo crvene oznake svugdje zato što rukovanje() metoda još
uvijek vraća nulu, što možemo popraviti. Da zaokružimo ovaj test slučaj, možemo sad sigurno
dodati realni kod u rukovanje() metodu u DetaljiKnjigeKontrolor:
protected ModelAndView handle(
HttpServletRequest request,
HttpServletResponse response,
Object command,
BindException errors) throws Exception {
Book book = (Book) command;
book.load(bookDao);
return new ModelAndView("bookdetails", "book", book);
}
Pokretanjem ovog koda kroz različite testere jedinica dobijamo zeleno svjetlo, što znači da je test
zadovoljio.
2.6. Testiranje Prikaz Stranica Knjiga Nije Pronađena Kontrolor (Display Book
Not Found Page Controller)
U završnom test slučaju, testiramo alternativne kurseve u kojima je ID knjige ne postoji. Tekst
korištenog slučaja, koji povezuje sa ovim test slučajem je:
ALTERNATIVNI KURSEVI:
Knjiga nije pronađena: Sistem prikazuje stranicu Detalji Knjige Nisu Pronađeni
Slika 12. prikazuje test scenario koji je dodat u EA za ovaj test slučaj.
40
Tu su dva test scenarija: “Stranica Knjiga Nije Pronađena Prikazana” i “Detalji Knjige Nisu
Pronađeni” . Oba ova scenarija su kategorizovana kao alternativni test scenariji, koji imaju
smisla zato što je ovo test slučaj za kontrolora na alternativnom kursu u korištenom slučaju.
Slika 13. prikazuje izvod sekvencijalnog dijagrama koji pokriva dizajn za ovaj alternativni kurs.
Slika 12. Test scenarij za Knjiga Nije Pronađena kontrolor/test slučaj
41
Slika 13. Izvod iz sekvencijalnog dijagrama Prikaži detalje knjige za alternativne kurseve
Pisanje kostura koda za klasu testa jedinica je jednostavna stvar prolaska kroz test scenarije za
ovaj test slučaj i dodavanje test metode za svaki scenario. Test metode su prikazane crvenom
bojom u slijedećem kodu:
public class DisplayBookNotFoundPageTest extends TestCase {
public DisplayBookNotFoundPageTest(String testName) {
super(testName);
}
public void setUp() throws Exception {
}
public void tearDown() throws Exception {
}
public void testBookNotFoundPageDisplayed() throws Exception {
42
}
public void testBookDetailsNotFound() throws Exception {
}
}
Osnovni kod za ovu klasu će biti identičan osnovnom kodu prethodnog test slučaja. Zapravo, kod
koji ide u obje test metode je takođe veoma sličan. Slika 14. prikazuje dvije klase koje bi trebale
biti spojene.
.
Slika 14. Dijagram klase za dva test slučaja Detalji Knjige (prvi pokušaj)
43
Problem sa ovim dizajnom je taj da kada pokrenemo StranicaPrikazKnjigaNijePronađenaTest,
test iz “roditeljske” klase testova će se takođe pokrenuti. Možemo uzeti “promodernistički”
pristup i izbjeći “naslijedstvo”u korist agregacije. Drugim riječima, možemo premjestiti
zajednički kod u odvojene pomoćne klase za oba test slučaja.(slika 15.)
Slika 15. Dijagram klase za dva Detalji knjige test slučaja
Završit ćemo ovo poglavlje sa 10 najvećih grešaka dizajnom vođenog testiranja.
44
3. Deset najvećih grešaka dizajna vođenog testiranjem
Slijedi lista 10 najvećih grešaka koje ne bi trebali raditi:
10. Pretjerivati sa mock(lažnim) objektima.
9. Duplicirati scenarije alternativnih kurseva u alternativne test scenarije za osnovne kurs
kontrolore.
8. Zaboraviti da povežemo testove sa zahtjevima.
7. Ostaviti testiranje nakon što je napisan kod.
6. Zamijeniti testiranje sa dizajnom.
5. Ignorisati vruće tačke problema.
4. Koristiti nasilno testiranje umjesto identifikovanje, pa onda ciljanje “vrućih tački” iz
preliminarnog dizajna.
3. Koristiti pogrešnu vrstu testiranja za pogrešnu situaciju.
2. Zaboraviti uraditi testiranje uopće.
1. Testirati toliko temeljito da nikada ne objavite proizvod.
45
Slika 16. Aktivnosti testiranja u toku faze implementacije
46
Zaključak
U ovom poglavlju pokrili smo različite oblike korištenih slučajeva – vođenih testiranjem i opisali
kada bi trebali koristiti svaki od njih. Dizaj vođen testiranjem je metoda koja nam omogućava
proizvodnju test slučajeva, kako bi se uvjerili da su svi naznačeni scenariji. Ovu metodu možemo
takođe koristiti da napišemo izvršne testove testnih slučajeva. Naveli smo i definisali vrste
testova koje se koriste i objasnili kako i kada se oni koriste.
Takođe smo prošli kroz primjer dizajna vođenog testiranjem na primjeru Internet knjižare i
napisali neke testove jedinica da pokrijemo Prikaži Detalje Knjige – korišteni slučaj.
Slika 16. pokazuje gdje smo trenutno. Aktivnosti koje su urađene u ovom poglavlju su prikazane
crvenom bojom. Omogućili smo detaljan prikaz i diskusiju primjera urađenog u Agilnom
dodataku ICONIX Procces-a u Enterprise Arhitect-u. Dodavanje osnovnih i alternativnih
scenarija kao i postupak transformiranja robusnih dijagrama u sekvencijali ili dijagram test
slučaja.
Jedna od ključnih tački u ovom poglavlju je da testovi ne dokazuju puno ako nisu uvezani na
mikroskopskom nivou sa zahtjevima.
Na kraju smo naveli 10 greški koje nikako ne bismo trebali činiti u procesu testiranja. U
slijedećem poglavlju govorit ćemo o zahtjevima i pokazat ćemo kako se oni uklapaju u ukupni
proces.
47
Bibliografija
D. Rosenberg, M Stephens, Use case driven object modeling with UML: Theory and
Practice, 2007.god.
48
Popis slika i tabela
Slike:
Slika 1. „V“ model softverskog testiranja primjenjljivog u ICONIX Procces-u
Slika 2. Pregled DDT-a
Slika 3. Korištenje Agilnog ICONIX/EA dodatka za generiranje dijagrama
Slika 4. Generacija test slučajeva u EA
Slika 5. Dodavanje test scenarija u EA
Slika 6. Generirani test slučaj za prikaži detalje knjige korišteni slučaj
Slika 7. Dodavanje test scenarija za test slučaj Prikaz početne stranice
Slika 8. Izvod iz sekvencijalnog dijagrama Prikaži početnu stranicu
Slika 9. Test scenario za Preuzmi detalje Knjige
Slika 10. Test scenario za Prikaži Detalje knjige kontrolor/test slučaj
Slika 11. Izvod iz sekvencijalnog dijagrama Prikaži Detalje Knjige
Slika 12. Test scenarij za Knjiga Nije Pronađena kontrolor/test slučaj
Slika 13. Izvod iz sekvencijalnog dijagrama Prikaži detalje knjige za alternativne kurseve
Slika 14. Dijagram klase za dva test slučaja Detalji Knjige (prvi pokušaj)
Slika 15. Dijagram klase za dva Detalji knjige test slučaja
Slika 16. Aktivnosti testiranja u toku faze implementacije
Tabele:
Tabela 1. Različite vrste testova i kada ih primjeniti
Tabela 2. Testovi koji prolaze kroz razvojni proces
49