首页 > 其他分享 >k8s的滚动更新

k8s的滚动更新

时间:2023-02-25 12:45:07浏览次数:37  
标签:kubectl 滚动 httpd httpservice 更新 deployment pod k8s 2.4

一、什么是滚动更新

当某个服务需要升级时,传统的做法是,先将要更新的服务下线,业务停止后再更新版本和配置,然后重新启动服务。

如果业务集群规模较大时,这个工作就变成了一个挑战,而且全部停止了服务,再逐步升级的方式会导致服务较长时间不可用。

针对这个问题,k8s提供了滚动更新(rolling-update)的方式来解决上述问题。

滚动更新是针对pod来操作的,它通过一次只更新一小部分副本,成功后,再更新更多的副本,最终完成所有副本的更新。

滚动更新的最大的好处是零停机,整个更新过程始终有副本在运行,从而保证了服务的连续性。

二、实例分析滚动更新实现逻辑

部署一个http应用,三个副本,初始镜像为 httpd:2.4.33,然后将其更新到 httpd:2.4.38。

编写一个Deployment文件http-service.yml

vim http-service.yml

---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: httpservice-deployment
spec:
  replicas: 5
  selector:
    matchLabels:
      run: httpservice
  strategy:
    rollingUpdate:
      #指定更新时最大扩展的pod数
      maxSurge: 2
      #指定可接受的不可用pod数
      maxUnavailable: 1
  template:
    metadata:
      labels:
        run: httpservice
    spec:
      containers:
        - name: http-service
          image: httpd:2.4.33
          ports:
            - containerPort: 80

应用deployment

$ kubectl apply -f http-service.yml 
deployment.apps/httpservice-deployment created

查看replicaset和deployment的状态

$ kubectl get replicaset -o wide 
NAME                                DESIRED   CURRENT   READY   AGE     CONTAINERS     IMAGES         SELECTOR
httpservice-deployment-66d9fd5f76   5         5         5       6m39s   http-service   httpd:2.4.33   pod-template-hash=66d9fd5f76,run=httpservice
$ kubectl get deployments -o wide 
NAME                     READY   UP-TO-DATE   AVAILABLE   AGE     CONTAINERS     IMAGES         SELECTOR
httpservice-deployment   5/5     5            5           6m48s   http-service   httpd:2.4.33   run=httpservice

可以看到本版是2.4.33

查看pod状态

$ kubectl get pod -o wide 
NAME                                      READY   STATUS    RESTARTS   AGE     IP            NODE         NOMINATED NODE   READINESS GATES
httpservice-deployment-66d9fd5f76-85xdg   1/1     Running   0          6m50s   10.244.2.22   centos7907   <none>           <none>
httpservice-deployment-66d9fd5f76-9rbsb   1/1     Running   0          6m50s   10.244.3.16   centos7906   <none>           <none>
httpservice-deployment-66d9fd5f76-f5fj4   1/1     Running   0          6m50s   10.244.3.17   centos7906   <none>           <none>
httpservice-deployment-66d9fd5f76-trx7k   1/1     Running   0          6m50s   10.244.3.18   centos7906   <none>           <none>
httpservice-deployment-66d9fd5f76-zntf9   1/1     Running   0          6m50s   10.244.2.21   centos7907   <none>           <none>

将http-service.yml文件中,镜像的版本改为httpd:2.4.38,再次执行更新操作
vim http-service.yml

---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: httpservice-deployment
spec:
  replicas: 5
  selector:
    matchLabels:
      run: httpservice
  template:
    metadata:
      labels:
        run: httpservice
    spec:
      containers:
        - name: http-service
          image: httpd:2.4.38
          ports:
            - containerPort: 80

更新deployment

$ kubectl apply -f http-service.yml 
deployment.apps/httpservice-deployment configured

再查看状态

从中可以发现:新创建的ReplicaSet镜像为httpd:2.4.38,并且管理了三个新的 Pod。

