Better Decisions
For Better Life

Aanpak unit-test binnen een Agile BI-project

-

agileDit artikel is onderdeel van de themareeks BI & Techniek, bedoeld om de meer technische aspecten van BI voor het voetlicht te krijgen. Het is geschreven voor project-managers en ontwikkelaars binnen de BI, die zich afvragen hoe agile zich in de BI-praktijk staande houdt.

Er is al veel geschreven over de aanpak van testen binnen Agile BI-projecten. Maar dat is theorie, in de praktijk blijkt testen toch een lastig onderwerp, waardoor het testtraject vaak een ondergeschoven kindje binnen het project wordt. Dit blog beschrijft een aanpak om de voorbereiding - die altijd voorafgaat aan het functioneel testen - zo veel mogelijk te beperken en toch een adequate, automatische unit-test uit te kunnen voeren. Het doel is om uiteindelijk meer moeite en tijd te kunnen stoppen in het testen zelf en niet in de voorbereiding (en het automatiseren) ervan. De aanpak die ik hier beschrijf vloeit uit eerdere eigen ervaringen binnen verschillende Agile BI-projecten.

Probleem
In de praktijk wordt een testtraject binnen Agile BI-projecten vaak als tijdrovend ervaren. We moeten immers testdata genereren die afdoende alle mogelijke paden en scenario’s afdekt.  Alle voorkomens van data, hoe die data zich gedraagt binnen de opgestelde omgeving en welke resulterende foutpaden kunnen worden bewandeld, moeten worden geïnventariseerd om ze te kunnen toetsen. Lastig hierbij is het verkrijgen van een testset die representatief is. Uit praktische overwegingen gaat men veelal uit van een tot vijf procent van de productiedata, maar een dergelijke set hoeft lang niet alle gewenste testsituaties te bevatten. In een Agile BI-traject is testen en vooral regressietesten een serieus aan te pakken onderwerp. Bij de bouw van nieuwe software loopt alles immers nog lekker vlotjes, maar na een paar increments gaat regressietesten steeds meer moeite en tijd kosten, waarbij de tijdsgrenzen van de twee-wekelijkse cyclus je al snel parten gaat spelen.

Investeer in een flexibele, gedegen testset
Even los van privacy-eisen, is het vaak een goede en pragmatische oplossing om een set vanuit productie te kopiëren en beschikbaar te stellen. Vooraf moet je dan wel een analyse doen om te bepalen welke data vaak voorkomt in productie. Zo kan men bepalen welke waarden vaak voorkomen en welke uitzonderingen er zijn. Die analyse kun je met behulp van profiling tools en/of queries uitvoeren. Profiling tools zijn natuurlijk een stuk sneller en overzichtelijker, maar soms ook wat duur en niet altijd beschikbaar. Uit de resultaten van de analyse selecteer je een gevarieerde set die zo representatief is dat alle voorkomende situaties gedekt zijn. Verder kun je deze testset aanvullen met eigen testsets waarmee je (vanuit de logica van de software afgeleide) mogelijk voorkomende foutpaden en/of uitzonderingssituaties afdekt. Hierbij is ook de interactie met de gebruikers belangrijk die de verwerkingslogica vaak functioneel goed kennen. De startset wordt dan iedere keer bijgehouden zodra nieuwe onvoorziene gevallen ontdekt worden.

Hou hierbij rekening met de doorlooptijd en beheerbaarheid van de testsets. De testsets moeten snel geladen kunnen worden, het uitvoeren van de test moet snel lopen en de testset moet makkelijk uit te breiden zijn. Dit is een incrementeel proces. Dus bij iedere nieuwe functionaliteit dient de testset uitgebreid te worden met testgevallen.

