• No results found

Syftet med observationerna var att skaffa praktisk erfarenhet av AGT och att göra en kvalitativ utvärdering av att använda Selenium WebDriver för regressionster av C-Load.

För att öka validiteten kompletterades observationerna med ett antal intervjuer med Triona-medarbetare som har erfarenhet av att arbeta med Selenium WebDriver i andra projekt och förvaltningar.

6.1.1 Intervjuer

Fyra personer som hade någon form av erfarenhet av AGT intervjuades. Deras erfarenheter kom från ett projekt som kallas Transport Data Platform (TDP) och ett projekt som kallas Rask. TDP är en integrationsplattform för transportdata som knyter samman Clas Ohlsons affärssystem med butiker, leverantörer, lagersystem,

transportadministrationssystem och logistikaktörer. Rask är ett verksamhetssystem för hantering av alla aktiviteter kopplade till att avverka och sälja skog. Rask kan sägas vara både en förvaltning och ett projekt, då systemet är i drift samtidigt som omfattande utveckling av systemet pågår.

Intervjurespondenter:

 Hansi Henningson: Arkitekt och utvecklare i TDP

 Pontus Berglund: Utvecklare i TDP

 Cecilia Landberg: Testledare och kravanalytiker i Rask

 Olle Eriksson: Utvecklare i Rask

Transkriberingar av intervjuerna redovisas i bilaga 3

6.1.1.1 Intervju med arkitekt och utvecklare Hansi Henningson

I intervjun med Hansi Henningson visade det sig att han inte hade direkt erfarenhet av AGT, däremot av andra typer av automatiserade test, vilka han betraktar som helt nödvändiga för att kunna leverera kvalitet. Henningson hänvisade till Pontus Berglund för information om AGT.

6.1.1.2 Intervju med utvecklare Pontus Berglund

Syftet med intervjun var att ta del av en utvecklares praktiska erfarenhet av att använda Selenium WebDriver. Berglund berättade att behovet av automatiserad GUI-testning uppstod p.g.a. att ny funktionalitet ofta orsakade fel i GUI:t:

Vi insåg att när vi utvecklade så förstördes webinterfacet ibland utan att vi visste om det. Ändringar i API:et eller nästan var som helst som förstörde gränssnittet så då tittade jag lite på hur man kunde testa det automatiskt. (P. Berglund, personlig kommunikation, 4 maj, 2020)

Enligt Berglund valdes Selenium WebDriver för att det är det mest populära verktyget. Att skapa testskripten visade sig dock inte vara problemfritt. Att hitta bra selektorer, att vänta in att element finns tillgängliga på sidan och att det krävdes olika metoder för att utföra till synes samma sak på olika ställen i flödet, upplevdes av Berglund som problematiskt.

Berglund påpekar att det skulle bli betydligt enklare att skapa testskript om man vid utvecklingen av en applikation såg till att skapa unika ID:n på alla element. Testfallen innehöll också för mycket kod och logik. Berglund insåg att det skulle behövas ett lager av abstraktion, som POM, för att göra skripten tydliga och lätta att använda. Tid för att göra detta saknades dock. När applikationen sedan blev allt mer stabil minskade behovet av testerna och man beslutade att det inte var mödan värt att göra testskripten användbara.

Testerna kördes inte heller manuellt, utan man klarade sig utan dem.

Berglund är ändå positiv till idén med AGT:

Jag önskar att man hade mer sådana här tester. Det är svårt att testa GUI grundligt. Vi hade en söksida där man kunde söka på en mängd saker. När man testar den manuellt är det jobbigt att behöva söka efter sjutton olika saker [...] Det kan finnas fel som är svåra att upptäcka manuellt när man ska köra en hel “round trip” genom flödet.

(P. Berglund, personlig kommunikation, 4 maj, 2020)

Berglund påpekar att om man vill jobba i korta iterationer och driftsätta ofta, vilket är vanligt idag, är det nästan ett måste att automatisera regressionstester.

6.1.1.3 Intervju med testare och kravanalytiker Cecilia Landberg Syftet med intervjun var att ta del av erfarenheter från en testledare som arbetar i ett projekt där Selenium WebDriver används. Landberg skriver inte själv testskript, men är med och beslutar om vilka scenarier som är lämpliga att testa med Selenium WebDriver.

