Testing

Spring Boot bietet sehr viel Komfort beim Anwendungstest. Man muß nur die richtige Annotation (injezierbare Services aufgeführt)

  • @SpringBootTest

    • @Autowired private TestRestTemplate restTemplate;

  • @WebMvcTest

    • @Autowired private MockMvc mvc;

  • @WebFluxTest

  • @RestClientTest

    • @Autowired private MockRestServiceServer server;

  • @DataJpaTest

  • @JdbcTest

  • @DataMongoTest

  • ...

und schon kann man sich ganz zentrale Services per @Autowired injecten als Mocks lassen. Deren Verhalten muß man allerdings häufig im Test über eine Fluent-API konfigurieren (denn man will ja unterschiedliche Szenarien testen).

Integrationtesting

Eine typische Testklasse für eine Webapplikation sieht so aus:

@RunWith(SpringJUnit4ClassRunner.class)

Dieser JUnit-Testrunner sollte grundsätzlich bei Spring-basierten Komponenten verwendet werden. Er stellt die Grundvoraussetzung dar - sonst darf man sich nicht wundern, wenn spring-spezifische Aspekte (z. B. der Aufbau des ApplicationContext aus xml-Dateien @ContextConfiguration(locations = { "classpath:mymodule-context.xml" })) nicht funktionieren.

@SpringApplicationConfiguration

Diese Annotation wird eingesetzt, um die zu testenden Applikation zu initialisieren. Deshalb darf die SpringBoot-Main-Class nicht fehlen. Zudem werden evtl. noch ein paar Initializer für die Testumgebung aufgeführt (z. B. zur Initialisierung von Mocks).

Hier kann man auch Spring-Initialisierung über Spring-Kontexte in XML-Form anstoßen:

@IntegrationTest

@WebIntegrationTest

Handelt es sich um einen @IntegrationTest, der auch eine @WebAppConfiguration benötigt, dann sollte man vermutlich @WebIntegrationTest verwenden. In einem WebIntegrationTest wird ein Applicationserver (Servlet-Container - per Default Toncat) gestartet

Applikationskonfiguration

Die Applikationskonfiguration wird aus der application.properties gezogen, kann aber über

für jeden Test übersteuert werden.

Freien Port suchen

Es macht Sinn, einen freien (!!!) Port für zu startenden Applicationserver zu suchen:

und diesen Port dann per

zu injezieren.

Rest-Tests

Das Testen von Rest-Schnittstellen läuft über TestRestTemplate.

Vorsicht vor Test-Fakes

Da die Rest-Services ganz normale Java-Beans sind, läuft man Gefahr die Beans über Java-Aufrufe zu testen. Hierbei wird allerdings nicht die Funktionalität getestet, die ein RICHTIGER Applikationsclient verwendet. Beispielsweise wird das Marshalling/Unmarshalling nicht durchlaufen.

Diese Abkürzungen fangen am Anfang vielleicht gar nicht auf, doch spätestens, wenn beispielsweise auf HttpServletRequest im Rest-Service zugegriffen werden soll ... eine solche Instanz dann aber gar nicht existiert.

Option 1: TestRestTemplate

Basic-Authentication:

new TestRestTemplate("username", "password")

MessageConverters:

RestTemplate: postForObject vs. postForEntity

Entity liefert nicht nur das eigentliche Result-Objekt des Webservice, sondern auch gleichzeitig Status-Code, ...

Empfehlung: verwende postForEntity

Beispiel:

Option 2: MockMvc

Option 3...n:

Irgendweinen anderen Http-Client verwenden.

Last updated

Was this helpful?