Vanuit eigen ervaring is dit proces goed haalbaar en uiteindelijk minder arbeidsintensief. Als je hierin investeert aan het begin van een project (zoals in Sprint 0 bij Scrum) kun je er alleen maar profijt van hebben. Het is echter wel noodzakelijk om dit bij het begin van een traject op te pakken, anders blijkt het vaak lastig om alles later nog eens in te halen. Hoe langer je dit uitstelt, hoe groter de inhaalslag is. In Scrum termen kan men dan op een gegeven moment spreken van een epic aan testactiviteiten.

Investeer in automatisch testen
Door het incrementele karakter van Agile projecten, zul je vaak regressietests moeten doen. Daarom is het belangrijk om dit proces te automatiseren. Bij ieder increment investeer je dan alleen in het aanmaken van testsets voor je nieuwe functionaliteit. Het regressietesten op eerder opgeleverde functionaliteit zal daarnaast automatisch moeten gaan lopen. Binnen Agile BI is automatisch testen in de praktijk dus onmisbaar, maar daarvoor moet je wel vooraf een automatisch proces inrichten.

Om hier op een pragmatische manier mee om te gaan, wordt vaak een (product-)risico-analyse uitgevoerd, door impact van en kans op falen te bepalen en met elkaar te vermenigvuldigen om tot een risico-verwachtingswaarde te komen. Je testaanpak wordt dan bijvoorbeeld 'licht', 'gemiddeld' of 'zwaar', direct afhankelijk van de uitkomst van je risico-analyse. Bij een risico-verwachtingswaarde ‘licht’ zou je bijvoorbeeld kunnen volstaan met tellingen over een ontwikkelset. Bij een risico-verwachtingswaarde 'zwaar' kies je dan ook een 'zware' testaanpak, waarbij bijvoorbeeld alle delen van de geïmplementeerde logica intensief getest moeten worden, gebruikmakend van een complete en slimme testset gevolgd door een complete vergelijkingstest op detail-niveau.

Voorbeeld:
Ik heb een testset in de vorm van een brontabel A. Ik verwacht dat mijn ETL-software vanuit A een resultaat levert in de vorm van B. Die set kan ik handmatig gaan samenstellen, maar het is nog sneller  om door middel van een SQL query de geïmplementeerde logica na te bootsen in SQL (i.e. reverse engineering). Deze query levert een verwachte output set B. Mijn te testen proces levert, vanuit dezelfde brontabel A, de werkelijke output set C. Nu kan ik door middel van SQL Except bepalen of er verschillen bestaan tussen mijn verwachte output set B en mijn werkelijke output set C. En dat natuurlijk in twee richtingen: B except C en daarna C except B. Een lege result-set betekent dan foutvrije software.

BI project

 

Wanneer je dit hebt bereikt, heb je al een eerste belangrijke stap gezet naar een pragmatische maar solide unit-test. Vervolgens gaan we dit automatiseren, zodat iedere keer als we dit proces draaien de test automatisch opstart. Het resultaat van beide vergelijkingen moet positief zijn (in dit geval een lege result-set opleveren).

De queries zouden onmiddellijk na het proces geplaatst kunnen worden, bijvoorbeeld in een stored procedure. Hierdoor start - elke keer als het ETL-proces wordt geraakt- de test automatisch. Als we een keten hebben ontwikkeld waarin alle componenten met elkaar verbonden zijn, dan zouden deze tests daarvan onderdeel moeten uitmaken. Het is hier belangrijk om te onthouden dat een test een bepaalde verwachte output levert en deze makkelijk geïntegreerd kan worden in het proces voor testdoeleinden.

Het opleveren en uitbreiden van de automatische testset wordt ieder increment vastgesteld en uitgebreid. Men zou dit kunnen opnemen als acceptatiecriterium of in geval van Scrum als onderdeel van de Definition Of Done.

SCRUM-StarterKit 
Download hieronder de gratis SCRUM-StarterKit met handige checklists en templates:

SCRUM-StarterKit
 
Dit blogartikel is geschreven door Abdel L’Ghdas