Landberg uppskattar att Rask-projektet använder Selenium WebDriver till ca 15% av det totala antalet regressionstester. Det är mestadels så kallade “happy flows” som

automatiserats, alltså test där användaren använder systemet på det sätt som är avsett.

Landberg berättar att det tar lång tid att köra testerna, men att Rask-projektet ändå upplever att de tjänar in tid, eftersom det går att köra testerna nattetid. Enligt Landberg är det ett problem att testerna är känsliga för förändring:

Min erfarenhet av det är det jag fått höra från utvecklarna och det är att det tar mycket lång tid. Det är därför vi kör på natten. Man tycker att testen är krångliga att underhålla. I ett projekt i förvaltning fungerar det nog bättre. Vi får ny kod varje dag och seleniumtesterna som är känsliga för förändring smäller ganska ofta då.

Därför använder vi inte så mycket seleniumtester som vi hade velat.

(C. Landberg, personlig kommunikation, 29 april, 2020)

6.1.1.4 Intervju med utvecklare Olle Eriksson

Syftet med intervjun var att ta del av en utvecklares praktiska erfarenhet av att använda Selenium WebDriver. Eriksson berättar att när han använde Selenium WebDriver hade kunden stort fokus på testautomation. Inte bara GUI-tester utan även enhetstester och integrationstester automatiserades. Applikationen var en så kallade “Single-Page Application”, byggd med Angular JS. Enligt Eriksson var det en utmaning att använda Selenium med Angular JS eftersom Selenium är gjort för äldre, serverbaserad webbteknik.

För att hantera den väntetid som uppstår när klienten gör asynkrona anrop mot ett REST API var det nödvändigt att skriva specialkod. De metoder för att hantera väntetid som finns inbyggda i Selenium fungerade inte. Om behovet av specialkod säger Eriksson:

Det går att lösa och hitta sätt runt men inte lika klart och tydligt som vi hade förväntat oss. [...] Det var ganska tidskrävande att få det fungera stabilt. Vi fick ibland falska negativa utfall som var knepiga att felsöka. Det här kokar nog ner till timingen och hur man väntar in saker.

(O. Eriksson, personlig kommunikation, 4 maj, 2020) Eriksson återkommer till svårigheter med att felsöka:

Det är tråkigt med Selenium att man måste hacka fram vissa lösningar. Det är svårt och tidskrävande att felsöka. Vi fick ofta sätta dom bästa utvecklarna på att felsöka.

(O. Eriksson, personlig kommunikation, 4 maj, 2020)

Eriksson säger att eftersom det är krångligt och dyrt att bygga testskripten vore det nog bäst att vänta med detta tills det mesta av funktionaliteten är på plats:

Vi började nog lite för tidigt i systemet jag var med i. Då lägger man mycket tid på att ändra testfallen för att GUI:t förändras ofta. Systemet rörde sig fort för vi var tio utvecklare. Så om någon byggde någon ny knapp så failade allas skript.

(O. Eriksson, personlig kommunikation, 4 maj, 2020)

POM användes i projektet. I samband med detta blev det snabbt tydligt att det är bra att ha id på alla element, eftersom Xpath är ganska skört.

Om valet att använda just Selenium WebDriver säger Eriksson följande:

Det fanns en resurs som kunde Selenium och hade ett ramverk färdigt så vi fick det lite till oss. Om jag hade gjort det idag så hade jag nog googlat fram lite andra alternativ. Som C-Load ser ut idag så är nog Selenium bra, men med modern web så skulle jag nog välja något annat.

(O. Eriksson, personlig kommunikation, 4 maj, 2020)

Eriksson har en klar bild av hur han hade gått till väga om han hade fått börja från början med projektet:

Hade jag gjort det från början så hade jag lagt så mycket det går på att få enhetstestning så bra som det bara går och så skulle jag lägga en del krut på integration som testar serverstacken och så skulle jag ha några GUI testfall som testar centrala flöden när dom är på plats och inte ska förändras så mycket. Att

testa hela systemet med Selenium tar för lång tid.(O. Eriksson, personlig kommunikation, 4 maj, 2020)

För att göra det lättare att komma fram till vad som gått fel när ett test fallerat användes en lösning där Selenium WebDriver sparade en bild av skärmen så snart något gick fel. Att kunna titta på dessa bilder var enligt Eriksson till mycket stor hjälp.

6.1.2 Observationer