而老的ReplicaSet里面已经没有任何Pod。结论是老的ReplicaSet的三个httpd:2.4.33 Pod 已经被新的ReplicaSet的三个httpd:2.4.38 Pod逐渐替换了。


更新完成


具体替换过程

kubectl describe deployments httpservice-deployment

对照具体版本

Scaled up replica set httpservice-deployment-66d9fd5f76 to 5 将76结尾的RS的pod增加到5个
Scaled up replica set httpservice-deployment-7ccf67cf77 to 2 将77结尾的RS的pod增加到2个
Scaled down replica set httpservice-deployment-66d9fd5f76 to 4 将76结尾的RS的pod减少到4个
Scaled up replica set httpservice-deployment-7ccf67cf77 to 3 将77结尾的RS的pod增加到3个
Scaled down replica set httpservice-deployment-66d9fd5f76 to 3 将76结尾的RS的pod减少到3个
Scaled up replica set httpservice-deployment-7ccf67cf77 to 4 将77结尾的RS的pod增加到4个
Scaled down replica set httpservice-deployment-66d9fd5f76 to 2 将76结尾的RS的pod减少到2个
Scaled up replica set httpservice-deployment-7ccf67cf77 to 5 将77结尾的RS的pod增加到5个
Scaled down replica set httpservice-deployment-66d9fd5f76 to 1 将76结尾的RS的pod减少到1个
Scaled down replica set httpservice-deployment-66d9fd5f76 to 0 将76结尾的RS的pod减少到0个

三、k8s中版本回滚方法

在执行kubectl apply命令更新应用时,K8s都会记录下当前的配置,保存为一个revision(版本),通过这个版本记录,就可以回滚到某个特定的revision。

默认配置下,K8s只会保留最近的几个版本,不过可以在Deployment配置文件中通过revisionHistoryLimit属性增加revision的数量

下面具体来演示一下K8s中版本回滚的方法。编写四个Deployment文件httpd-2.4.33.yml、httpd-2.4.39.yml、httpd-2.4.41.yml、httpd-2.4.43.yml,分别对应的httpd镜像为2.4.33、2.4.39、2.4.41和2.4.43

httpd-2.4.33.yml

---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: httpservice-deployment
spec:
  #设置可保存的记录版本数
  revisionHistoryLimit: 10
  replicas: 3
  selector:
    matchLabels:
      run: httpservice
  template:
    metadata:
      labels:
        run: httpservice
    spec:
      containers:
        - name: http-service
          image: httpd:2.4.33
          ports:
            - containerPort: 80

这是第一个文件http-2.4.33.yml,其它三个文件中,对应的httpd镜像分别为2.4.39、2.4.41和2.4.43,其它配置均一样。

先执行发布http-2.4.33.yml

$ kubectl apply -f httpd2.4.33.yml 
deployment.apps/httpservice-deployment created
$ kubectl get deployments -o wide 
NAME                     READY   UP-TO-DATE   AVAILABLE   AGE   CONTAINERS     IMAGES         SELECTOR
httpservice-deployment   3/3     3            3           14s   http-service   httpd:2.4.33   run=httpservice

然后再更新其他三个版本

$ kubectl apply -f httpd2.4.39.yml --record 
deployment.apps/httpservice-deployment configured
$ kubectl apply -f httpd2.4.41.yml --record
deployment.apps/httpservice-deployment configured
$ kubectl apply -f httpd2.4.43.yml --record
deployment.apps/httpservice-deployment configured

其中,--record的作用是将当前命令记录到revision记录中,这样就可以知道每个revison对应的是哪个配置文件了。

每个版本之前间隔一段时间

更新好查看历史版本

$ kubectl rollout history deployment httpservice-deployment 
deployment.apps/httpservice-deployment 
REVISION  CHANGE-CAUSE
1         <none>
2         kubectl apply --filename=httpd2.4.39.yml --record=true
3         kubectl apply --filename=httpd2.4.41.yml --record=true
4         kubectl apply --filename=httpd2.4.43.yml --record=true

查看replicaset

