Remarque
L’accès à cette page nécessite une autorisation. Vous pouvez essayer de vous connecter ou de modifier des répertoires.
L’accès à cette page nécessite une autorisation. Vous pouvez essayer de modifier des répertoires.
La création d’un processus d’intégration continue et de livraison continue (CI/CD) fiable pour une architecture de microservices peut être difficile. Chaque équipe doit libérer des services rapidement et de manière fiable, sans perturber d’autres équipes ou déstabiliser l’application dans son ensemble.
Cet article décrit un exemple de pipeline CI/CD pour le déploiement de microservices sur Azure Kubernetes Service (AKS). Chaque équipe et chaque projet étant uniques, cet article ne doit pas être considéré comme un ensemble de règles à suivre à la lettre. Utilisez-le plutôt comme point de départ pour concevoir votre propre processus CI/CD.
La liste suivante résume les objectifs d’un pipeline CI/CD pour les microservices hébergés par Kubernetes :
- Les équipes peuvent générer et déployer leurs services en toute indépendance.
- Les modifications de code qui passent le processus CI sont automatiquement déployées dans un environnement de type production.
- Chaque étape du pipeline applique des points de contrôle qualité.
- Une nouvelle version d'un service peut être déployée aux côtés de la version précédente.
Pour plus d’informations, consultez CI/CD pour les architectures de microservices.
Hypothèses
Pour cet exemple, voici quelques hypothèses sur l’équipe de développement et la base de code :
- Le référentiel de code est un monorepo, avec des dossiers organisés par microservice.
- La stratégie de création de branche de l’équipe est basée sur un développement de type tronc.
- L'équipe utilise des branches de mise en production pour gérer les mises en production. Des mises en production distinctes sont créées pour chaque microservice.
- Le processus CI/CD utilise Azure Pipelines pour générer, tester et déployer les microservices sur AKS.
- Les images conteneur pour tous les microservices sont stockées dans une instance de Azure Container Registry partagée unique, avec un référentiel distinct pour chaque microservice. Utilisez les autorisations ABAC de dépôt d’Azure Container Registry pour limiter chaque identité de pipeline à son propre dépôt, ou utilisez des registres séparés lorsque des frontières de confiance plus strictes sont requises.
- L'équipe utilise des graphiques Helm pour empaqueter chaque microservice.
- Un modèle de déploiement Push est utilisé, où Azure Pipelines et les agents associés effectuent des déploiements en se connectant directement au cluster AKS.
Ces hypothèses déterminent un certain nombre de détails spécifiques au pipeline CI/CD. Toutefois, vous pouvez adapter l’approche de base décrite ici pour d’autres processus, outils et services, tels que GitHub Actions, Jenkins ou Docker Hub.
Autres solutions
Lorsque vous choisissez une stratégie CI/CD avec AKS, tenez compte des alternatives courantes suivantes :
Au lieu d’utiliser Helm comme outil de gestion et de déploiement de package, vous pouvez utiliser Kustomize, un outil de gestion de configuration native Kubernetes qui introduit un moyen gratuit pour personnaliser et paramétrer la configuration de l’application.
Au lieu d’utiliser Azure DevOps pour les référentiels et pipelines Git, vous pouvez utiliser GitHub référentiels pour les référentiels Git privés et publics, et GitHub Actions pour les pipelines CI/CD.
GitHub Actions fournit une intégration à AKS avec des flux de travail de démarrage et prend en charge OpenID Connect (OIDC) pour une authentification sécurisée et sans secret pour Azure.
Au lieu d’utiliser un modèle de déploiement Push, envisagez de gérer la configuration kubernetes à grande échelle à l’aide d’un modèle de déploiement GitOps (pull deployment model) . Un opérateur Kubernetes en cluster tel que Flux ou Argo CD synchronise l’état du cluster en fonction de la configuration stockée dans un référentiel Git. GitOps élimine la nécessité pour les pipelines d’avoir un accès direct au cluster, réduit la surface d’attaque et fournit des fonctionnalités de détection d’auto-guérison et de dérive.
Tip
Lors de l’évaluation des modèles de déploiement basés sur push ou pull (GitOps), tenez compte des besoins de votre charge de travail. Les déploiements basés sur push offrent des mises à jour déterministes et un contrôle de pipeline direct, qui conviennent aux pratiques de déploiement sécurisées. Les déploiements GitOps de type pull offrent cohérence, auditabilité et autoréparation, ce qui les rend idéaux pour les environnements où les clusters doivent converger vers un état souhaité sans accès direct du pipeline aux clusters.
Builds de validation
Supposons qu’un développeur travaille sur un microservice appelé Delivery Service. Lors du développement d’une nouvelle fonctionnalité, le développeur vérifie le code dans une branche de fonctionnalité. Par convention, les branches de fonctionnalité sont nommées feature/*.
Le schéma montre deux lignes horizontales représentant des branches Git et un pipeline de compilation en dessous de celles-ci. En haut est la branche principale, représentée sous la forme d’une ligne horizontale. La branche 8150 diffère de la branche principale. Cette branche comporte trois points situés dessus, appelés collectivement « commits ». Depuis chacun des trois commits, une flèche pointe vers le bas en direction d’un encadré situé en bas du diagramme. La zone porte l’étiquette Pipeline de build et contient le nom du pipeline ci-delivery-validation. Les trois flèches en pointillés convergent vers ce bloc unique du pipeline de build, ce qui indique que chaque commit sur la branche feature/8150 déclenche une exécution du pipeline ci-delivery-validation.
Le fichier de définition de build inclut un déclencheur qui filtre par nom de branche et par chemin source :
trigger:
batch: true
branches:
include:
# for new release to production: release flow strategy
- release/delivery/v*
- refs/release/delivery/v*
- main
- feature/delivery/*
- topic/delivery/*
paths:
include:
- /src/shipping/delivery/
Lorsque vous utilisez cette approche, chaque équipe peut avoir son propre pipeline de build. Seul le code archivé dans le /src/shipping/delivery dossier déclenche une build de Delivery Service. L'envoi (push) des validations vers une branche qui correspond au filtre déclenche une build CI. À ce stade du workflow , la build CI exécute une vérification minimale du code :
- Compiler le code.
- Exécution de tests unitaires
L'objectif est de réduire les délais de build pour que le développeur obtienne des commentaires rapides. Lorsque la fonctionnalité est prête à être fusionnée dans la branche principale, le développeur ouvre une pull request. Cette opération déclenche une autre build CI qui effectue des vérifications supplémentaires :
- Compiler le code.
- Exécution de tests unitaires
- Exécutez le test de sécurité des applications statiques (SAST) sur le code source.
- Génération de l'image du conteneur d'exécution
- Exécution d'analyses de vulnérabilité sur l'image
Le schéma montre deux lignes horizontales représentant des branches Git et un pipeline de compilation en dessous de celles-ci. En haut est la branche principale, représentée sous la forme d’une ligne horizontale. En dessous, la branche feature/8150 est parallèle à celle-ci et comporte trois points représentant des commits. À l’extrémité droite de la branche feature/8150, une flèche en pointillés relie un point de la branche principale. Ce point est repéré par un autre point étiqueté PR, ce qui indique qu’une pull request a été ouverte sur la branche main. À partir du point de PR sur la branche principale, une flèche en pointillés pointe vers le bas en direction d’une boîte intitulée « Build pipeline », qui contient le nom du pipeline ci-delivery-full. Cette ligne illustre que l’ouverture d’une pull request de la branche feature vers main déclenche le pipeline ci-delivery-full, qui exécute l’ensemble étendu des vérifications d’intégration continue.
Note
Dans Azure Repos, l’un des services de Azure DevOps, vous pouvez définir des stratégies pour protéger les branches. Par exemple, la stratégie peut nécessiter une build CI réussie et une validation par un approbateur avant la fusion dans la branche main.
Build CI/CD complète
Lorsque l’équipe est prête à déployer une nouvelle version de Delivery Service, le gestionnaire de versions crée une branche à partir de la branche principale, à l’aide de ce modèle d’affectation de noms : release/<microservice name>/<semver>. Par exemple : release/delivery/v1.0.2.
La création de cette branche déclenche une build CI complète qui exécute toutes les étapes précédentes et les étapes suivantes :
- Envoyez l’image conteneur à Container Registry. L’image est étiquetée avec le numéro de version dans le nom de la branche.
- L'exécution de
helm packageafin d'empaqueter le graphique Helm pour le service. Le graphique est également étiqueté avec un numéro de version. - L'envoi (push) du package Helm à Container Registry.
Si cette build réussit, elle déclenche un processus de déploiement (CD) avec un pipeline de mise en production Azure Pipelines. Ce pipeline contient les étapes suivantes :
- Déployez le graphique Helm sur un environnement AQ.
- Un approbateur effectue une validation avant que le package passe en production. Consultez Contrôler le déploiement de mise en production avec des approbations.
- Réétiquetez l’image Docker pour l’espace de nommage de production dans Container Registry. Par exemple, si l’étiquette actuelle est
myrepo.azurecr.io/delivery:v1.0.2, l’étiquette de production estmyrepo.azurecr.io/prod/delivery:v1.0.2. - Déployez le graphique Helm dans l'environnement de production.
Même dans un monorepo, limitez ces tâches à des microservices individuels afin que les équipes puissent déployer indépendamment. Le processus comprend quelques étapes manuelles : approbation des demandes de tirage, création de branches de mise en production et approbation des déploiements dans le cluster de production. Les équipes de charge de travail peuvent automatiser ces étapes si elles le souhaitent.
Isolation des environnements
Vous déployez des services dans plusieurs environnements, notamment les environnements de développement, de test de fumée, de test d’intégration, de test de charge et de production. Ces environnements ont besoin d’un certain niveau d’isolation. Dans Kubernetes, vous pouvez choisir entre l’isolation physique et l’isolation logique. L’isolation physique est déployée dans des clusters séparés. L’isolation logique utilise des espaces de noms et des politiques.
Notre recommandation est de créer un cluster de production dédié avec un cluster distinct pour vos environnements de développement/test. L’isolation logique permet de séparer les environnements au sein du cluster de développement/test. Les services déployés sur le cluster de développement/test ne doivent jamais avoir accès à des magasins de données qui contiennent des données métier.
Pour appliquer l’isolation au sein d’un cluster, procédez comme suit :
-
Espaces de noms : Utilisez des espaces de noms Kubernetes pour séparer logiquement les environnements (par exemple,
dev,staging,qa). - Stratégies réseau : appliquez des stratégies réseau Kubernetes pour refuser la communication pod-à-pod entre les espaces de noms.
- Quotas de ressources : appliquez des quotas de ressources par espace de noms pour éviter les problèmes de voisin bruyant dans les clusters partagés.
- Intégration de Microsoft Entra ID : combinez l’authentification Microsoft Entra ID avec Kubernetes RBAC et Microsoft Entra ID pour contrôler quels utilisateurs et groupes Microsoft Entra peuvent accéder à chaque espace de noms.
Authentification et autorisation
Utilisez l’authentification sans secret dans la mesure du possible, à la fois pour les pipelines qui déploient vos microservices et pour les charges de travail que ces pipelines déploient :
- Fédération d’identités de charge de travail pour les pipelines : pour Azure Pipelines, utilisez une connexion de service de fédération d’identités de charge de travail pour vous authentifier auprès d’Azure sans stocker de secrets de principal de service à longue durée de vie. Pour GitHub Actions, configurez OIDC pour obtenir la même authentification sans secret.
- ID de charge de travail Microsoft Entra pour les charges de travail déployées : configurez les microservices que votre pipeline déploie pour utiliser ID de charge de travail Microsoft Entra au lieu d’injecter des informations d’identification via des manifestes, des valeurs Helm ou des secrets Kubernetes. L’ID de charge de travail fédère les comptes de service Kubernetes avec Microsoft Entra ID afin que les pods puissent s’authentifier auprès de Azure services (tels que Azure Key Vault, Container Registry ou Azure SQL) sans que le pipeline gère les secrets.
Gestion des secrets
N’incorporez jamais de secrets (chaînes de connexion, clés API, mots de passe de base de données) directement dans le code source, les fichiers Dockerfiles, les fichiers de valeurs Helm ou les définitions de pipeline. Au lieu de:
- Stockez les secrets dans Key Vault.
- Utilisez le fournisseur Key Vault pour Secrets Store CSI Driver pour monter directement des secrets dans des pods sous forme de volumes ou de variables d’environnement. Cette approche évite de stocker les secrets dans les objets Kubernetes
Secret, qui sont encodés en base64, mais non chiffrés par défaut. - Pour les secrets du pipeline, utilisez l’intégration de Key Vault à Azure Pipelines ou les secrets GitHub Actions.
- Activez la suppression réversible et la protection contre la purge dans Key Vault afin de vous protéger contre la suppression accidentelle ou malveillante de secrets.
Important
Évitez de stocker des informations d’identification de longue durée (secrets client, certificats ou mots de passe) dans des variables de pipeline, des variables d’environnement ou des secrets Kubernetes. Utilisez plutôt des identités managées et des informations d’identification fédérées pour réduire la charge de rotation des informations d’identification et la surface d’attaque.
Processus de génération
Si possible, empaquetez votre processus de génération dans un conteneur Docker. Cette configuration vous permet de générer des artefacts de code à l’aide de Docker sans configurer un environnement de build sur chaque machine de build. Un processus de construction conteneurisé simplifie l'extension horizontale du pipeline CI en ajoutant de nouveaux agents de construction. En outre, tout développeur de l’équipe peut générer le code en exécutant le conteneur de build.
À l’aide de builds multistage dans Docker, vous pouvez définir l’environnement de génération et l’image runtime dans un fichier Dockerfile unique. Par exemple, le fichier Dockerfile suivant génère une application .NET 10 :
FROM mcr.microsoft.com/dotnet/aspnet:10.0 AS base
USER app
WORKDIR /app
EXPOSE 8080
FROM mcr.microsoft.com/dotnet/sdk:10.0 AS build
WORKDIR /src/Fabrikam.Workflow.Service
COPY Fabrikam.Workflow.Service/Fabrikam.Workflow.Service.csproj .
RUN dotnet restore Fabrikam.Workflow.Service.csproj
COPY Fabrikam.Workflow.Service/. .
RUN dotnet build Fabrikam.Workflow.Service.csproj -c Release -o /app/build --no-restore
FROM build AS testrunner
WORKDIR /src/tests
COPY Fabrikam.Workflow.Service.Tests/*.csproj .
RUN dotnet restore Fabrikam.Workflow.Service.Tests.csproj
COPY Fabrikam.Workflow.Service.Tests/. .
ENTRYPOINT ["dotnet", "test", "--logger:trx"]
FROM build AS publish
RUN dotnet publish Fabrikam.Workflow.Service.csproj -c Release -o /app/publish
FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .
ENTRYPOINT ["dotnet", "Fabrikam.Workflow.Service.dll"]
Ce Dockerfile définit plusieurs étapes de génération. Notez que l’étape nommée base utilise l’image runtime .NET 10 ASP.NET, tandis que la phase nommée build utilise le kit SDK complet .NET 10. L’étape build génère le projet .NET. Mais le conteneur d'exécution final est généré à partir de base, qui ne contient que le runtime et est nettement plus petit que l'image SDK complète.
Important
À partir de .NET 8, les images de conteneur .NET officielles basées sur Linux incluent un utilisateur non racine appelé app. L’instruction USER app du fichier Dockerfile exécute le conteneur en tant qu’utilisateur non privilégié, en suivant le principe des privilèges minimum. Les images de conteneur ASP.NET Core ont également vu leur port d’écoute par défaut passer de 80 à 8080.
Générer un Test Runner
Une autre bonne pratique consiste à exécuter des tests unitaires dans le conteneur. Par exemple, le code suivant montre une partie d’un fichier Dockerfile qui génère un exécuteur de test :
FROM build AS testrunner
WORKDIR /src/tests
COPY Fabrikam.Workflow.Service.Tests/*.csproj .
RUN dotnet restore Fabrikam.Workflow.Service.Tests.csproj
COPY Fabrikam.Workflow.Service.Tests/. .
ENTRYPOINT ["dotnet", "test", "--logger:trx"]
Un développeur peut utiliser ce fichier Dockerfile pour exécuter les tests localement :
docker build . -t delivery-test:1 --target=testrunner
docker run delivery-test:1
Le pipeline CI doit également exécuter les tests dans le cadre de l'étape de vérification de build.
Ce fichier utilise la commande Docker, et non la commande Docker ENTRYPOINTRUN , pour exécuter les tests.
- Si vous utilisez la commande
RUN, les tests s'exécutent chaque fois que vous générez l'image. Si vous utilisezENTRYPOINT, les tests sont opt-in. Ils ne s'exécutent que lorsque vous ciblez explicitement l'étapetestrunner. - Un échec au test n'entraîne pas l'échec de la commande Docker
build. Ce comportement vous permet de distinguer les échecs de build de conteneur des échecs de test. - Les résultats des tests peuvent être enregistrés sur un volume monté.
Meilleures pratiques en matière de conteneurs
Voici quelques autres bonnes pratiques à prendre en compte pour les conteneurs :
- Définissez des conventions à l’échelle de l’organisation pour les étiquettes de conteneur, le contrôle de version et les conventions d’affectation de noms pour les ressources déployées sur le cluster (par exemple, les pods et les services). L’utilisation de ces conventions permet de diagnostiquer plus facilement les problèmes de déploiement.
- Pendant le cycle de développement et de test, le processus CI/CD génère de nombreuses images conteneur. Seules certaines de ces images sont candidates à la publication, et seules certaines de ces candidates sont promues en production. Disposez d’une stratégie de contrôle de version claire afin de savoir quelles images sont actuellement déployées en production et pouvez facilement revenir à une version précédente si nécessaire.
- Déployez toujours des balises de version de conteneur spécifiques, et non
latest. - Utilisez des espaces de noms dans Container Registry pour isoler les images approuvées pour la production des images qui sont toujours en cours de test. Ne déplacez pas une image dans l'espace de noms de production tant que vous n'êtes pas prêt à la déployer en production. La combinaison de cette pratique avec le contrôle de version sémantique des images conteneur peut réduire les risques de déploiement accidentel d’une version qui n’est pas approuvée pour la mise en production.
- Suivez le principe du moindre privilège en exécutant des conteneurs en tant qu'utilisateur non privilégié. Dans Kubernetes, utilisez Pod Security Standards avec Pod Security admission (qui a remplacé les Pod Security Policies obsolètes dans Kubernetes 1.25) pour appliquer des restrictions, comme empêcher les conteneurs de s’exécuter en tant que root. Utilisez le profil
restrictedpour les charges de travail en production. - Utilisez des images de base minimales ou distroless (par exemple, des images basées sur Alpine, des images de base Azure Linux ou des images distroless, ou des images .NET allégées) pour réduire la surface d’attaque de vos images conteneur.
- Pour les registres Premium, configurez une stratégie de rétention Container Registry pour supprimer des manifestes non étiquetés. Pour vider les balises par âge ou par nom, planifiez une tâche Container Registry qui exécute acr purge. Conservez les images utilisées par les déploiements actifs et les plans de retour arrière.
Graphiques Helm
Envisagez d’utiliser Helm pour gérer la génération et le déploiement des services. Les fonctionnalités Helm suivantes prennent en charge un pipeline CI/CD :
- Un seul microservice est souvent défini par plusieurs objets Kubernetes. Helm permet à ces objets d’être empaquetés dans un seul graphique Helm.
- Vous pouvez déployer un graphique à l’aide d’une seule commande Helm plutôt qu’une série de commandes kubectl.
- Les graphiques sont explicitement versionnés. Utilisez Helm pour publier une version, visualiser les versions et revenir à une version précédente. Helm utilise le contrôle de version sémantique pour suivre les mises à jour et les révisions.
- Les charts Helm utilisent des modèles pour éviter la duplication d'informations, telles que les étiquettes et les sélecteurs, dans de nombreux fichiers.
- Helm peut gérer les dépendances entre les graphiques.
- Vous pouvez stocker des graphiques dans un référentiel Helm, tel que Container Registry, et les intégrer dans le pipeline de build.
Pour plus d’informations, consultez Utiliser Container Registry comme référentiel Helm pour vos graphiques d’applications.
Un seul microservice peut nécessiter plusieurs fichiers de configuration Kubernetes. Pour mettre à jour un service, vous devrez peut-être modifier tous ces fichiers pour mettre à jour des sélecteurs, des étiquettes et des étiquettes d’image. Helm traite ces fichiers comme un package unique appelé graphique et facilite la mise à jour des fichiers YAML à l’aide de variables. Helm utilise un langage de modèle (basé sur des modèles Go) qui vous permet d’écrire des fichiers de configuration YAML paramétrables.
Par exemple, voici un extrait de fichier YAML qui définit un déploiement :
apiVersion: apps/v1
kind: Deployment
metadata:
name: {{ include "package.fullname" . | replace "." "" }}
labels:
app.kubernetes.io/name: {{ include "package.name" . }}
app.kubernetes.io/instance: {{ .Release.Name }}
annotations:
kubernetes.io/change-cause: {{ .Values.reason }}
...
spec:
template:
spec:
containers:
- name: &package-container_name fabrikam-package
image: {{ .Values.dockerregistry }}/{{ .Values.image.repository }}:{{ .Values.image.tag }}
imagePullPolicy: {{ .Values.image.pullPolicy }}
env:
- name: LOG_LEVEL
value: {{ .Values.log.level }}
Vous pouvez voir que le nom de déploiement, les étiquettes et les spécifications de conteneur utilisent tous les paramètres de modèle, que vous fournissez au moment du déploiement. Par exemple, à partir de la ligne de commande :
helm install <release-name> oci://<registry>/<repository>/<package-chart-name> --version <desiredVersion> \
--set image.tag=0.1.0 \
--set image.repository=package \
--set dockerregistry=$ACR_SERVER \
--namespace backend
Bien qu’un pipeline CI/CD puisse installer un graphique directement dans Kubernetes, créez une archive de graphique (fichier.tgz) et envoyez le graphique à un référentiel Helm tel que Container Registry. Pour plus d’informations, consultez Package et déploiement de graphiques Helm (tâche HelmDeploy).
Revisions
Les charts Helm ont toujours un numéro de version qui doit utiliser le versionnage sémantique. Un graphique peut également avoir une appVersion. Ce champ est facultatif et n’a pas besoin d’être lié à la version du graphique. Certaines équipes peuvent vouloir versionr des applications séparément des mises à jour des graphiques. Une approche plus simple consiste à utiliser un numéro de version. Il existe donc une relation 1:1 entre la version du graphique et la version de l’application. Vous pouvez ainsi stocker un graphique par version et déployer facilement la version souhaitée :
helm install <package-chart-name> --version <desiredVersion>
Une autre bonne pratique consiste à fournir une annotation sur la cause de la modification dans le modèle de déploiement :
apiVersion: apps/v1
kind: Deployment
metadata:
name: {{ include "delivery.fullname" . | replace "." "" }}
labels:
...
annotations:
kubernetes.io/change-cause: {{ .Values.reason }}
Cette annotation vous permet d’afficher le champ de modification de chaque révision à l’aide de la kubectl rollout history commande. Dans l’exemple précédent, la cause des modifications est fournie en tant que paramètre de graphique Helm.
kubectl rollout history deployments/delivery-v010 -n backend
deployment.apps/delivery-v010
REVISION CHANGE-CAUSE
1 Initial deployment
Vous pouvez également utiliser la commande helm list pour afficher l'historique des révisions :
helm list -n backend
NAME NAMESPACE REVISION UPDATED STATUS CHART APP VERSION
delivery-v0.1.0 backend 1 2024-04-07 00:25:30.000000 +0000 UTC deployed delivery-v0.1.0 v0.1.0
Azure Pipelines
Azure Pipelines, un service dans Azure DevOps, a deux types de pipelines : les pipelines de build et les pipelines de mise en production. Le pipeline de build exécute le processus CI et crée des artefacts de build. Pour une architecture de microservices sur Kubernetes, ces artefacts sont les images conteneur et les graphiques Helm qui définissent chaque microservice. Le pipeline de mise en production exécute le processus CD qui déploie un microservice dans un cluster.
En fonction du flux CI décrit plus haut dans cet article, un pipeline de build peut être constitué des tâches suivantes :
- Créez le conteneur d’exécution des tests à l’aide de la tâche
Docker. - Exécutez les tests en invoquant
docker runsur le conteneur d’exécution des tests à l’aide de la tâcheDocker. - Publiez les résultats des tests à l’aide de la
PublishTestResultstâche. Pour plus d’informations, consultez Générer une image. - Exécutez SAST sur le code source.
- Créez le conteneur d’exécution en utilisant
docker buildlocal et la tâcheDocker, ou en utilisant les builds de Container Registry et la tâcheAzureCLI. Générez une facture logicielle de matériaux (SBOM) pour l’image, par exemple à l’aide de l’outil SBOM Microsoft, puis publiez-la en tant qu’artefact de pipeline associé à la synthèse de l’image ou attachez-la à l’image dans Container Registry. - Exécutez l’analyse des vulnérabilités d’image conteneur (par exemple, à l’aide de Microsoft Defender pour conteneurs ou d’un outil non Microsoft comme Trivy) pour détecter les vulnérabilités connues avant la publication de l’image.
- Envoyez l’image de conteneur vers Container Registry (ou vers un autre registre de conteneurs) à l’aide de la tâche
DockerouAzureCLI. - Signez l’image poussée par condensat immuable afin de garantir son intégrité et son authenticité. Pour Azure Pipelines, suivez les instructions de signature de notation.
- Empaqueter le graphique Helm à l’aide de la
HelmDeploytâche. - Envoyez le paquet Helm vers Container Registry (ou vers un autre référentiel Helm) en utilisant la tâche
HelmDeploy.
La sortie du pipeline CI est composée d'une image conteneur prête pour la production et d'un graphique Helm mis à jour pour le microservice. À ce stade, le pipeline de mise en production peut prendre le relais. Il existe un pipeline de mise en production unique pour chaque microservice. Le pipeline de mise en production est configuré pour avoir une source de déclencheur définie sur le pipeline CI qui a publié l’artefact. Ce pipeline vous permet de déployer chaque microservice indépendamment. Le pipeline de mise en production effectue les étapes suivantes :
- Déployer le graphique Helm sur des environnements dev/QA/intermédiaires. Vous pouvez utiliser la
helm upgradecommande avec l’indicateur--installpour prendre en charge la première installation et les mises à niveau suivantes. - Attendre qu'un approbateur approuve ou rejette le déploiement
- Ré-étiquetez l'image conteneur pour la mise en production.
- Envoyer (push) l'étiquette de mise en production au registre de conteneurs
- Déployer le graphique Helm dans le cluster de production. Utilisez Ratification avec Azure Policy pour valider les signatures d’images lors de l’admission et configurer séparément une stratégie d’images autorisées pour restreindre les images aux registres approuvés.
Note
Pour permettre à AKS d’extraire des images de Container Registry sans secrets d’extraction d’images distincts, utilisez l’intégration AKS-to-Container-Registry pour un registre qui utilise le RBAC à l’échelle du registre. Pour un registre compatible ABAC, cette intégration n’est pas prise en charge. À la place, attribuez le rôle Container Registry Repository Reader à l’identité managée par kubelet du cluster.
Pour plus d'informations sur la création d'un pipeline de mise en production, consultez Pipelines de mise en production, versions préliminaires et options de mise en production.
Le diagramme suivant illustre le processus CI/CD de bout en bout décrit dans cet article :
alternative à GitHub Actions
Si votre équipe utilise GitHub pour le contrôle de code source, GitHub Actions fournit une plateforme CI/CD équivalente. Outre les flux de travail de démarrage et l’authentification OIDC notés précédemment, tenez compte de ces fonctionnalités spécifiques aux GitHub lorsque vous ciblez AKS :
- Environnements et règles de protection. Si votre plan de GitHub et la visibilité des référentiels les prennent en charge, utilisez des environnements GitHub avec les réviseurs, les minuteurs d’attente et les branches de déploiement nécessaires pour implémenter des portes d’approbation.
- Analyse du conteneur. Utilisez les actions de la marketplace GitHub Actions pour Trivy, Microsoft Defender pour DevOps ou des outils similaires afin d’analyser directement les images de conteneur dans votre flux de travail.
Observabilité et supervision
Implémentez l’observabilité dans l’ensemble du pipeline CI/CD et de l’environnement d’exécution :
- Surveillance du pipeline. Suivez les durées de build, les taux de réussite de test, la fréquence de déploiement et les taux d’échec. Azure DevOps fournit des analyses intégrées. GitHub Actions peut utiliser des tableaux de bord non-Microsoft.
- Surveillance du runtime. Utilisez Azure Monitor service managé pour Prometheus et Azure Managed Grafana pour surveiller les métriques d’intégrité et de charge de travail du cluster AKS.
- Télémétrie d’application. Instrumentez vos microservices avec Azure Monitor Application Insights pour le suivi distribué, la journalisation des requêtes et le suivi des dépendances.
- Avertissement. Configurez les alertes pour les échecs de déploiement, les redémarrages de pods, les taux d’erreur élevés et la saturation des ressources pour permettre une réponse rapide aux incidents.
Alignement sur le Well-Architected Framework
Lorsque vous concevez votre pipeline CI/CD pour les microservices sur Kubernetes, tenez compte des piliers de l’infrastructure Azure Well-Architected :
| Pilier | Considerations |
|---|---|
| Fiabilité | Stratégies de retour arrière automatisées, sondes d’intégrité pour les déploiements, stratégies de déploiement bleu-vert ou canari, budgets de perturbation des pods. |
| Security | Authentification sans secret (ID de charge de travail, OIDC), signature d’image, sécurité de la chaîne logistique, RBAC avec privilège minimum, stratégies réseau. |
| Optimisation des coûts | Dimensionnement adapté des agents de build, utilisation d’exécuteurs auto-hébergés éphémères, mise en place de stratégies de conservation des images du Container Registry, et utilisation de pools de nœuds Spot uniquement pour des charges de travail hors production tolérant les interruptions. |
| Excellence opérationnelle | GitOps pour les déploiements déclaratifs, l’infrastructure en tant que code, le pipeline en tant que code (YAML), l’observabilité et l’automatisation des runbooks. |
| Efficacité des performances | Étapes de pipeline parallèles, mise en cache de build (mise en cache de couche Docker, mise en cache des dépendances), mise à l’échelle automatique des pods horizontaux. |
Contributors
Microsoft conserve cet article. Les contributeurs suivants ont écrit cet article.
Auteur principal :
- Ray Kao | Ingénieur solutions principales
Pour afficher les profils LinkedIn non publics, connectez-vous à LinkedIn.
Étapes suivantes
- Adopter une stratégie de branchement Git
- Qu’est-ce qu’Azure Pipelines ?
- Pipelines de déploiement, versions préliminaires et options de déploiement
- Contrôle de déploiement à l’aide d’approbations
- Présentation d’Azure Container Registry
- ID de charge de travail Microsoft Entra avec AKS
- Fournisseur Azure Key Vault pour le pilote Secrets Store CSI.
- DevSecOps sur AKS