Det verktyg som valdes för de praktiska testen var Selenium WebDriver. Motivet till detta beskrivs i kapitel 3. Innan vi började arbeta med Selenium WebDriver deltog vi under en halv dag i verkliga regressionstester, där vi manuellt genomförde testfall. Det aktuella testfallet bestod av fyra delar som utgör huvudflödet i C-Load; att skapa lass, boka lass, lasta lass och lossa lass. Beskrivningen av observationerna delas in i två delar. Först beskrivs tillvägagångssättet och därefter beskrivs observationer kopplade till de teman som används i analysen.

6.1.2.1 Tillvägagångssätt

Eftersom C-Load är skrivet i C# använde vi det även i testskripten. Då Selenium WebDriver bara styr webbläsaren behövde vi också ett testramverk för att kunna skapa test. De vanligaste ramverken för .NET är MSTest, Xunit och Nunit. Vi valde att använda NUnit eftersom det verkade mest likt JUnit, vilket vi hade viss erfarenhet av. Vi använde Visual Studio Enterprise 2019 och skapade där ett Nunit-testprojekt till vilket vi adderade Selenium Webriver NuGet. För varje webbläsare vi ville testa med behövde vi också installera en exekverbar fil, kallad driver, som möjliggör kommunikation mellan Selenium och respektive webbläsare.

Fyra moment utgör grunden för att skapa testskript med Selenium WebDriver:

Identifiera element

Säkerställa att element är tillgängliga

Utföra önskad handling på element

Definiera testorakel. Dvs bestämma vilka villkor som ska gälla för att testet ska gå

igenom.

I det följande beskriver vi våra upplevelser i samband med de olika momenten och hur det var att använda POM.

Identifiera element

Med hjälp av en extension till Firefox kallad ChroPath gick det att hitta möjliga selektorer till ett givet element. Svårigheten bestod i att vi inte hade kunskap om hur sidorna i C-Load var uppbyggda. Till en början försökte vi därför ofta att utföra handlingar på element som låg för djupt i DOM-hierarkin. Exempelvis kunde vi identifiera ett element B som vi trodde var en textbox där vi skulle kunna skriva text. För att kunna skriva text i textboxen behövde vi dock i själva verket identifiera ett div-element A som omslöt element B. I vissa fall ledde detta “bara” till att vår selektor blev en lång XPath när vi istället hade kunnat använda id:t på ett element högre upp i DOM-hierarkin. I andra fall ledde det till att vi inte alls kunde utföra avsedd operation. Efter en del trial-and-error förstod vi hur vi skulle söka efter element på rätt nivå i DOM-hierarkin. C-Load har till stor del unika id:n

så det gick oftast att använda det som selektor. I C-Load finns ett antal Telerik UI komponenter. Det gick att hitta dessa element via deras id, men i till exempel drop-down menyer var det svårt att identifiera de olika elementen i menyn.

Säkerställa att element är tillgängliga

Vid ett par tillfällen lyckades vi inte få skriptet att fungera med vare sig Implicit eller Explicit Waits, utan vi fick använda en Thread.Sleep, som pausar tråden i angivet antal millisekunder. Detta är dock inte god praxis. Varför det ibland inte fungerade med varken implicit eller explicit waits har vi inte hunnit utreda. Att säkerställa att element är tillgängliga upplevde vi som det vanskligaste momentet med att skriva skripten. När ett skript inte fungerade som tänkt var det svårt att veta om det berodde på felaktig hantering av väntan eller något annat.

Utföra önskad handling på element

När man har säkerställt att ett element är tillgängligt kan man utföra olika handlingar på elementet. Det kan till exempel vara att klicka på en knapp, skriva in ett användarnamn i ett textfält eller trycka på en tangent. Selenium WebDriver har nativt stöd för de vanligaste handlingarna men när det kommer till vissa “ovanligare” handlingar, som t.ex.

drag & drop, får man antingen skriva en egen hjälpmetod eller använda olika hjälpklasser.

En sådan hjälpklass är Actions som har stöd för till exempel dubbelklick och att peka med musen på ett element. Till en början var det svårt att veta vilken klass som skulle användas för att utföra en viss handling, vilket gjorde att utvecklingen av skripten tog längre tid.

Definiera testorakel

