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 portes de 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 Container Registry Azure autorisations de référentiel ABAC pour étendre chaque identité de pipeline à son propre référentiel, ou utilisez des registres distincts où des limites de confiance plus fortes 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 (Pull) offrent une cohérence, une auditabilité et une auto-réparation, ce qui les rend idéaux pour les environnements où les clusters doivent se rapprocher d’un état souhaité sans accès direct de pipeline à cluster.
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 diagramme montre deux lignes de branche Git horizontales et un pipeline de build en dessous. 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 a trois points placés sur elle, des validations étiquetées collectivement. À partir de chacune des trois validations, une flèche pointe vers le bas vers le bas d’une zone en bas du diagramme. La zone est étiquetée Pipeline de build et contient le nom du pipeline ci-delivery-validation. Les trois flèches en pointillés convergent sur cette zone de pipeline de build unique, indiquant que chaque validation sur la branche 8150 déclenche une exécution du pipeline de validation ci-delivery.
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 en main, le développeur ouvre une demande de tirage. 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 diagramme montre deux lignes de branche Git horizontales et un pipeline de build en dessous. En haut est la branche principale, représentée sous la forme d’une ligne horizontale. En dessous, la branche 8150 de fonctionnalité s’exécute parallèlement à celle-ci et a trois points sur celui-ci qui représentent des validations. À l’extrémité droite de la branche 8150, une flèche pointillée se connecte à un point sur la branche principale. Ce point est marqué avec un autre point étiqueté PR, indiquant qu’une demande de tirage a été ouverte sur main. À partir du point de demande de tirage sur la branche principale, une flèche en pointillés pointe vers le bas vers le bas vers un pipeline de build étiqueté, qui contient le nom de pipeline ci-delivery-full. Cette ligne illustre que l’ouverture d’une demande de tirage à partir de la branche de fonctionnalité pour déclencher le pipeline ci-delivery-full, qui exécute l’ensemble étendu de vérifications CI.
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 déconnexion d’un approbateur avant une fusion en main.
Construction intégrale CI/CD
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.
Le diagramme montre trois lignes de branche Git horizontales et deux pipelines en dessous. Au milieu est la branche principale, représentée sous la forme d’une ligne horizontale. Ci-dessous est la branche 8150 de fonctionnalité, qui a trois points sur celui-ci qui représentent des validations. La branche de fonctionnalité/8150 se connecte à la branche principale à un point étiqueté fusion, indiquant que la branche de fonctionnalité est fusionnée dans la branche principale. Au-dessus et à droite de la branche principale, une nouvelle branche étiquetée release/delivery/v1.0.2 s’étend à droite. Cette branche de mise en production provient du principal à un point à droite de la fusion. À partir de la branche release/delivery/v1.0.2, une ligne pointillée vers le bas vers une boîte intitulée ci-delivery-full, qui se trouve au-dessus du pipeline de build d’étiquette. À droite de ci-delivery-full, une flèche horizontale pointe vers une deuxième zone intitulée cd-delivery, qui se trouve au-dessus du pipeline de mise en production de l’étiquette.
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.
- Exécutez
helm packagepour empaqueter le graphe Helm pour le service. Le graphique est également étiqueté avec un numéro de version. - Pousser le package Helm dans le registre de conteneurs.
Si cette build réussit, elle déclenche un processus de déploiement (CD) à l’aide d’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ôle du déploiement des versions à l'aide d'approbations.
- Rétagation de l’image Docker pour l’espace de noms 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 sur des clusters distincts. L’isolation logique utilise des espaces de noms et des stratégies.
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 Microsoft Entra ID : combinez l’authentification Microsoft Entra ID avec Kubernetes RBAC et Microsoft Entra ID pour contrôler quelles Microsoft Entra utilisateurs et groupes 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 des identités de charge de travail pour les pipelines : pour Azure Pipelines, utilisez une connexion de service de fédération d’identité de charge de travail pour s’authentifier auprès de Azure sans stocker de secrets de principal de service de longue durée. 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 le pilote CSI du magasin de secrets pour monter des secrets directement dans des pods en tant que volumes ou variables d’environnement. Cette approche empêche les secrets des objets Kubernetes
Secret, qui sont codés en base64, non chiffrés par défaut. - Pour les secrets de pipeline, utilisez Key Vault intégration à Azure Pipelines ou GitHub Actions secrets.
- Activez Key Vault protection contre la suppression réversible et le vidage pour 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 compilation
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
À compter de .NET 8, les images conteneur .NET linux officielles 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. ASP.NET Core images conteneur ont également changé leur port d’écoute par défaut 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 à partir d’images qui sont toujours testées. 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 les normes de sécurité des pods avec l’admission pod security (qui a remplacé les stratégies de sécurité pod déconseillées dans Kubernetes 1.25) pour appliquer des restrictions telles que l’empêchement des conteneurs de s’exécuter en tant que racine. Utilisez le
restrictedprofil pour les charges de travail de production. - Utilisez des images de base minimales ou distroless (par exemple, des images alpines, Azure une base Linux ou des images distroless, ou des images .NET ciseaux) 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 référencées par les déploiements actifs et les plans de restauration.
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 graphiques Helm ont toujours un numéro de version qui doit utiliser le contrôle de version 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 éléments de construction. 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 :
- Générez le conteneur d’exécuteur de test à l’aide de la
Dockertâche. - Exécutez les tests en appelant
docker runle conteneur de l’exécuteur de test à l’aide de laDockertâche. - 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.
- Générez le conteneur d’exécution à l’aide de la tâche locale
docker buildet de laDockertâche ou à l’aide des builds container Registry et de laAzureCLItâche. 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 (push) l’image conteneur à Container Registry (ou à un autre registre de conteneurs) à l’aide de la tâche ou
AzureCLIde laDockertâche. - Signer l’image envoyée par synthèse immuable pour 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 package Helm à Container Registry (ou à un autre référentiel Helm) à l’aide de la
HelmDeploytâche.
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é avec comme source de déclenchement 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
- Retagez 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. Au lieu de cela, attribuez le Container Registry Repository Reader rôle à l’identité managée 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 GitHub Actions actions de la Place de marché pour Trivy, Microsoft Defender pour DevOps ou des outils similaires pour l’analyse d’images conteneur directement 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 pouvez 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 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 restauration automatisées, sondes d’intégrité sur les déploiements, stratégies de mise en production bleu-vert ou canary, budgets d’interruption 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 approprié des agents de build, en utilisant des exécuteurs auto-hébergés éphémères, en implémentant des stratégies de rétention d’images Container Registry et en utilisant des pools de nœuds spot uniquement pour les charges de travail hors production tolérantes aux 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 CSI Secrets Store
- DevSecOps sur AKS