$ kubectl get rs -o wide 
NAME                                DESIRED   CURRENT   READY   AGE     CONTAINERS     IMAGES         SELECTOR
httpservice-deployment-66d9fd5f76   0         0         0       27m     http-service   httpd:2.4.33   pod-template-hash=66d9fd5f76,run=httpservice
httpservice-deployment-6777b8d7cf   3         3         3       4m49s   http-service   httpd:2.4.43   pod-template-hash=6777b8d7cf,run=httpservice
httpservice-deployment-6d578ff989   0         0         0       10m     http-service   httpd:2.4.41   pod-template-hash=6d578ff989,run=httpservice
httpservice-deployment-7b8f89958b   0         0         0       25m     http-service   httpd:2.4.39   pod-template-hash=7b8f89958b,run=httpservice

查看测试的deployment

$ kubectl get deploy -o wide 
NAME                     READY   UP-TO-DATE   AVAILABLE   AGE   CONTAINERS     IMAGES         SELECTOR
httpservice-deployment   3/3     3            3           46m   http-service   httpd:2.4.43   run=httpservice

要回滚到某个版本,只需要指定revision就可以了

例如,我们需要回滚到第三个版本,也就是httpd2.4.41

$ kubectl rollout undo deployment httpservice-deployment --to-revision=3
deployment.apps/httpservice-deployment rolled back

查看replicaset

$ kubectl get rs -o wide 
NAME                                DESIRED   CURRENT   READY   AGE   CONTAINERS     IMAGES         SELECTOR
httpservice-deployment-66d9fd5f76   0         0         0       80m   http-service   httpd:2.4.33   pod-template-hash=66d9fd5f76,run=httpservice
httpservice-deployment-6777b8d7cf   0         0         0       57m   http-service   httpd:2.4.43   pod-template-hash=6777b8d7cf,run=httpservice
httpservice-deployment-6d578ff989   3         3         3       63m   http-service   httpd:2.4.41   pod-template-hash=6d578ff989,run=httpservice
httpservice-deployment-7b8f89958b   0         0         0       78m   http-service   httpd:2.4.39   pod-template-hash=7b8f89958b,run=httpservice

可以看到,当前的三个副本都是2.4.41版本

查看历史版本

$ kubectl rollout history deployment httpservice-deployment 
deployment.apps/httpservice-deployment 
REVISION  CHANGE-CAUSE
1         <none>
2         kubectl apply --filename=httpd2.4.39.yml --record=true
4         kubectl apply --filename=httpd2.4.43.yml --record=true
5         kubectl apply --filename=httpd2.4.41.yml --record=true

可以看到原本的3版本已经变成了5版本

第一个版本和其他相比,少了执行的命令

因此,有回滚需求的话,一定要在执行kubectl apply时加上 --record参数。

四、自定义滚动更新策略

maxSurgemaxUnavailable用来控制滚动更新的更新策略

取值范围

数值

1、maxUnavailable: [0, 副本数]

2、maxSurge: [0, 副本数]

注意:两者不能同时为0。

比例

1、maxUnavailable: [0%, 100%] 向下取整,比如10个副本,5%的话==0.5个,但计算按照0个;

2、maxSurge: [0%, 100%] 向上取整,比如10个副本,5%的话==0.5个,但计算按照1个;

注意:两者不能同时为0。

建议配置

1、maxUnavailable == 0

2、maxSurge == 1

这是我们生产环境提供给用户的默认配置。即“一上一下,先上后下”最平滑原则:
1个新版本pod ready(结合readiness)后,才销毁旧版本pod。此配置适用场景是平滑更新、保证服务平稳,但也有缺点,就是太慢了。

总结

  • maxUnavailable:和期望的副本数比,不可用副本数最大比例(或最大值),这个值越小,越能保证服务稳定,更新越平滑;
  • maxSurge:和期望的副本数比,超过期望副本数最大比例(或最大值),这个值调的越大,副本更新速度越快。

自定义策略

修改更新策略:maxUnavailable=1,maxSurge=1

