Azure DevOps – erste CI/CD-Pipeline einrichten 2025

Von Code zu Produktion: Build, Test und Deployment automatisieren

S
SeeColors IT
11. Juni 20265 Min. Lesezeit41 Aufrufe

Was ist Azure DevOps?

Azure DevOps ist Microsofts integrierte DevOps-Plattform mit fünf Modulen:

Modul Funktion
Azure Repos Git-Repositories (oder TFVC)
Azure Pipelines CI/CD – Build, Test, Deploy
Azure Boards Agile Planung (Sprints, User Stories, Bugs)
Azure Artifacts Package Registry (NuGet, npm, Maven)
Azure Test Plans Manuelle und automatisierte Tests

Azure DevOps vs. GitHub Actions

Merkmal Azure DevOps GitHub Actions
Microsoft-Integration Sehr tief (Entra ID, Azure) Gut
Enterprise-Features Ja (RBAC, Audit, Compliance) GitHub Enterprise
Kosten 5 User kostenlos, dann ~6 $/User Free-Tier, dann GitHub-Plans
Komplexe Genehmigungen Ja (Stage Gates) Environments
Self-hosted Agents Ja Self-hosted Runners

Für Microsoft-zentrischen Enterprises: Azure DevOps. Für Open-Source-Projekte und einfachere Workflows: GitHub Actions.

Azure DevOps Organisation einrichten

  1. dev.azure.com aufrufen → Mit Microsoft-Account oder Entra ID anmelden
  2. New organization erstellen (z. B. meinefirma)
  3. New project erstellen:
    • Name: mein-projekt
    • Visibility: Private
    • Version control: Git
    • Work item process: Scrum oder Agile

Azure Repos – Repository einrichten

Neues Repo

In Azure DevOps: Repos → Files → Initialize (oder bestehendes Git-Repo importieren).

Bestehendes lokales Repo verknüpfen

cd mein-projekt
git remote add origin https://[email protected]/meinefirma/mein-projekt/_git/mein-projekt
git push -u origin main

Branch-Policies (empfohlen)

Repos → Branches → main → Branch policies:

  • Require minimum reviewers: 1 (kein direkter Push auf main)
  • Check for comment resolution: Ja
  • Limit merge types: Squash merge oder Rebase

Erste YAML-Pipeline

Pipeline erstellen

Pipelines → New Pipeline → Azure Repos Git → Ihr Repository → Starter pipeline

Azure DevOps erstellt eine azure-pipelines.yml Datei. Passen Sie sie an:

trigger:
  branches:
    include:
      - main
      - develop

pr:
  branches:
    include:
      - main

pool:
  vmImage: 'ubuntu-latest'

variables:
  buildConfiguration: 'Release'

stages:
  - stage: Build
    displayName: 'Build und Test'
    jobs:
      - job: BuildJob
        displayName: 'Build'
        steps:
          - task: NodeTool@0
            inputs:
              versionSpec: '20.x'
            displayName: 'Node.js 20 einrichten'

          - script: npm ci
            displayName: 'Abhängigkeiten installieren'

          - script: npm run lint
            displayName: 'Lint prüfen'

          - script: npm test -- --ci --coverage
            displayName: 'Tests ausführen'

          - task: PublishTestResults@2
            inputs:
              testResultsFormat: 'JUnit'
              testResultsFiles: '**/junit.xml'
            displayName: 'Testergebnisse publizieren'

          - script: npm run build
            displayName: 'App bauen'

          - task: PublishBuildArtifacts@1
            inputs:
              pathtoPublish: 'dist'
              artifactName: 'drop'

Multi-Stage-Pipeline: Build → Staging → Produktion

