Upload
others
View
27
Download
0
Embed Size (px)
Test- AutomatisierungMatthias Reichinger
14.01.2019
Inhalt● Block A
○ Allgemeines○ Property-based Testing○ Mock-Objekte○ Continuous-Testing○ Integration Testing
● Block B○ API-Testing○ GUI-Testing
Quelle: sphereinc.com
Unit-Testing● Anforderungen
○ Design-by-contract○ Isolierung von Units○ Testabdeckung (Corner Cases, …)
● Testfallgenerierung○ Example-based Testing (Stichproben)○ Property-based Testing (Eigenschaften)
● Fehlerfreiheit nicht garantiert!
Property-based Testing● Warum?
○ Testfallgenerierung durch Stichproben ist■ Unvollständig (vergessene Fälle)
■ Zeitaufwändig (viele Kombinationen der Parameter)
● Wie?○ Eigenschaften des Algorithmus finden○ Parameterbereich definieren○ Testfälle zufällig generieren
● “Shrinking” und “Seeds”
Quelle: heise.de
Property-based Testing - Beispiel “Primfaktorenzerlegung”
● Klasse PrimeFactorCalculator
Quelle: heise.de
public class PrimeFactorCalculator {
public List<Long> factor(Long i) { List<Long> primeFactors = new ArrayList<Long>(); long divisor = 1; double squareRoot = Math.sqrt(i); while (i > 1) { divisor++; while (i % divisor == 0) { primeFactors.add(divisor); i /= divisor; } if (divisor > squareRoot) { divisor = i - 1; } } return primeFactors; }}
@Test public void factor4() { assertTrue(
sut.factor(4L).equals(Arrays.asList(2L, 2L)));
} @Test public void factor5() { assertTrue(
sut.factor(5L).equals(Arrays.asList(5L)));
}}@Testpublic void factor36() { assertTrue(
sut.factor(36L).equals(Arrays.asList(2L, 2L, 3L, 3L)));
}
public class PrimeFactorCalculatorTest {
private PrimeFactorCalculator sut; // system under test
@BeforeEach public void setup() { sut = new PrimeFactorCalculator(); }
@Test public void factor2() { assertTrue(sut.factor(2L).equals(Arrays.asList(2L))); }
@Test public void factor3() { assertTrue(sut.factor(3L).equals(Arrays.asList(3L))); }
Quelle: heise.de
Klassisches Stichproben-Testing
● Bsp.: Example-Based testing
Quelle: heise.de
public class PrimeFactorCalculatorParameterizedTest {
private PrimeFactorCalculator sut; // system under test
@BeforeEach public void setup(){ sut = new PrimeFactorCalculator(); }
@ParameterizedTest(name = "{0} should be factored as [{1}]") @CsvSource({
"2, 2", "3, 3", "4, 2;2", "5, 5",
“36, 2;2;3;3 })
public void factorSmallNumbers(long n, String factors) { assertTrue(sut.factor(n).equals(split(factors))); }
Parametrisiertes Testing
● Bsp.: Example-Based testing
Quelle: heise.de
@RunWith(JUnitQuickcheck.class)public class PrimeFactorCalculatorPropertiesTest { @Property public void productOfPrimeFactorsShouldBeTheOriginalNumber( @InRange(min = "2", max = "9999999999999") Long i) { PrimeFactorCalculator sut = new PrimeFactorCalculator(); assertThat(sut.factor(i).stream() .reduce(1L, (a, b) -> a * b)) .isEqualTo(i); }}
Property-based Testing(Quickcheck)
@Property public void primeFactorsShouldBePrimeNumbers( @InRange(min = "2", max = "9999999999999") Long i) { PrimeFactorCalculator sut = new PrimeFactorCalculator(); sut.factor(i).stream() .forEach(primeFactor -> assertThat(isPrime(primeFactor)) .as("factor " + primeFactor + " should be a prime number") .isTrue());}
Property-based Testing
● Nicht alle Algorithmen für Test geeignet!
● 5 Faustregeln um Property-based Tests zu entwickeln
Quelle: heise.de
Property-based Testing
Quelle: heise.de
Bsp.: JSON-(De)serialisierung
Operation ausführen ->Gegenoperation ausführen -> ursprüngliches Objekt
Property-based Testing
Quelle: heise.de
Bsp: Filtern einer Liste nach Geschlecht und Alter.
Abfolge ändern -> gleiches Ergebnis
Property-based Testing
Quelle: heise.de
Bsp: SHA256 Hashing Algorithmus
Ergebnis muss 64 Hexadezimalzeichen lang sein.
Property-based Testing
Quelle: heise.de
Bsp: Sortierte Liste bleibt sortiert nach nochmaligem sortieren
Property-based Testing
Quelle: heise.de
Bsp: neu entwickelten schnelleren Algorithmus mit bekanntem langsamerem vergleichen
Property-based Testing● Ersetzt nicht Unit-Testing mit Beispielen,
● aber kann es sinnvoll ergänzen.
Quelle: heise.de
Mock-Objekte● Platzhalter für echte Objekte zur Isolierung von
Units bei Unit-Tests
● Beispiel (Java):○ Mocken von Spring Beans mit Mockito
Quelle: baeldung.com
Mock-Objekte
Quelle: baeldung.com
NameService
Teste: UserService
Methode: getUserName(String id)
Test Isolation!!
Mock-Objekte
Quelle: baeldung.com
nameService wird gemockt (dies wird in einer NameServiceTestConfiguration festgelegt. Mehr dazu unter dem Link unten)
Gewünschter Output bei gegebenem Input wird angegeben
Continuous-Testing● ...ist das Ausführen von automatischen Tests als Teil der
Software Delivery Pipeline
● Ziel○ Kontinuierliches Feedback○ Schnelles Feedback
● Im Zuge von “Continuous Integration, Delivery, and Deployment”
● Bekanntes Tool:
Quelle: techwell.com
Quelle: dzone.com
+Automatische User Acceptance Tests
+Automatische Releases
Änderung im Source Code-> Build Script deployed auf Build Server
Integration-Testing● Individuelle Module werden kombiniert
und dann als Gruppe getestet.● Arten:
○ Big-bang○ Top-down○ Bottom-up○ Mixed
Quelle: guru99.com
Integration-Testing● Big Bang
○ Alle Module integrieren und zusammen testen○ Pro: Alles auf einmal○ Contra: Fehler schwer zu identifizieren
Quelle: softwarehelpingtest.com
Integration-Testing● Top Down
○ Zuerst high-level Module testen (mit Stubs)
Quelle: softwarehelpingtest.com
Integration-Testing● Bottom Up
○ Zuerst low-level Module testen (mit Drivers)
Quelle: softwarehelpingtest.com
Integration-Testing● 2 Unit Tests 0 Integration Tests
API-Testing● Test der API auf
○ Funktionalität, Verlässlichkeit, Performance, Sicherheit
● Bsp.: Test einer REST API (mit JSON payload)
● bei REST-Tests Fokus auf:○ den HTTP Response Code○ die HTTP Header im Response○ den Payload
Quelle: baeldung.com
Erwarte Status: “404 - Not Found”
Führe API Aufruf aus
API-TestingBsp: Rufe User API mit unbekanntem User auf
-> erwarte 404 Not Found
Quelle: baeldung.com
Erzeuge zufälligen Usernamen
Erzeuge API Aufruf
API-TestingBsp: Rufe User API mit User “eugenp” auf
-> erwarte Media Type “application/json”
Quelle: baeldung.com
Erwarte Type: “application/json”
Erzeuge API Aufruf
Führe API Aufruf aus
GUI-TestingTesten ob...● … Teile einer GUI funktionieren.
○ Z.b: Menüs, Fenster, Textfelder, Buttons, …● … Folge von Interaktionen in GUI funktionieren.
○ z.B: Fenster öffenen -> Textbox ausfüllen -> Bestätigen
● Bsp.: Selenium○ IDE: Aufnahme von Interaktionen
-> export als Skript○ WebDriver: Nutzt nativen Support
eines Browsers zur Automatisierung(z.B: chromedriver für Chrome)
GUI-Testing
Quelle: blazemeter.com
Download von Website!!
Hält Instanz des Webdrivers mit Getter und Setter
GUI-Testing
Quelle: blazemeter.com
Webseite wird aufgerufen
Element aus Webseite wird geholt
GUI-TestingProbleme
● Schwer gute Tests zu schreiben-> best practices z.B.: PageObjects
● Ausführung dauert lange
● Wartbarkeit -> GUI zu instabil○ Bsp.: Umbenennung eines Buttons
-> Test schlägt bereits fehl
● Praxis: Wenn API primäres Interface für Programmlogik -> API- statt GUI-Tests (als Teil der Integration-Tests)
Danke für Eure Aufmerksamkeit!