8.4. Utilisation de stratégies de déploiement basées sur les itinéraires
Les stratégies de déploiement permettent à l'application d'évoluer. Certaines stratégies utilisent les objets Deployment
pour apporter des changements qui sont vus par les utilisateurs de toutes les routes qui aboutissent à l'application. D'autres stratégies avancées, telles que celles décrites dans cette section, utilisent les fonctions du routeur en conjonction avec les objets Deployment
pour avoir un impact sur des routes spécifiques.
La stratégie la plus courante en matière d'itinéraires consiste à utiliser un site blue-green deployment. La nouvelle version (la version verte) est mise en place à des fins de test et d'évaluation, tandis que les utilisateurs continuent d'utiliser la version stable (la version bleue). Lorsqu'ils sont prêts, les utilisateurs passent à la version verte. En cas de problème, vous pouvez revenir à la version bleue.
Une stratégie alternative courante consiste à utiliser A/B versions qui sont tous deux actifs en même temps et dont certains utilisateurs utilisent une version et d'autres l'autre. Cette méthode peut être utilisée pour expérimenter des modifications de l'interface utilisateur et d'autres fonctionnalités afin d'obtenir l'avis des utilisateurs. Elle peut également servir à vérifier le bon fonctionnement dans un contexte de production où les problèmes n'affectent qu'un nombre limité d'utilisateurs.
Le déploiement d'un canari permet de tester la nouvelle version, mais lorsqu'un problème est détecté, il revient rapidement à la version précédente. Cela peut se faire avec les deux stratégies ci-dessus.
Les stratégies de déploiement basées sur les itinéraires ne permettent pas de faire évoluer le nombre de pods dans les services. Pour maintenir les caractéristiques de performance souhaitées, il peut être nécessaire de modifier les configurations de déploiement.
8.4.1. Proxy shards et fractionnement du trafic
Dans les environnements de production, vous pouvez contrôler avec précision la distribution du trafic qui arrive sur un shard particulier. Lorsqu'il s'agit d'un grand nombre d'instances, vous pouvez utiliser l'échelle relative des différents serveurs pour mettre en œuvre un trafic basé sur le pourcentage. Cela se combine bien avec proxy shard, qui transfère ou divise le trafic qu'il reçoit vers un service ou une application distinct(e) fonctionnant ailleurs.
Dans la configuration la plus simple, le proxy transmet les demandes sans les modifier. Dans des configurations plus complexes, vous pouvez dupliquer les requêtes entrantes et les envoyer à la fois à un cluster séparé et à une instance locale de l'application, et comparer le résultat. D'autres modèles consistent à garder les caches d'une installation DR au chaud ou à échantillonner le trafic entrant à des fins d'analyse.
N'importe quel proxy TCP (ou UDP) peut être exécuté sous le shard souhaité. Utilisez la commande oc scale
pour modifier le nombre relatif d'instances servant les requêtes sous le proxy shard. Pour une gestion plus complexe du trafic, envisagez de personnaliser le routeur OpenShift Container Platform avec des capacités d'équilibrage proportionnel.
8.4.2. Compatibilité N-1
Les applications dans lesquelles un nouveau code et un ancien code sont exécutés en même temps doivent veiller à ce que les données écrites par le nouveau code puissent être lues et traitées (ou ignorées de manière élégante) par l'ancienne version du code. C'est ce qu'on appelle parfois schema evolution et c'est un problème complexe.
Ces données peuvent prendre plusieurs formes : données stockées sur un disque, dans une base de données, dans un cache temporaire ou faisant partie de la session du navigateur de l'utilisateur. Bien que la plupart des applications web puissent prendre en charge les déploiements continus, il est important de tester et de concevoir votre application en conséquence.
Pour certaines applications, la période pendant laquelle l'ancien et le nouveau code fonctionnent côte à côte est courte, de sorte que les bogues ou quelques transactions d'utilisateurs qui échouent sont acceptables. Pour d'autres, le modèle de défaillance peut aboutir à ce que l'ensemble de l'application devienne non fonctionnelle.
Une façon de valider la compatibilité N-1 est de procéder à un déploiement A/B : exécuter l'ancien et le nouveau code en même temps, de façon contrôlée, dans un environnement de test, et vérifier que le trafic qui circule vers le nouveau déploiement ne provoque pas de défaillances dans l'ancien déploiement.
8.4.3. Fin gracieuse
OpenShift Container Platform et Kubernetes donnent aux instances d'applications le temps de s'arrêter avant de les retirer des rotations d'équilibrage de charge. Cependant, les applications doivent s'assurer qu'elles terminent proprement les connexions des utilisateurs avant de quitter l'instance.
Lors de l'arrêt, OpenShift Container Platform envoie un signal TERM
aux processus du conteneur. Le code de l'application, lorsqu'il reçoit SIGTERM
, cesse d'accepter de nouvelles connexions. Cela permet de s'assurer que les équilibreurs de charge acheminent le trafic vers d'autres instances actives. Le code de l'application attend ensuite que toutes les connexions ouvertes soient fermées, ou met fin de manière gracieuse aux connexions individuelles à la prochaine occasion, avant de quitter.
À l'expiration de la période d'arrêt en douceur, un processus qui n'a pas été arrêté reçoit le signal KILL
, ce qui met immédiatement fin au processus. L'attribut terminationGracePeriodSeconds
d'un pod ou d'un modèle de pod contrôle la période de terminaison gracieuse (30 secondes par défaut) et peut être personnalisé par application si nécessaire.
8.4.4. Déploiements "bleu-vert
Les déploiements bleu-vert impliquent l'exécution simultanée de deux versions d'une application et le transfert du trafic de la version en production (la version bleue) vers la version la plus récente (la version verte). Vous pouvez utiliser une stratégie de roulement ou changer de service dans un itinéraire.
Étant donné que de nombreuses applications dépendent de données persistantes, vous devez disposer d'une application prenant en charge N-1 compatibility, ce qui signifie qu'elle partage des données et met en œuvre la migration en direct entre la base de données, le magasin ou le disque en créant deux copies de la couche de données.
Tenez compte des données utilisées pour tester la nouvelle version. S'il s'agit des données de production, un bogue dans la nouvelle version peut endommager la version de production.
8.4.4.1. Mise en place d'un déploiement bleu-vert
Les déploiements bleu-vert utilisent deux objets Deployment
. Les deux sont en cours d'exécution et celui qui est en production dépend du service spécifié par l'itinéraire, chaque objet Deployment
étant exposé à un service différent.
Les routes sont destinées au trafic web (HTTP et HTTPS), cette technique est donc mieux adaptée aux applications web.
Vous pouvez créer une nouvelle route vers la nouvelle version et la tester. Lorsque vous êtes prêt, modifiez le service dans l'itinéraire de production pour qu'il pointe vers le nouveau service et la nouvelle version (verte) est en ligne.
Si nécessaire, vous pouvez revenir à l'ancienne version (bleue) en rebasculant le service sur la version précédente.
Procédure
Créer deux composants d'application indépendants.
Créez une copie de l'application d'exemple exécutant l'image
v1
sous le serviceexample-blue
:$ oc new-app openshift/deployment-example:v1 --name=example-blue
Créez une deuxième copie qui utilise l'image
v2
sous le serviceexample-green
:$ oc new-app openshift/deployment-example:v2 --name=example-green
Créez un itinéraire qui pointe vers l'ancien service :
$ oc expose svc/example-blue --name=bluegreen-example
-
Accédez à l'application à l'adresse
bluegreen-example-<project>.<router_domain>
pour vérifier que vous voyez l'imagev1
. Modifiez l'itinéraire et changez le nom du service en
example-green
:$ oc patch route/bluegreen-example -p '{"spec":{"to":{"name":"example-green"}}}'
-
Pour vérifier que l'itinéraire a changé, actualisez le navigateur jusqu'à ce que vous voyiez l'image
v2
.
8.4.5. Déploiements A/B
La stratégie de déploiement A/B vous permet d'essayer une nouvelle version de l'application de manière limitée dans l'environnement de production. Vous pouvez spécifier que la version de production reçoit la plupart des demandes des utilisateurs, tandis qu'une fraction limitée des demandes va à la nouvelle version.
Étant donné que vous contrôlez la part des requêtes adressées à chaque version, vous pouvez, au fur et à mesure des tests, augmenter la part des requêtes adressées à la nouvelle version et, en fin de compte, cesser d'utiliser la version précédente. En ajustant la charge des requêtes sur chaque version, il se peut que le nombre de pods dans chaque service doive également être ajusté pour fournir les performances attendues.
Outre la mise à niveau du logiciel, vous pouvez utiliser cette fonction pour expérimenter des versions de l'interface utilisateur. Étant donné que certains utilisateurs reçoivent l'ancienne version et d'autres la nouvelle, vous pouvez évaluer la réaction de l'utilisateur aux différentes versions afin d'éclairer les décisions en matière de conception.
Pour que cela soit efficace, l'ancienne et la nouvelle version doivent être suffisamment similaires pour pouvoir fonctionner en même temps. C'est souvent le cas lors de la publication de corrections de bogues et lorsque les nouvelles fonctionnalités n'interfèrent pas avec les anciennes. Les versions doivent être compatibles N-1 pour fonctionner correctement ensemble.
OpenShift Container Platform prend en charge la compatibilité N-1 via la console web et le CLI.
8.4.5.1. Équilibrage de la charge pour les tests A/B
L'utilisateur établit une route avec plusieurs services. Chaque service gère une version de l'application.
Chaque service se voit attribuer une adresse weight
et la part des demandes adressées à chaque service correspond à l'adresse service_weight
divisée par l'adresse sum_of_weights
. L'adresse weight
de chaque service est distribuée aux points d'extrémité du service de manière à ce que la somme des adresses weights
des points d'extrémité corresponde à l'adresse weight
du service.
La ligne peut comporter jusqu'à quatre services. L'adresse weight
du service peut être comprise entre 0
et 256
. Lorsque weight
est 0
, le service ne participe pas à l'équilibrage de charge mais continue à servir les connexions persistantes existantes. Lorsque le service weight
n'est pas 0
, chaque point d'extrémité a un minimum de weight
de 1
. Pour cette raison, un service avec beaucoup de points d'extrémité peut se retrouver avec un weight
plus élevé que prévu. Dans ce cas, réduisez le nombre de pods pour obtenir l'équilibre de charge attendu weight
.
Procédure
Pour configurer l'environnement A/B :
Créez les deux applications et donnez-leur des noms différents. Chacune crée un objet
Deployment
. Les applications sont des versions du même programme ; l'une est généralement la version de production actuelle et l'autre la nouvelle version proposée.Créer la première application. L'exemple suivant crée une application appelée
ab-example-a
:$ oc new-app openshift/deployment-example --name=ab-example-a
Créez la deuxième application :
$ oc new-app openshift/deployment-example:v2 --name=ab-example-b
Les deux applications sont déployées et les services sont créés.
Rendre l'application accessible à l'extérieur par le biais d'une route. À ce stade, vous pouvez exposer l'une ou l'autre version. Il peut être pratique d'exposer d'abord la version de production actuelle et de modifier ensuite la route pour ajouter la nouvelle version.
$ oc expose svc/ab-example-a
Naviguez jusqu'à l'application à l'adresse
ab-example-a.<project>.<router_domain>
pour vérifier que vous voyez la version attendue.Lorsque vous déployez la route, le routeur équilibre le trafic en fonction des
weights
spécifiés pour les services. À ce stade, il n'y a qu'un seul service avecweight=1
par défaut, de sorte que toutes les requêtes lui sont adressées. L'ajout de l'autre service en tant quealternateBackends
et l'ajustement deweights
donnent vie à la configuration A/B. Cette opération peut être effectuée à l'aide de la commande . Cela peut être fait par la commandeoc set route-backends
ou en modifiant la route.En fixant la valeur de
oc set route-backend
à0
, le service ne participe pas à l'équilibrage de la charge, mais continue à servir les connexions persistantes existantes.NoteLes modifications apportées à l'itinéraire ne font que changer la portion de trafic vers les différents services. Il se peut que vous deviez faire évoluer le déploiement pour ajuster le nombre de pods afin de gérer les charges prévues.
Pour modifier l'itinéraire, exécutez :
oc edit route <route_name> $ oc edit route <route_name>
Exemple de sortie
... metadata: name: route-alternate-service annotations: haproxy.router.openshift.io/balance: roundrobin spec: host: ab-example.my-project.my-domain to: kind: Service name: ab-example-a weight: 10 alternateBackends: - kind: Service name: ab-example-b weight: 15 ...
8.4.5.1.1. Gestion des poids d'une route existante à l'aide de la console web
Procédure
-
Naviguez jusqu'à la page Networking
Routes. - Cliquez sur le menu Actions à côté de l'itinéraire que vous souhaitez modifier et sélectionnez Edit Route.
-
Modifiez le fichier YAML. Mettez à jour la valeur
weight
pour qu'elle soit un nombre entier entre0
et256
qui spécifie le poids relatif de la cible par rapport à d'autres objets de référence de la cible. La valeur0
supprime les demandes adressées à ce back-end. La valeur par défaut est100
. Exécutezoc explain routes.spec.alternateBackends
pour plus d'informations sur les options. - Cliquez sur Save.
8.4.5.1.2. Gestion des poids d'une nouvelle route à l'aide de la console web
-
Naviguez jusqu'à la page Networking
Routes. - Cliquez sur Create Route.
- Saisissez l'itinéraire Name.
- Sélectionnez le site Service.
- Cliquez sur Add Alternate Service.
-
Saisissez une valeur pour Weight et Alternate Service Weight. Entrez un nombre entre
0
et255
qui représente le poids relatif par rapport aux autres cibles. La valeur par défaut est100
. - Sélectionnez le site Target Port.
- Cliquez sur Create.
8.4.5.1.3. Gestion des poids à l'aide du CLI
Procédure
Pour gérer les services et les poids correspondants équilibrés par la route, utilisez la commande
oc set route-backends
:$ oc set route-backends ROUTENAME \ [--zero|--equal] [--adjust] SERVICE=WEIGHT[%] [...] [options]
Par exemple, le texte suivant définit
ab-example-a
comme le service principal avecweight=198
etab-example-b
comme le premier service de remplacement avecweight=2
:$ oc set route-backends ab-example ab-example-a=198 ab-example-b=2
Cela signifie que 99 % du trafic est envoyé au service
ab-example-a
et 1 % au serviceab-example-b
.Cette commande ne met pas le déploiement à l'échelle. Il se peut que vous deviez le faire pour avoir suffisamment de pods pour gérer la charge de la demande.
Exécutez la commande sans drapeaux pour vérifier la configuration actuelle :
$ oc set route-backends ab-example
Exemple de sortie
NAME KIND TO WEIGHT routes/ab-example Service ab-example-a 198 (99%) routes/ab-example Service ab-example-b 2 (1%)
Pour modifier le poids d'un service individuel par rapport à lui-même ou au service principal, utilisez l'option
--adjust
. La spécification d'un pourcentage ajuste le service par rapport au service principal ou au premier service de remplacement (si vous spécifiez le service principal). S'il y a d'autres backends, leur poids reste proportionnel à celui qui a été modifié.L'exemple suivant modifie le poids des services
ab-example-a
etab-example-b
:$ oc set route-backends ab-example --adjust ab-example-a=200 ab-example-b=10
Il est également possible de modifier le poids d'un service en spécifiant un pourcentage :
$ oc set route-backends ab-example --adjust ab-example-b=5%
En spécifiant
$ oc set route-backends ab-example --adjust ab-example-b=+15%
L'indicateur
--equal
fixe l'adresseweight
de tous les services à100
:$ oc set route-backends ab-example --equal
Le drapeau
--zero
fixe l'adresseweight
de tous les services à0
. Toutes les requêtes renvoient alors une erreur 503.NoteTous les routeurs ne peuvent pas prendre en charge des backends multiples ou pondérés.
8.4.5.1.4. Un service, plusieurs objets Deployment
Procédure
Créez une nouvelle application, en ajoutant un label
ab-example=true
qui sera commun à tous les tessons :$ oc new-app openshift/deployment-example --name=ab-example-a --as-deployment-config=true --labels=ab-example=true --env=SUBTITLE\=shardA $ oc delete svc/ab-example-a
L'application est déployée et un service est créé. Il s'agit du premier shard.
Rendre l'application disponible via une route ou utiliser directement l'IP du service :
$ oc expose deployment ab-example-a --name=ab-example --selector=ab-example\=true $ oc expose service ab-example
-
Accédez à l'application à l'adresse
ab-example-<project_name>.<router_domain>
pour vérifier que vous voyez l'imagev1
. Créer un deuxième dépôt basé sur la même image source et le même label que le premier dépôt, mais avec une version étiquetée différente et des variables d'environnement uniques :
$ oc new-app openshift/deployment-example:v2 \ --name=ab-example-b --labels=ab-example=true \ SUBTITLE="shard B" COLOR="red" --as-deployment-config=true $ oc delete svc/ab-example-b
À ce stade, les deux ensembles de pods sont desservis par la route. Cependant, comme les navigateurs (en laissant une connexion ouverte) et le routeur (par défaut, par l'intermédiaire d'un cookie) tentent de préserver votre connexion à un serveur dorsal, il se peut que les deux ensembles ne vous soient pas renvoyés.
Pour forcer votre navigateur vers l'un ou l'autre shard :
Utilisez la commande
oc scale
pour réduire les répliques deab-example-a
à0
.$ oc scale dc/ab-example-a --replicas=0
Rafraîchissez votre navigateur pour afficher
v2
etshard B
(en rouge).Faites passer
ab-example-a
à la réplique de1
etab-example-b
à0
:$ oc scale dc/ab-example-a --replicas=1; oc scale dc/ab-example-b --replicas=0
Rafraîchissez votre navigateur pour afficher
v1
etshard A
(en bleu).
Si vous déclenchez un déploiement sur l'un ou l'autre shard, seuls les pods de ce shard sont affectés. Vous pouvez déclencher un déploiement en modifiant la variable d'environnement
SUBTITLE
dans l'un des objetsDeployment
:$ oc edit dc/ab-example-a
ou
$ oc edit dc/ab-example-b