stages:
  - stage: Build
    jobs:
      - job: Build
        steps:
          - script: npm ci && npm run build
          - publish: dist
            artifact: drop

  - stage: DeployStaging
    displayName: 'Deploy Staging'
    dependsOn: Build
    condition: succeeded()
    jobs:
      - deployment: DeployToStaging
        displayName: 'Staging'
        environment: staging
        strategy:
          runOnce:
            deploy:
              steps:
                - task: AzureWebApp@1
                  inputs:
                    azureSubscription: 'Azure-Verbindung'
                    appName: 'meine-app-staging'
                    package: '$(Pipeline.Workspace)/drop/**'

  - stage: DeployProduction
    displayName: 'Deploy Produktion'
    dependsOn: DeployStaging
    condition: succeeded()
    jobs:
      - deployment: DeployToProduction
        displayName: 'Produktion'
        environment: production   # Genehmigung erforderlich!
        strategy:
          runOnce:
            deploy:
              steps:
                - task: AzureWebApp@1
                  inputs:
                    azureSubscription: 'Azure-Verbindung'
                    appName: 'meine-app-prod'
                    package: '$(Pipeline.Workspace)/drop/**'

Approval Gates konfigurieren

Environments → production → Approvals and checks → Add → Approvals:

  • Approvers: IT-Leiter oder verantwortliche Entwickler
  • Timeout: 24 Stunden
  • Die Pipeline pausiert bei „Deploy Produktion" und wartet auf Genehmigung

Service Connection zu Azure einrichten

Damit Pipelines auf Azure-Ressourcen zugreifen dürfen:

Project Settings → Service connections → New service connection → Azure Resource Manager:

  1. Authentication method: Service principal (automatic)
  2. Subscription und Resource Group auswählen
  3. Service connection name: Azure-Verbindung
  4. Grant access permission to all pipelines: Ja (oder pro Pipeline einschränken)

Self-hosted Agent

Für Deployments in private Netzwerke (On-Premises, VPN) brauchen Sie einen Self-hosted Agent:

# Agent herunterladen
mkdir -p ~/azure-agent && cd ~/azure-agent
wget https://vstsagentpackage.azureedge.net/agent/3.x.x/vsts-agent-linux-x64-3.x.x.tar.gz
tar -xzf vsts-agent-linux-x64-3.x.x.tar.gz

# Konfigurieren
./config.sh --url https://dev.azure.com/IHRE_ORG             --auth pat             --token <PERSONAL_ACCESS_TOKEN>             --pool Default             --agent MeinServer

# Als Service installieren
sudo ./svc.sh install
sudo ./svc.sh start

In der Pipeline den eigenen Agent-Pool nutzen:

pool:
  name: Default   # statt 'ubuntu-latest'

Variablen und Secrets

Pipeline → Edit → Variables → New variable:

  • Name: DATABASE_URL
  • Value: Verbindungsstring
  • Keep this value secret: Aktiviert (wird verschlüsselt gespeichert)

In der Pipeline:

steps:
  - script: npm run migrate
    env:
      DATABASE_URL: $(DATABASE_URL)

FAQ

Was kostet Azure DevOps?
5 Benutzer kostenlos, dann ~6 $/Benutzer/Monat (Basic Plan). CI/CD-Minuten: 1.800 Minuten/Monat kostenlos pro Organisation.

Kann Azure DevOps on-premises installiert werden?
Ja: Azure DevOps Server (früher TFS) ist die On-Premises-Variante. Für die meisten KMU ist die Cloud-Version jedoch empfohlen.

Wie migriere ich von Azure DevOps zu GitHub?
Microsoft bietet offizielle Migrationswerkzeuge an (Azure DevOps Migration Tools). Pipelines müssen manuell zu GitHub Actions konvertiert werden.

Fazit

Azure DevOps ist die erste Wahl für .NET- und Microsoft-Teams die ihre gesamte Entwicklungspipeline in einem Tool verwalten wollen – eng integriert mit Azure und Entra ID.

Wir implementieren Azure DevOps-Pipelines und begleiten DevOps-Transformationen für KMU in Heidelberg, Mannheim und der Rhein-Neckar-Region. DevOps-Beratung anfragen.

Artikel teilen

War dieser Artikel hilfreich?

Dein Feedback hilft uns, bessere Inhalte zu erstellen.

Kommentar hinterlassen

Verwandte Artikel