För att definiera vilka villkor som ska gälla för att testet ska gå igenom används Assert-klassen i det ramverk för enhetstester som används, i vårt fall NUnit. De testfall som vi skrev skript för gick ut på att gå igenom hela flödet för de fyra huvuduppgifterna: skapa lass, boka lass, lasta lass och lossa lass. Eftersom skripten i stort sett bara behövde verifiera att flödet gick att genomföra, användes Assert bara en gång i själva testet.

Däremot användes Assert flitigt för att felsöka skripten genom att t.ex. kontrollera att värden på elements attribut var de förväntade. Vi upplevde inga särskilda svårigheter med detta.

Page Object Model

Vi visste från början att vi ville använda POM, men först skrev vi all kod i samma klass för att lära oss hur vi kunde identifiera element, utföra handlingar på element etc. I bilaga 2 visas exempel på kod före och efter att vi skapade page objects. Som framgår av exemplen blir koden betydligt enklare att läsa när POM används.

6.1.2.2 Observationer per tema

Som underlag till kommande analys och diskussion beskrivs i detta avsnitt observationer uppdelade på de teman som kopplats till identifierade krav: applicerbarhet, webbläsare, exekveringstid och total tid för testrelaterat arbete.

Applicerbarhet

Det var möjligt att skriva fungerande testskript för alla fyra stegen i det testfall som användes, men för att identifiera Telerik UI-komponenter användes alternativa lösningar eftersom Selenium WebDrivers metoder inte fungerade på förväntat sätt.

Webbläsare

Vi försökte köra testskripten med Chrome, Edge, Internet Explorer och Firefox. Chrome och Internet Explorer var de enda webbläsarna där testen fungerade helt utan problem. I Internet Explorer var man dock tvungen att ändra inställningar för att använda Selenium WebDriver, inkluderat att stänga av "Enhanced Protected Mode" och göra tillägg i windowsregistret. När konfigurationen var avklarad uppstod inga ytterligare problem. I Edge startade webbläsaren när skripten startades, men sedan hände inget mer.

I Firefox kunde vi inte använda vissa metoder ur Actionklassen, det löste vi genom att göra om våra metoder. Vi kunde ändå inte köra hela flödet med Firefox, då Selenium WebDriver i ett steg klickar på fel element, trots att elementet identifieras med id. Varför detta sker har vi inte utrett. Det ska gå att använda äldre versioner av Firefox och Selenium för undvika problemen med Actionklassen men vi har inte utforskat det närmare.

Exekveringstid

Vi körde det testfall som vi skapat skript för tre gånger vardera i Chrome och Internet Explorer, manuellt och med Selenium WebDriver. Genomsnittliga tider visas i tabell 3. I Chrome tog de manuella testerna i genomsnitt 86% längre tid än de automatiserade och i Internet Explorer 33% längre tid. Syftet med mätningen var bara att få en uppfattning om skillnaden i tid mellan manuella och automatiserade test och inga långtgående slutsatser kan dras av resultatet.

Tabell 3. Genomsnittlig exekveringstid manuellt och med Selenium WebDriver.

Total tid för testrelaterat arbete

Att installera och lära sig grunderna i Selenium WebDriver samt skriva testskripten tog cirka tre arbetsveckor. Efter den tiden hade produktiviteten stigit betydligt. När vi väl hade kommit fram till hur en viss typ av element skulle hanteras gick det för det mesta relativt snabbt att skriva koden för att hantera ett annat element av samma typ.

Att införa designmönstret POM gjorde stor skillnad för kodens läsbarhet och hur lätt det bedöms vara att underhålla koden. Bilaga 2 visar exempel på kod före och efter att POM infördes.

Vi observerade ett fåtal gånger att skript inte fungerade konsekvent, men det var inte vanligt. För att undersöka detta ordentligt hade det varit nödvändigt att göra systematiska observationer där fungerande testskript kördes många gånger, vilket inte hanns med. Ett

annat problem som inträffade vid ett tillfälle var att Selenium WebDriver konsekvent klickade på ett extra element som inte ingick i testfallet.

De svårigheter som upplevdes var framförallt att hantera väntetid och att komma fram till vilka metoder som fungerade för att hantera olika element.

Angående problemlösning och felsökning är vårt samlade intryck att det går snabbt att hitta många lösningsförslag på till exempel Stackoverflow, men många av dessa är inaktuella eftersom webbläsare och Selenium ständigt uppdateras. Det går att hitta svar på allt, men det är ibland tidskrävande.

Related documents