Déploiement bleu-vert, version Canary, résumé des mises à jour progressives dans K8s

Préface

Cet article vous amènera à comprendre le déploiement bleu et vert, la version Canary, la mise à jour progressive et d'autres méthodes de publication dans kubernetes. Mes articles originaux contiennent beaucoup de contenu, et ils comptent en gros plus de 5 000 mots. Si vous ne le terminez pas , faites d'abord attention à la collecte., Plein de produits secs ~~

Présentation des méthodes de publication multiples de Kubernetes

Introduction du déploiement bleu-vert de Kubernetes, version Canary, mise à jour progressive

Version Canary (également appelée version en niveaux de gris, mise à jour des niveaux de gris):

Les versions Canary sont généralement lancées sur une machine en premier, ou un petit pourcentage, comme 2% des serveurs, principalement pour la vérification du trafic, également connu sous le nom de test Canary, souvent appelé test en niveaux de gris en Chine. Dans le passé, avant de descendre à la mine, un canari était installé pour détecter s'il y a du gaz nocif dans la grotte, pour voir si le canari peut survivre, et le canari a publié son nom. Les tests Canary simples sont généralement vérifiés par des tests manuels, tandis que les tests Canary complexes nécessitent une infrastructure de surveillance relativement complète. En surveillant le retour des indicateurs, observez l'état de santé du Canary comme base pour une version ultérieure ou une restauration. Si le test du fil d'or réussit, toutes les versions V1 restantes sont mises à niveau vers les versions V2. Si le test Canary échoue, le Canary est directement annulé et la version échoue.

Mise à jour continue:

Une optimisation et une amélioration supplémentaires sur la base de la version Canary est une méthode de publication avec un degré d'automatisation plus élevé et une expérience utilisateur relativement fluide. Une version glissante est généralement composée de plusieurs lots de lancement, et la quantité de chaque lot est généralement configurable (peut être définie par le modèle de version). Par exemple, le premier lot de 1 (canari), le deuxième lot de 10%, le troisième lot de 50% et le quatrième lot de 100%. Il y a un intervalle d'observation entre chaque lot, et une vérification manuelle ou des commentaires de surveillance sont utilisés pour s'assurer qu'il n'y a pas de problème avant d'envoyer le lot suivant. Par conséquent, le processus de lancement progressif est généralement plus lent (dans lequel la durée du canari est généralement plus longue que le lot suivant Plus long, par exemple 10 minutes pour les canaris et 2 minutes pour les intervalles suivants).

Déploiement bleu-vert:

Certaines applications n'ont besoin que de déployer une nouvelle version et doivent passer à cette version immédiatement. Par conséquent, nous devons effectuer un déploiement bleu / vert. Dans un déploiement bleu / vert, une nouvelle copie (verte) de l'application sera déployée avec la version existante (bleue). Mettez ensuite à jour l'entrée / le routeur de l'application pour passer à la nouvelle version (verte). Ensuite, vous devez attendre que l'ancienne version (bleue) complète toutes les requêtes qui lui sont envoyées, mais dans la plupart des cas, le trafic de l'application sera modifié à la fois vers la nouvelle version; Kubernetes ne prend pas en charge le bleu / déploiement vert. Le meilleur moyen actuellement est de créer un nouveau déploiement, puis de mettre à jour le service de l'application (tel que le service) pour pointer vers le nouveau déploiement; le déploiement bleu-vert consiste à conserver l'ancienne version, déployer la nouvelle version puis tester, confirmer OK et coupez progressivement le trafic vers la nouvelle version. Le déploiement bleu-vert ne nécessite aucun temps d'arrêt et est moins risqué.

Définition du déploiement

Le déploiement implémente la logique de mise à jour et la stratégie de mise à jour au moyen de ReplicaSet. Quels sont les champs qui peuvent être définis pour un objet ressource tel que Déploiement? Vous pouvez l'afficher à l'aide de la commande suivante:

kubectl explique déployer

L'affichage est le suivant:


