Integrationstests in C# mit Docker: Ein vollständiger Leitfaden von A bis Z

Online Python-Trainer für Anfänger

Lernen Sie Python einfach ohne theoretische Überlastung. Lösen Sie praktische Aufgaben mit automatischer Überprüfung und schreiben Sie Code direkt im Browser.

Kurs starten

Integrationstests in C# mit Docker: Von A bis Z

\n\n

Integrationstests sind ein kritisch wichtiger Schritt bei der Entwicklung jeder ernsthaften C#-Anwendung. Sie prüfen, wie verschiedene Systemkomponenten (Datenbank, externe APIs, Dateisysteme) zusammenarbeiten. Die Einrichtung der Testumgebung wird jedoch oft zum Kopfzerbrechen: Man muss echte Server hochfahren, Daten nach Tests bereinigen und mit instabilen Umgebungen kämpfen. Docker löst diese Probleme, indem es leichte, isolierte und reproduzierbare Container bereitstellt. In diesem Artikel zeigen wir, wie Sie Integrationstests in C# mit Docker von Null bis zur funktionierenden Pipeline einrichten.

\n\n

Warum ist Docker ideal für Integrationstests in C#?

\n\n

Der traditionelle Ansatz – die Verwendung lokaler SQL Server-Datenbanken oder Emulatoren externer Dienste – führt zu Problemen:

\n
    \n
  • Datenverschmutzung: Tests hinterlassen Müll in der Datenbank und beeinflussen andere Tests.
  • \n
  • Umgebungsinkompatibilität: Auf dem Entwicklerrechner läuft eine DBMS-Version, auf dem CI-Server eine andere.
  • Schwierigkeiten beim parallelen Ausführen: Tests geraten in Konflikt um Ports und Ressourcen.
\n\n

Docker löst dies einfach: Jeder Test (oder jede Testgruppe) erhält seinen eigenen isolierten Container mit der benötigten Version der Datenbank, Redis oder eines anderen Dienstes. Container sind leicht, starten in Sekunden und werden nach Abschluss der Tests garantiert zerstört. Für .NET-Entwickler ist dies dank der Bibliothek Testcontainers for .NET besonders relevant, die die Containerverwaltung direkt aus dem Testcode heraus automatisiert.

\n\n

Projekteinrichtung: Docker zu C#-Tests hinzufügen

\n\n

Zunächst erstellen wir ein Projekt mit Integrationstests. Angenommen, wir haben eine Web-API auf .NET 8, die mit PostgreSQL arbeitet. Wir müssen den Endpunkt zum Erstellen eines Benutzers testen.

\n\n

Schritt 1: Installation der NuGet-Pakete

\n

Fügen Sie dem Testprojekt die folgenden Pakete hinzu:

\n
dotnet add package Testcontainers.PostgreSql\ndotnet add package Microsoft.AspNetCore.Mvc.Testing\ndotnet add package FluentAssertions
\n\n

Testcontainers.PostgreSql ist ein Wrapper um das Docker SDK, der PostgreSQL-Container verwaltet. Microsoft.AspNetCore.Mvc.Testing ermöglicht das Ausführen der Webanwendung im Arbeitsspeicher zum Testen.

\n\n

Schritt 2: Erstellen einer Basisklasse für Tests

\n

Wir erstellen eine abstrakte Klasse, die vor den Tests einen Container mit der Datenbank startet:

\n
using Testcontainers.PostgreSql;\nusing Xunit;\n\npublic abstract class IntegrationTestBase : IAsyncLifetime\n{\n    private readonly PostgreSqlContainer _postgresContainer;\n\n    protected string ConnectionString => _postgresContainer.GetConnectionString();\n\n    protected IntegrationTestBase()\n    {\n        _postgresContainer = new PostgreSqlBuilder()\n            .WithImage("postgres:16-alpine")\n            .WithDatabase("testdb")\n            .WithUsername("test")\n            .WithPassword("test123")\n            .Build();\n    }\n\n    public async Task InitializeAsync()\n    {\n        await _postgresContainer.StartAsync();\n    }\n\n    public async Task DisposeAsync()\n    {\n        await _postgresContainer.StopAsync();\n    }\n}
\n\n

Diese Klasse implementiert IAsyncLifetime von xUnit, was den Start des Containers vor allen Tests und dessen Stopp danach garantiert. ConnectionString wird dynamisch aus dem Container bezogen – der Port kann ein beliebiger freier Port sein.

\n\n

Schritt 3: Schreiben eines Tests mit Testcontainers und WebApplicationFactory

\n

Jetzt schreiben wir den eigentlichen Test. Wir verwenden WebApplicationFactory, um einen Test-HTTP-Client zu erstellen:

\n
using Microsoft.AspNetCore.Mvc.Testing;\nusing FluentAssertions;\nusing System.Net.Http.Json;\n\npublic class UserApiTests : IntegrationTestBase\n{\n    private readonly WebApplicationFactory<Program> _factory;\n\n    public UserApiTests()\n                

Blogs

Buchempfehlungen