CI/CD für C#: Schluss mit manuellem Deployment – starten Sie durch
\n\nWenn Sie Ihr C#-Projekt immer noch lokal bauen, Builds per FTP hochladen und hoffen, dass nichts schiefgeht – habe ich Neuigkeiten für Sie. Im Jahr 2025 ist das einfach nicht mehr zeitgemäß. Nicht einmal für ein kleines Pet-Projekt.
\n\nCI/CD ist keine Zauberei von Senioren für 300k, sondern einfach eine Sammlung von Skripten, die die lästige Routine für Sie erledigen. Heute richten wir eine vollwertige CI/CD-Pipeline für C# von Grund auf ein. Ohne überflüssiges Blabla, mit echten Beispielen und einer Fehleranalyse.
\n\nÜbrigens: Wenn Sie in Python programmieren, finden Sie auf pythonlib.ru ebenfalls Guides zur Automatisierung. Aber heute arbeiten wir mit C#.
\n\nWas ist CI/CD und warum braucht ein C#-Entwickler das?
\n\nCI (Continuous Integration) bedeutet, dass jeder Ihrer Commits in Git automatisch gebaut und getestet wird. Schluss mit „Aber bei mir läuft es doch“.
\n\nCD (Continuous Delivery/Deployment) bedeutet, dass der Code nach einem erfolgreichen Build automatisch auf den Server (oder in die Cloud) geht.
\n\nFür C# ist das besonders relevant: Der Build über dotnet build kann auf verschiedenen Maschinen unterschiedlich ausfallen, und Tests werden gerne mal vergessen. CI/CD löst beide Probleme.
Tool-Auswahl: GitHub Actions vs. GitLab CI vs. Jenkins
\n\nFür den Start empfehle ich GitHub Actions. Warum?
\n\n- \n
- Kostenlos für öffentliche Repositories (ja, auch für C#) \n
- Kein eigener Server nötig \n
- Fertige Actions für .NET \n
- YAML ist leicht lesbar \n
Wenn Sie GitLab nutzen – gleiches Prinzip, ähnliche Syntax. Jenkins heben wir uns für den Unternehmensalltag auf.
\n\nDen ersten Pipeline für ein C#-Projekt schreiben
\n\nErstellen Sie im Repository-Stammverzeichnis die Datei .github/workflows/dotnet.yml. Ja, die Datei muss genau in diesem Ordner liegen.
Hier ist ein minimaler, funktionierender Pipeline, der das Projekt baut und die Tests ausführt:
\n\nname: .NET CI\n\non:\n push:\n branches: [ main, develop ]\n pull_request:\n branches: [ main ]\n\njobs:\n build-and-test:\n runs-on: ubuntu-latest\n\n steps:\n - uses: actions/checkout@v4\n\n - name: Setup .NET\n uses: actions/setup-dotnet@v4\n with:\n dotnet-version: '8.0.x'\n\n - name: Restore dependencies\n run: dotnet restore\n\n - name: Build\n run: dotnet build --no-restore --configuration Release\n\n - name: Run tests\n run: dotnet test --no-build --configuration Release --verbosity normal\n\nSchritt-für-Schritt-Erklärung:
\n\n- \n
on: push– Der Pipeline startet bei einem Push in main oder develop \n runs-on: ubuntu-latest– Wir bauen auf Linux (C# unter .NET Core/8+ läuft überall) \n setup-dotnet– Installiert die benötigte .NET SDK-Version \n dotnet restore– Stellt NuGet-Pakete wieder her \n dotnet build– Kompiliert die Release-Version \n dotnet test– Führt alle Tests aus dem Projekt aus \n
Gehen Sie nach dem Push in den Reiter „Actions“ Ihres Repositorys – Sie sehen, wie der Pipeline ausgeführt wird. Fallen Tests durch, erhalten Sie einen roten Status und eine Benachrichtigung per E-Mail.
\n\nCode Coverage hinzufügen (weil Tests ohne Abdeckung sinnlos sind)
\n\nEin schöner Pipeline sollte zeigen, wie viel Code von Tests abgedeckt wird. Für C# verwenden wir coverlet in Kombination mit ReportGenerator.
\n\nFügen Sie zuerst die NuGet-Pakete zu Ihrem Testprojekt hinzu:
\n\ndotnet add YourTestProject.csproj package coverlet.collector\ndotnet add YourTestProject.csproj package coverlet.msbuild\n\nAktualisieren Sie nun den Test-Schritt im Pipeline:
\n\n - name: Run tests with coverage\n run: |\n dotnet test --no-build --configuration Release \\\n /p:CollectCoverage=true \\\n /p:CoverletOutputFormat=opencover \\\n /p:CoverletOutput=./TestResults/coverage.xml\n\n - name: Install ReportGenerator\n run: dotnet t