GENRE: DeploymentVERSION: extensions / v1beta1DESCRIPTION: DEPRECATED - Cette version de groupe de Deployment est obsolète par apps / v1beta2 / Deployment. Consultez les notes de version pour plus d'informations. Le déploiement permet des mises à jour déclaratives pour les pods et les ReplicaSets. # 我们 使用 apps / v1FIELDS: apiVersion <string> APIVersion définit le schéma versionné de cette représentation d'un objet. Les serveurs doivent convertir les schémas reconnus à la dernière valeur interne et peuvent rejeter les valeurs non reconnues. Plus d'infos: https://git.k8s.io/community/contributors/devel/api-conventions.md#resources kind <string> Kind est une valeur de chaîne représentant la ressource REST que cet objet représente. Les serveurs peuvent déduire cela à partir du point de terminaison auquel le client soumet les demandes. Ne peut pas être mis à jour. Dans CamelCase. Plus d'informations: https: //git.k8s. io / community / contributors / devel / api-conventions.md # types-types metadata <Objet> Métadonnées d'objet standard. spec <Objet> Spécificité du comportement souhaité du déploiement. status <Object> Dernier état observé du déploiement.

kubectl explique deploy.spec   

L'affichage est le suivant:

GENRE: DeploymentVERSION: extensions / v1beta1RESOURCE: spec <Object> DESCRIPTION: Spécification du comportement souhaité du déploiement. DeploymentSpec est la spécification du comportement souhaité de Deployment.FIELDS: minReadySeconds <integer> Nombre minimum de secondes pendant lesquelles un pod nouvellement créé doit être prêt sans qu'aucun de ses conteneurs ne plante, pour qu'il soit considéré comme disponible. La valeur par défaut est 0 (le pod sera considéré comme disponible dès qu'il sera prêt) paused <boolean> Indique que le déploiement est suspendu et ne sera pas traité par le contrôleur de déploiement.立即 更新 progressDeadlineSeconds <integer> Durée maximale en secondes d'un déploiement pour progresser avant d'être considéré comme ayant échoué. Le contrôleur de déploiement continuera à traiter les déploiements qui ont échoué et une condition avec une raison ProgressDeadlineExceeded apparaîtra dans l'état du déploiement. Notez que la progression ne sera pas estimée pendant la période de pause d'un déploiement. Ceci n'est pas défini par défaut. replicas <entier> Nombre de pods souhaités. Il s'agit d'un pointeur pour faire la distinction entre zéro explicite et non spécifié. La valeur par défaut est 1. revisionHistoryLimit <integer> Le nombre d'anciens ReplicaSets à conserver pour permettre la restauration. Il s'agit d'un pointeur pour faire la distinction entre zéro explicite et non spécifié. # 保留 的 历史 版本 数 , 默认 是 10 个 rollbackTo <Object> DEPRECATED. La configuration vers laquelle ce déploiement revient. Sera effacé une fois la restauration terminée. sélecteur <Objet> Sélecteur d'étiquettes pour les pods. Les ReplicaSets existants dont les pods sont sélectionnés seront ceux affectés par ce déploiement. strategy <Object> La stratégie de déploiement à utiliser pour remplacer les pods existants par de nouveaux. # 更新 策略 , 支持 的 滚动 更新 策略 template <Object> -required- Le modèle décrit les pods qui seront créés.

kubectl explique deploy.spec.strategy

L'affichage est le suivant:

GENRE: DeploymentVERSION: extensions / v1beta1RESOURCE: stratégie <Objet> DESCRIPTION: La stratégie de déploiement à utiliser pour remplacer les pods existants par de nouveaux. DeploymentStrategy décrit comment remplacer les pods existants par de nouveaux. uniquement si DeploymentStrategyType = RollingUpdate. type <string> Type de déploiement. Peut être «Recréer» ou «RollingUpdate». La valeur par défaut est RollingUpdate. # Prend en charge deux types de mises à jour, Recreate et RollingUpdate # Recreate est une mise à jour de reconstruction, supprimez une mise à jour et une #RollingUpdate Rolling update, qui définit la méthode de mise à jour de la mise à jour progressive, c'est-à-dire que le nombre de pods peut être supérieur ou inférieur et le degré de mise à jour est contrôlé

kubectl explique deploy.spec.strategy.rollingUpdate

L'affichage est le suivant:

GENRE: DeploymentVERSION: extensions / v1beta1RESOURCE: rollingUpdate <Object> DESCRIPTION: Paramètres de configuration de mise à jour progressive. Présent uniquement si DeploymentStrategyType = RollingUpdate. Spécification pour contrôler le comportement souhaité de la mise à jour progressive.FIELDS: maxSurge <string> Le nombre maximum de pods pouvant être planifiés au-dessus du nombre souhaité de pods. La valeur peut être un nombre absolu (ex: 5) ou un pourcentage de dosettes souhaitées (ex: 10%). Cela ne peut pas être 0 si MaxUnavailable est égal à 0. Le nombre absolu est calculé à partir du pourcentage en arrondissant vers le haut. Par défaut, une valeur de 1 est utilisée. Exemple: lorsqu'il est défini sur 30%, le nouveau RC peut être mis à l'échelle immédiatement au début de la mise à jour progressive, de sorte que le nombre total d'anciens et de nouveaux pods ne dépasse pas 130% des pods souhaités. Une fois que les vieilles cabosses ont été tuées,

Démonstration de la stratégie de mise à jour de l'application de déploiement de déploiement

En supposant qu'il y ait 5 copies, au plus une n'est pas disponible, cela signifie qu'il y en a au moins 4 disponibles, le déploiement est une structure à trois niveaux, le réplicaset de contrôles de déploiement, le pod de contrôle du réplicaset, utilise le déploiement pour créer un pod
cd / root / demo-test

Créez un
fichier deploy-demo.yaml Le contenu du fichier de configuration deploy-demo.yaml est le suivant:

apiVersion: apps / v1kind: Deploymentmetadata: name: myapp-deploy namespace: testspec: replicas: 3 selector: matchLabels: app: myapp release: canary template: metadata: labels: app: myapp release: canary spec: containers: - name: myapp image: myapp: ports v1: - nom: http containerPort: 80

kubectl apply -f deploy-demo.yaml
kubectl get deploy -n test

Vous pouvez voir que le nom du contrôleur créé est myapp-deploy. La
valeur attendue du pod est 2, la valeur actuelle est 2, l'état prêt est 2 et la valeur disponible est 2.

kubectl obtenir rs -n test

L'affichage est le suivant:

上面表示创建deploy的时候也会创建一个rs(replicaset),7657db6c59这个随机数字是我们引用pod的模板template的名字的hash值

kubectl  get  pods    -n test

显示如下:

deploy在实现中心应用时,可以直接编辑配置文件实现,比方说想要修改副本数,把两个变成3个,打开deploy-demo.yaml,直接修改replicas数量,把2变成3,修改之后保存退出,执行如下


kubectl  apply  -f deploy-demo.yaml

apply不同于create,apply可以执行多次;create执行一次,再执行就会报错有重复。

kubectl   get pods

可以看到pod副本数变成了3个

kubectl describe deploy myapp

查看myapp这个控制器的详细信息

Name:                   myapp-deployNamespace:              defaultCreationTimestamp:      Thu, 27 Dec 2018 15:47:48 +0800Labels:                 <none>Annotations:            deployment.kubernetes.io/revision=1                        kubectl.kubernetes.io/last-applied-configuration={"apiVersion":"apps/v1","kind":"Deployment","metadata":{"annotations":{},"name":"myapp-deploy","namespace":"default"},"spec":{"replicas":3,"selector":{...Selector:               app=myapp,release=canaryReplicas:               3 desired | 3 updated | 3 total | 3 available | 0 unavailableStrategyType:           RollingUpdate#默认的更新策略rollingUpdateMinReadySeconds:        0RollingUpdateStrategy:  25% max unavailable, 25% max surge#最多允许多25%个pod,25%表示不足一个,可以补一个Pod Template:  Labels:  app=myapp           release=canary  Containers:   myapp:    Image:        ikubernetes/myapp:v1    Port:         80/TCP    Host Port:    0/TCP    Environment:  <none>    Mounts:       <none>  Volumes:        <none>Conditions:  Type           Status  Reason  ----           ------  ------  Progressing    True    NewReplicaSetAvailable  Available      True    MinimumReplicasAvailableOldReplicaSets:  <none>NewReplicaSet:   myapp-deploy-69b47bc96d (3/3 replicas created)Events:  Type    Reason             Age   From                   Message  ----    ------             ----  ----                   -------  Normal  ScalingReplicaSet  26m   deployment-controller  Scaled up replica set myapp-deploy-69b47bc96d to 2  Normal  ScalingReplicaSet  4m    deployment-controller  Scaled up replica set myapp-deploy-69b47bc96d to 3


案例演示


例1:金丝雀发布

打开一个标签监测更新过程
kubectl  get pods -l app=myapp  -n test -w,(也可以使用kubectl rollout statusdeployment myapp-deploy,显示Waiting for deployment "myapp-deploy"rollout to finish: 1 out of 5 new replicas have been updated),下面命令执行完之后显示如下,之前的pod还在,新创建了一个pod,没有立即删除。

图片

打开另一个标签操作如下:
kubectl  set image deployment  myapp-deploy   myapp:v2  -n test &&  kubectl  rolloutpause deployment  myapp-deploy  -n  test
注:上面的步骤解释说明
把myapp这个容器的镜像更新到myapp:v2版本,更新镜像之后,创建一个新的pod就立即暂停,这就是我们说的金丝雀发布;如果暂停几个
小时之后没有问题,那么取消暂停,就会依次执行后面步骤,把所有pod都升级。
(1)解除暂停

打开一个新的标签
kubectl  get pods -l app=myapp  -n test -w
打开另一个标签
kubectl  rollout  resume  deployment myapp-deploy -n test
在刚才监测的界面可以看到如下一些信息,下面过程是把余下的pod里的容器都更新到新的版本:

myapp-deploy-6bdcd6755d-llrw8   0/1       Pending   0         0smyapp-deploy-6bdcd6755d-llrw8   0/1       ContainerCreating   0         0smyapp-deploy-67f6f6b4dc-7cs8v   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-7cs8v   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-7cs8v   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-7cs8v   0/1       Terminating   0         1hmyapp-deploy-6bdcd6755d-llrw8   1/1       Running   0         16smyapp-deploy-67f6f6b4dc-nhcp2   1/1       Terminating   0         1hmyapp-deploy-6bdcd6755d-r4mrl   0/1       Pending   0         0smyapp-deploy-6bdcd6755d-r4mrl   0/1       Pending   0         1smyapp-deploy-6bdcd6755d-r4mrl   0/1       ContainerCreating   0         1smyapp-deploy-67f6f6b4dc-nhcp2   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-nhcp2   0/1       Terminating   0         1hmyapp-deploy-6bdcd6755d-r4mrl   1/1       Running   0         5smyapp-deploy-67f6f6b4dc-hwx7w   1/1       Terminating   0         1hmyapp-deploy-6bdcd6755d-j8nj8   0/1       Pending   0         0smyapp-deploy-6bdcd6755d-j8nj8   0/1       Pending   0         0smyapp-deploy-6bdcd6755d-j8nj8   0/1       ContainerCreating   0         0smyapp-deploy-67f6f6b4dc-nhcp2   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-nhcp2   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-hwx7w   0/1       Terminating   0         1hmyapp-deploy-6bdcd6755d-j8nj8   1/1       Running   0         4smyapp-deploy-67f6f6b4dc-dbcqh   1/1       Terminating   0         1hmyapp-deploy-6bdcd6755d-lpk5b   0/1       Pending   0         1smyapp-deploy-6bdcd6755d-lpk5b   0/1       Pending   0         1smyapp-deploy-6bdcd6755d-lpk5b   0/1       ContainerCreating   0         1smyapp-deploy-67f6f6b4dc-dbcqh   0/1       Terminating   0         1hmyapp-deploy-6bdcd6755d-lpk5b   1/1       Running   0         4smyapp-deploy-67f6f6b4dc-b4wfc   1/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-b4wfc   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-hwx7w   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-hwx7w   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-b4wfc   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-b4wfc   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-dbcqh   0/1       Terminating   0         1hmyapp-deploy-67f6f6b4dc-dbcqh   0/1       Terminating   0         1h

kubectl get rs  -n test

可以看到replicaset控制器有2个了

(2)回滚

如果发现刚才升级的这个版本有问题可以回滚,查看当前有哪几个版本:

kubectl  rollout  history deployment myapp-deploy -n test

显示如下:

上面可以看到第一版没了,被还原成了第三版,第三版的前一版是第二版

kubectl get rs -n test -o wide     

显示如下:

可以看到上面的rs已经用第一个了,这个就是还原之后的rs


例2:滚动更新

(1) kubectl  get pods  -l app=myapp -n test -w   

在一个窗口监测,打开另外一个窗口按如下操作:
cd   /root/demo_test
cat  deploy-demo.yaml
把myapp:v1改成myapp:v3

保存退出,执行如下

kubectl apply -f deploy-demo.yaml

再在监测的那个窗口可以看到信息如下:

pending表示正在进行调度,ContainerCreating表示正在创建一个pod,running表示运行一个pod,running起来一个pod之后再Terminating(停掉)一个pod,以此类推,直到所有pod完成滚动升级

在另外一个窗口执行kubectl  get rs -n test,显示如下:

上面可以看到rs有两个,上面那个是升级之前的,已经被停掉,但是可以随时回滚,kubectl rollout history deployment myapp-deploy  -n test

查看myapp-deploy这个控制器的滚动历史,显示如下:

回滚的话操作如下:

kubectl rollout  undo

(2) 扩容到5个

cat  deploy-demo.yaml

修改replicas数值是5

kubectl apply -f deploy-demo.yaml

kubectl get pods   -n test显示如下:

图片

上面说明扩容成功了

(3)修改maxSurge和maxUnavailable用来控制滚动更新的更新策略

修改更新策略最多不可用0个,也就是少不能少于5个,最大不能超过6个

kubectl  patch deployment myapp-deploy -p '{"spec":{"strategy":{"rollingUpdate":{"maxSurge":1,"maxUnavailable":0}}}}' -n  test

kubectl describe deployment myapp-deploy  -n test

查看myapp-deploy这个控制器的详细信息

图片

上面可以看到RollingUpdateStrategy:  0 max unavailable, 1 max surge  
这个rollingUpdate更新策略变成了刚才设定的,因为我们设定的pod副本数是5,0和1表示最少不能少于5个pod,最多不能超过6个pod
这个就是通过控制RollingUpdateStrategy这个字段来设置滚动更新策略的


例3:蓝绿部署

lan.yaml配置文件内容如下:


apiVersion: apps/v1

kind: Deployment

metadata:

  name: myapp-v1

  namespace: blue-green

spec:

  replicas: 3

  selector:

    matchLabels:

      app: myapp

      version: v1

  template:

    metadata:

     labels:

      app: myapp

      version: v1

    spec:

       containers:

       - name: myapp

         image: janakiramm/myapp:v1

         imagePullPolicy: IfNotPresent

         ports:

         - containerPort: 80


lv.yaml配置文件内容如下:

apiVersion: apps/v1

kind: Deployment

metadata:

  name: myapp-v2

  namespace: blue-green

spec:

  replicas: 3

  selector:

    matchLabels:

      app: myapp

      version: v2

  template:

    metadata:

     labels:

       app: myapp

       version: v2

    spec:

      containers:

      - name: myapp

        image: janakiramm/myapp:v2

        imagePullPolicy: IfNotPresent

        ports:

        - containerPort: 80


service_lanlv.yaml 配置文件内容如下:

apiVersion: v1

kind: Service

metadata:

  name: myapp-lan

  namespace: blue-green

  labels:

     app: myapp

     version: v1

spec:

   type: NodePort

   ports:

   - port: 80

     nodePort: 30062

     name: http

   selector:

     app: myapp

     version: v1


cd  /root/demo_test/lanlv

kubectl apply -f lan.yaml

kubectl apply  -f lv.yaml

kubectl get pods -n blue-green  

显示如下:

图片


上面可以看到有两个pod,一个是myapp-v1这个是蓝程序(升级之前的程序),一个是myapp-v2这个是绿程序(升级之后的程序),蓝绿程序一起运行kubectl apply -f service_lanlv.yaml

kubectl get svc -n blue-green

在浏览器访问http://<k8s集群任何一个节点ip>:port    显示如下:

图片

修改service_lanlv.yaml 配置文件,修改标签,让其匹配到绿程序(升级之后的程序)

 service_lv.yaml 文件内容如下:

apiVersion: v1

kind: Service

metadata:

  name: myapp-lan

  namespace: blue-green

  labels:

     app: myapp

     version: v2

spec:

   type: NodePort

   ports:

   - port: 80

     nodePort: 30062

     name: http

   selector:

     app: myapp

     version: v2

kubectl apply -f service_lv.yaml

kubectl get svc -n blue-green   显示如下:

图片

在浏览器访问http://<k8s集群任何一个节点ip>:port   

显示如下:

图片


Je suppose que tu aimes

Origine blog.51cto.com/15127502/2655093
conseillé
Classement