1、直接命令修改

$ kubectl patch deployment myapp-v1 -p '{"spec":{"strategy":{"rollingUpdate": {"maxSurge":1,"maxUnavailable":1}}}}' 

2、通过修改yaml文件修改

....
spec:
  replicas: 3
  revisionHistoryLimit: 5
  selector:
    matchLabels:
      app: http
  strategy:
    rollingUpdate:
      #指定更新时最大扩展的pod数
      maxSurge: 2
      #指定可接受的不可用pod数
      maxUnavailable: 1
  template:
  ......

最后应用

$ kubectl apply -f test.yaml

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

$ kubectl describe deployment myapp-v1 

显示如下:

RollingUpdateStrategy: 1 max unavailable, 1 max surge

上面可以看到RollingUpdateStrategy: 1 max unavailable, 1 max surge

这个rollingUpdate更新策略变成了刚才设定的,因为我们设定的pod副本数是3,1和1表示最少不能少于2个pod,最多不能超过4个pod

这个就是通过控制RollingUpdateStrategy这个字段来设置滚动更新策略的

标签:kubectl,滚动,httpd,httpservice,更新,deployment,pod,k8s,2.4
From: https://www.cnblogs.com/guangdelw/p/17154142.html

相关文章

  • js实战-更新单价、小计、总计
    资料来源于:B站尚硅谷JavaWeb教程(全新技术栈,全程实战),本人才疏学浅,记录笔记以供日后回顾视频链接个人总结知识点1.相较于上一节,新增当鼠标悬浮在单价上后,点击单价......
  • k8s-部署Nginx+Keepalived高可用负载均衡器
    本文章是 k8s二进制高可用集群部署 的分支。详细步骤请参考目录。Kubernetes集群高可用性包含以下两个层面的考虑:Etcd数据库的高可用性KubernetesMaster组件......
  • ​04.Win10_22H2_2023年2月官方累积更新镜像下载
    大版本号:22H2​内部版本号:19045.2604​版本说明​大版本号:每年发布一次,如2021年21H2、2022年22H2​小版本号:每年提供若干次ISO镜像,大版本号不变,变化的是小版本号(内部版本号......
  • ​04.Win11_22H2_2023年2月官方累积更新镜像下载
    大版本号:22H2​内部版本号:22621.1265​版本说明​大版本号:每年发布一次,如2021年21H2、2022年22H2​小版本号:每年提供若干次ISO镜像,大版本号不变,变化的是小版本号(内部版本号......
  • 如何实现 Web 页面更新版本时候不会影响到使用旧版本的用户 All In One
    如何实现Web页面更新版本时候不会影响到使用旧版本的用户AllInOne用户无感知更新API非覆盖式发布自动刷新(......
  • K8S中Pod概念
    一、资源限制Pod是kubernetes中最小的资源管理组件,Pod也是最小化运行容器化应用的资源对象。一个Pod代表着集群中运行的一个进程。kubernetes中其他大多数组件都是......
  • k8s-新增服务端节点
    本文章是 k8s二进制高可用集群部署 的分支。详细步骤请参考目录。1.etcd扩容**如果etcd通过CA生成的证书不包含当前节点的ip,可能etcd集群需要重新生成证书。1......
  • K8SYaml文件详解
    一、K8S支持的文件格式kubernetes支持YAML和JSON文件格式管理资源对象。JSON格式:主要用于api接口之间消息的传递YAML格式:用于配置和管理,YAML是一种简洁的非标记性语言,内......
  • k8s-部署CoreDNS
    本文章是 k8s二进制高可用集群部署 的分支。详细步骤请参考目录。CoreDNS用于集群内部Service名称解析部署CoreDNS需要使用到官方提供的两个文件 deploy.sh 和......
  • k8s orders
    一、资源管理介绍二、陈述式对象管理三、k8s的ip和端口介绍四、项目生命周期一、资源管理介绍1、资源管理概念在kubernetes中,所有的内容都抽象为资源,用户需要通过操......