Tutorial: Verwenden einer Canary-Bereitstellungsstrategie für Kubernetes
Azure DevOps Services | Azure DevOps Server 2022
In dieser schrittweisen Anleitung erfahren Sie, wie Sie die Kubernetes-Manifestaufgabe zusammen mit der canary
Strategie verwenden. Bei einer Canary-Bereitstellungsstrategie werden neue Versionen einer Anwendung neben stabilen Produktionsversionen bereitgestellt.
Sie verwenden den zugeordneten Workflow, um den Code bereitzustellen und die Baseline- und Canary-Bereitstellungen zu vergleichen. Basierend auf der Auswertung entscheiden Sie, ob Sie die Canary-Bereitstellung hochstufen oder ablehnen möchten.
In diesem Tutorial werden Docker-Registrierungs- und Azure Resource Manager-Dienstverbindungen zur Herstellung von Verbindungen zu Azure-Ressourcen verwendet. Für einen privaten Azure Kubernetes Service (AKS)-Cluster oder einen Cluster, für den lokale Konten deaktiviert sind, sind Azure Resource Manager-Dienstverbindungen die bessere Möglichkeit, Verbindungen herzustellen.
Voraussetzungen
Ein Azure DevOps-Projekt, das mindestens über Benutzerberechtigungen verfügt.
Ein Azure-Konto. Sie können kostenlos ein Konto erstellen.
Eine Azure Container Registry-Instanz mit Pushberechtigungen.
Ein bereitgestelltes Azure Kubernetes Service (AKS)-Cluster. Sie können den AKS-Cluster an Ihren Azure -Containerregistrierungscluster bei Bereitstellung des AKS-Clusters oder später anfügen.
Ein GitHub-Konto. Erstellen Sie ein kostenloses GitHub-Konto.
Ein Fork des https://github.com/MicrosoftDocs/azure-pipelines-canary-k8s GitHub-Repositorys.
Wichtig
Während der Ausführung der folgenden Verfahren werden Sie möglicherweise aufgefordert, eine GitHub-Dienstverbindung zu erstellen, oder zu GitHub umgeleitet, um sich anzumelden, Azure Pipelines zu installieren oder Azure Pipelines zu autorisieren. Folgen Sie den Anweisungen auf dem Bildschirm, um den Prozess abzuschließen. Weitere Informationen finden Sie unter Zugriff auf GitHub-Repositorys.
GitHub-Repositorydateien
Das GitHub-Repository enthält die folgenden Dateien:
Datei | Beschreibung |
---|---|
./app/app.py | Ein einfacher, Flask-basierter Webserver. Die Datei richtet einen benutzerdefinierten Zähler für die Anzahl der guten und schlechten Antworten ein, basierend auf dem Wert der Variablen success_rate . |
./app/Dockerfile | Wird bei jeder Änderung von app.py zum Erstellen des Images verwendet. Jede Änderung löst die Buildpipeline aus, um das Image zu erstellen und zur Containerregistrierung zu pushen. |
./manifests/deployment.yml | Enthält die Spezifikation des sampleapp -Bereitstellungsworkloads, der dem veröffentlichten Image entspricht. Sie verwenden diese Manifestdatei für die stabile Version des Bereitstellungsobjekts und zum Ableiten der Baseline- und Canary-Varianten der Workloads. |
./manifests/service.yml | Erstellt den sampleapp -Dienst. Dieser Dienst leitet Anforderungen an die Pods weiter, die von den Stable-, Baseline- und Canary-Bereitstellungen gestartet werden. |
./misc/fortio.yml | Richtet eine Fortio-Bereitstellung ein. Bei dieser Bereitstellung handelt es sich um ein Tool zum Testen der Auslastung, das einen Strom von Anforderungen an den bereitgestellten sampleapp -Dienst sendet. Der Anforderungsstream wird an Pods in den drei Bereitstellungen weitergeleitet: Stable, Baseline und Canary. |
Erstellen von Dienstverbindungen
- Navigieren Sie im Azure DevOps-Projekt zu Projekteinstellungen>Pipelines>Dienstverbindungen.
- Erstellen Sie eine Docker-Registrierungsdienstverbindung namens azure-pipelines-canary-acr, die Ihrer Azure Container Registry-Instanz zugeordnet ist.
- Erstellen Sie eine Azure Resource Manager-Dienstverbindung mit der Workload-Identität namens azure-pipelines-canary-k8s für Ihre Ressourcengruppe.
Hinzufügen der Build-Phase
Wechseln Sie im Azure DevOps-Projekt zu Pipelines>Pipeline erstellen oder Neue Pipeline.
Wählen Sie GitHub als Codespeicherort aus. Wählen Sie anschließend Ihr geforktes Repository azure-pipelines-canary-k8s aus.
Wählen Sie auf der Registerkarte Konfigurieren die Option Starterpipeline aus.
Ersetzen Sie auf der Registerkarte Überprüfen den Pipeline-YAML durch den folgenden Code:
trigger: - main pool: vmImage: ubuntu-latest variables: imageName: azure-pipelines-canary-k8s # name of ACR image dockerRegistryServiceConnection: azure-pipelines-canary-acr # name of ACR service connection imageRepository: 'azure-pipelines-canary-k8s' # name of image repository containerRegistry: example.azurecr.io # name of Azure container registry tag: '$(Build.BuildId)' stages: - stage: Build displayName: Build stage jobs: - job: Build displayName: Build pool: vmImage: ubuntu-latest steps: - task: Docker@2 displayName: Build and push image inputs: containerRegistry: $(dockerRegistryServiceConnection) repository: $(imageName) command: buildAndPush Dockerfile: app/Dockerfile tags: | $(tag)
Wenn die von Ihnen erstellte Docker-Registrierungsdienstverbindung einer Containerregistrierung namens
example.azurecr.io
zugeordnet ist, wird das Image aufexample.azurecr.io/azure-pipelines-canary-k8s:$(Build.BuildId)
festgelegt.Wählen Sie Speichern und ausführen aus. Stellen Sie sicher, dass der Auftrag erfolgreich ausgeführt wird.
Bearbeiten der Manifestdatei
Bearbeiten Sie im Repository-Fork manifests/deployment.yml, indem Sie <foobar>
durch die URL Ihrer Containerregistrierung ersetzen, z. B. example.azurecr.io/azure-pipelines-canary-k8s
.
Einrichten der fortlaufenden Bereitstellung
Jetzt können Sie die kontinuierliche Bereitstellung einrichten, die die Canary-Phase bereitstellen und die Canary-Bereitstellung manuell hochstufen oder ablehnen.
Erstellen einer Umgebung
Sie können die Bereitstellung mit YAML oder klassisch durchführen.
- Navigieren Sie im Azure DevOps-Projekt zu Pipelines>Umgebungen. Wählen Sie dann Umgebung erstellen oder Neue Umgebung aus.
- Geben Sie im ersten Bildschirm unter Neue Umgebung akscanary in Name ein. Wählen Sie anschließend Kubernetes unter Ressource und dann Weiter aus.
- Geben Sie im Bildschirm Kubernetes-Ressource Folgendes ein:
- Anbieter: Wählen Sie Azure Kubernetes Service aus.
- Azure-Abonnement: Wählen Sie Ihr Azure-Abonnement aus.
- Cluster: Wählen Sie Ihren AKS-Cluster aus.
- Namespace: Wählen Sie Neu aus, und geben Sie canarydemo ein.
- Wählen Sie Überprüfen und erstellen aus.
Hinzufügen der Canary-Phase
Navigieren Sie zu Pipelines, und wählen Sie die von Ihnen erstellte Pipeline aus. Wählen Sie anschließend Bearbeiten aus.
Ersetzen Sie den gesamten Pipeline-YAML durch den folgenden Code.
Dieser Code ändert den Schritt
Docker@2
, den Sie zuvor zur Verwendung einer Phase ausgeführt haben, und fügt zwei weitere Schritte hinzu, um die Manifeste und die misc-Verzeichnisse als Artefakte für folgende Phasen zu kopieren.Der Code verschiebt auch einige Werte zu Variablen, um die Verwendung an späterer Stelle in der Pipeline zu vereinfachen. Ersetzen Sie in der Variablen
containerRegistry
<example>
durch den Namen Ihrer Containerregistrierung.trigger: - main pool: vmImage: ubuntu-latest variables: imageName: azure-pipelines-canary-k8s dockerRegistryServiceConnection: azure-pipelines-canary-acr imageRepository: 'azure-pipelines-canary-k8s' containerRegistry: <example>.azurecr.io tag: '$(Build.BuildId)' stages: - stage: Build displayName: Build stage jobs: - job: Build displayName: Build pool: vmImage: ubuntu-latest steps: - task: Docker@2 displayName: Build and push image inputs: containerRegistry: $(dockerRegistryServiceConnection) repository: $(imageName) command: buildAndPush Dockerfile: app/Dockerfile tags: | $(tag) - publish: manifests artifact: manifests - publish: misc artifact: misc
Fügen Sie am Ende der YAML-Datei eine weitere Phase hinzu, um die Canary-Version bereitzustellen. Ersetzen Sie die Werte
my-resource-group
undmy-aks-cluster
mit Ihrer Ressourcengruppe und dem Namen des Azure Kubernetes Service-Clusters.trigger: - main pool: vmImage: ubuntu-latest variables: imageName: azure-pipelines-canary-k8s dockerRegistryServiceConnection: azure-pipelines-canary-acr imageRepository: 'azure-pipelines-canary-k8s' containerRegistry: yourcontainerregistry.azurecr.io #update with container registry tag: '$(Build.BuildId)' stages: - stage: Build displayName: Build stage jobs: - job: Build displayName: Build pool: vmImage: ubuntu-latest steps: - task: Docker@2 displayName: Build and push image inputs: containerRegistry: $(dockerRegistryServiceConnection) repository: $(imageName) command: buildAndPush Dockerfile: app/Dockerfile tags: | $(tag) - publish: manifests artifact: manifests - publish: misc artifact: misc - stage: DeployCanary displayName: Deploy canary dependsOn: Build condition: succeeded() jobs: - deployment: Deploycanary displayName: Deploy canary pool: vmImage: ubuntu-latest environment: 'akscanary' strategy: runOnce: deploy: steps: - task: KubernetesManifest@1 displayName: Create Docker Registry Secret inputs: action: 'createSecret' connectionType: 'azureResourceManager' azureSubscriptionConnection: 'azure-pipelines-canary-sc' azureResourceGroup: 'my-resource-group' kubernetesCluster: 'my-aks-cluster' secretType: 'dockerRegistry' secretName: 'my-acr-secret' dockerRegistryEndpoint: 'azure-pipelines-canary-acr' - task: KubernetesManifest@1 displayName: Deploy to Kubernetes cluster inputs: action: 'deploy' connectionType: 'azureResourceManager' azureSubscriptionConnection: 'azure-pipelines-canary-sc' azureResourceGroup: 'my-resource-group' kubernetesCluster: 'my-aks-cluster' strategy: 'canary' percentage: '25' manifests: | $(Pipeline.Workspace)/manifests/deployment.yml $(Pipeline.Workspace)/manifests/service.yml containers: '$(containerRegistry)/$(imageRepository):$(tag)' imagePullSecrets: 'my-acr-secret' - task: KubernetesManifest@1 displayName: Deploy Forbio to Kubernetes cluster inputs: action: 'deploy' connectionType: 'azureResourceManager' azureSubscriptionConnection: 'azure-pipelines-canary-sc' azureResourceGroup: 'my-resource-group' kubernetesCluster: 'my-aks-cluster' manifests: '$(Pipeline.Workspace)/misc/*'
Wählen Sie Überprüfen und speichern aus, und speichern Sie die Pipeline direkt am Hauptbranch.
Hinzufügen einer manuellen Genehmigung für die Hochstufung oder Ablehnung der Canary-Bereitstellung
Sie können manuell mit YAML oder klassisch eingreifen.
- Erstellen Sie eine neue Kubernetes-Umgebung namens akspromote.
- Öffnen Sie die neue Umgebung akspromote in der Liste der Umgebungen. Wählen Sie dann Genehmigungen auf der Registerkarte Genehmigungen und Prüfungen aus.
- Fügen Sie im Bildschirm Genehmigungen Ihr eigenes Benutzerkonto unter Genehmiger hinzu.
- Erweitern Sie Erweitert, und stellen Sie sicher, dass die Option Genehmigern die Genehmigung eigener Ausführungen gestatten ausgewählt ist.
- Klicken Sie auf Erstellen.
Hinzufügen von Hochstufungs- und Ablehnungsstufen zur Pipeline
Navigieren Sie zu Pipelines, und wählen Sie die von Ihnen erstellte Pipeline aus. Wählen Sie anschließend Bearbeiten aus.
Fügen Sie die folgende
PromoteRejectCanary
-Phase am Ende der YAML-Datei hinzu, in der die Änderungen hochgestuft werden.- stage: PromoteRejectCanary displayName: Promote or Reject canary dependsOn: DeployCanary condition: succeeded() jobs: - deployment: PromoteCanary displayName: Promote Canary pool: vmImage: ubuntu-latest environment: 'akspromote' strategy: runOnce: deploy: steps: - task: KubernetesManifest@1 displayName: Create Docker Registry Secret for akspromote inputs: action: 'createSecret' connectionType: 'azureResourceManager' azureSubscriptionConnection: 'azure-pipelines-canary-sc' azureResourceGroup: 'my-resource-group' kubernetesCluster: 'my-aks-cluster' secretType: 'dockerRegistry' secretName: 'my-acr-secret' dockerRegistryEndpoint: 'azure-pipelines-canary-acr' - task: KubernetesManifest@1 displayName: promote canary inputs: action: 'promote' connectionType: 'azureResourceManager' azureSubscriptionConnection: 'azure-pipelines-canary-sc' azureResourceGroup: 'my-resource-group' kubernetesCluster: 'my-aks-cluster' strategy: 'canary' manifests: '$(Pipeline.Workspace)/manifests/*' containers: '$(containerRegistry)/$(imageRepository):$(tag)' imagePullSecrets: 'my-acr-secret' ```
Fügen Sie die folgende
RejectCanary
-Phase am Ende der Datei hinzu, in der die Änderungen zurückgenommen werden.- stage: RejectCanary displayName: Reject canary dependsOn: PromoteRejectCanary condition: failed() jobs: - deployment: RejectCanary displayName: Reject Canary pool: vmImage: ubuntu-latest environment: 'akscanary' strategy: runOnce: deploy: steps: - task: KubernetesManifest@1 displayName: Create Docker Registry Secret for reject canary inputs: action: 'createSecret' connectionType: 'azureResourceManager' azureSubscriptionConnection: 'azure-pipelines-canary-sc' azureResourceGroup: 'kubernetes-testing' kubernetesCluster: 'my-aks-cluster' secretType: 'dockerRegistry' secretName: 'my-acr-secret' dockerRegistryEndpoint: 'azure-pipelines-canary-acr' - task: KubernetesManifest@1 displayName: Reject canary deployment inputs: action: 'reject' connectionType: 'azureResourceManager' azureSubscriptionConnection: 'azure-pipelines-canary-sc' azureResourceGroup: 'my-resource-group' kubernetesCluster: 'my-aks-cluster' namespace: 'default' strategy: 'canary' manifests: '$(Pipeline.Workspace)/manifests/*' ```
Wählen Sie Überprüfen und speichern aus, und speichern Sie die Pipeline direkt am Hauptbranch.
Bereitstellen einer stabilen Version
Bei der ersten Ausführung der Pipeline sind die stabile Version der Workloads und ihre Baseline- oder Canary-Versionen nicht im Cluster vorhanden. Sie stellen eine stabile Version des Workloads sampleapp
wie folgt bereit.
Sie können eine stabile Version mit YAML oder klassisch bereitstellen.
- Ändern Sie
success_rate = 50
in app/app.py insuccess_rate = 100
. Diese Änderung löst die Pipeline, das Erstellen und Pushen des Images zur Containerregistrierung sowie dieDeployCanary
-Phase aus. - Da Sie eine Genehmigung für die Umgebung
akspromote
konfiguriert haben, wartet die Version, bevor diese Phase ausgeführt wird. Wählen Sie auf der Übersichtsseite für die Buildausführung Überprüfen und dann Genehmigen aus.
Nach der Genehmigung stellt die Pipeline die stabile Version des Workloads sampleapp
in manifests/deployment.yml für den Namespace bereit.
Initiieren des Canary-Workflows und Ablehnen der Genehmigung
Die stabile Version des Workloads sampleapp
ist jetzt im Cluster vorhanden. Nehmen Sie als Nächstes an der Simulationsanwendung die folgende Änderung vor.
- Ändern Sie
success_rate = 50
in app/app.py insuccess_rate = 100
. Diese Änderung löst die Pipeline, das Erstellen und Pushen des Images zur Containerregistrierung sowie dieDeployCanary
-Phase aus. - Da Sie eine Genehmigung für die Umgebung
akspromote
konfiguriert haben, wartet die Version, bevor diese Phase ausgeführt wird. - Wählen Sie auf der Zusammenfassungsseite „Buildausführung“ die Option Überprüfen und dann Ablehnen im nachfolgenden Dialogfeld aus. Dadurch wird die Bereitstellung abgelehnt.
Nach der Ablehnung verhindert die Pipeline die Codebereitstellung.
Bereinigung
Wenn Sie diese Anwendung nicht weiter verwenden möchten, löschen Sie die Ressourcengruppe im Azure-Portal und das Projekt in Azure DevOps.