一 、更新

   滚动更新是一次只更新一小步部分副本,成功后,在更新更多的副本,最终完成所有副本的更新,滚动更新的最大的好处就是零停机,整个更新过程始终有副本在运行,从而保证了业务的连续性

    1.案例:

      ①、基础环境

vim service.yml

apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: httpd
  name: httpd
spec:
  replicas: 3
  selector:
    matchLabels:
      app: httpd
  template:
    metadata:
      labels:
        app: httpd
    spec:
      containers:
      - image: httpd:2.2
        name: httpd
        ports:
         - containerPort: 80
kubectl apply  -f  service.yml

 查看现在状态:

     部署过程如下:

          1.创建deployment httpd

          2.创建 replicaset httpd

          3.创建三个pod

               当前镜像为httpd:2.2,将配置文件中httpd:2.4 再次执行kubectl apply

更新配置文件

apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: httpd
  name: httpd
spec:
  replicas: 3
  selector:
    matchLabels:
      app: httpd
  template:
    metadata:
      labels:
        app: httpd
    spec:
      containers:
      - image: httpd:2.4
        name: httpd
        ports:
         - containerPort: 80

   发现以下变化:

        1.deployment httpd的镜像更新为httpd:2.4

        2.新创建le replicaset httpd 镜像为httpd:2.4 并且管理了三个新的pod。

        3.之前的replicaset httpd里面没有任何pod

过程可以通过kubectl describe deployment httpd查看的。

  

二、回滚

       kubectl apply每次更新应用时kubernetes都会记录下当前的配置,保存为一个revision版次 ,这样就可以回滚到某个特定的revision

      默认配置下,kubernetes只会保留最近的几个revision,可以在deployment配置文件中通过revisionhistoryLimit 属性增加revision数量。

    1.部署:

准备两个版本

1.service.yml

apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: httpd
  name: httpd
spec:
  replicas: 3
  selector:
    matchLabels:
      app: httpd
  template:
    metadata:
      labels:
        app: httpd
    spec:
      containers:
      - image: httpd:2.2
        name: httpd
        ports:
         - containerPort: 80
kubectl apply -f service.yml --record

2.service1.yml

apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: httpd
  name: httpd
spec:
  replicas: 3
  selector:
    matchLabels:
      app: httpd
  template:
    metadata:
      labels:
        app: httpd
    spec:
      containers:
      - image: httpd:2.4
        name: httpd
        ports:
         - containerPort: 80
kubectl apply -f service1.yml --record

  部署结果:

    

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

   2.  查看revison历史记录:

kubectl rollout history deployment httpd

   3.change-cause就是 --record结果。如果回滚到某个版本,比如service ,可以执行命令

kubectl rollout undo  deployment httpd --to-revision=3

   

  

三、默认的健康检查

          每个容器启动时都会执行一个进程,此进程由dockerfile或者entryponint指定。如果进程退出时返回码非零,则认为容器发生故障,kubernetes就会根据restartpolicy重启容器。

         1..模拟容器发生故障:

mkdir restar
vim busy.yml
apiVersion: v1
kind: Pod
metadata:
   labels:
       test: healthcheck
   name: healthcheck
spec:
  restartPolicy: OnFailure
  containers:
    - name: healthcheck
      image: busybox
      args:
        - /bin/sh
        - -c
        - sleep 10;exit 1

pod的restartPolicy设置为OnFailure,默认为Always
sleep 10,exit 1 模拟容器启动10秒后发生故障。
执行kubectl apply创建pod 命名为healthcheck

    查看状态

        

         容器重启了6次。

     容器进程返回值非零,kubernetes则会认为容器发生故障,需要重启。但有不少情况是发生了故障,但进程并不会退出。

四、liveness探测

      liveness 探测让用户可以自定义判断容器是否健康的条件,如果探测失败,kubernetes就会重启容器

   1.案例:

vim busy_liven.yml

apiVersion: v1
kind: Pod
metadata:
   labels:
       test: healthcheck
   name: healthcheck
spec:
  restartPolicy: OnFailure
  containers:
    - name: healthcheck
      image: busybox
      args:
        - /bin/sh
        - -c
        - touch /tmp/healthy;sleep 30;rm -rf /tmp/healthy;sleep 600
      livenessProbe:
        exec:
         command:
          - cat
          - /tmp/healthy
        initialDelaySeconds: 10
        periodSeconds: 5

kubectl apply -f busy_live.yml

启动进程首先先创建文件/tmp/healthy,30秒后删除,如果/tmp/healthy文件存在,则认为容器处于正常状态,反正则发生故障。

  livenessProbe部分定义如何执行Liveness探测:

   

验证结果:

kubectl describe pod healthcheck

watch kubectl get pod(动态查看pod)

五、readiness探测

   除了liveness探测, kubernetes health check 机制还包括readiness探测。

   用户通过liveness探测可以告诉我们kubernetes什么时候通过重启容器实现自愈;readiness探测则是告诉kubernetes什么时候可以将容器加入service负载均衡中,对外提供服务。

   1.案例:


apiVersion: v1
kind: Pod
metadata:
   labels:
       test: healthcheck
   name: healthcheck
spec:
  restartPolicy: OnFailure
  containers:
    - name: healthcheck
      image: busybox
      args:
        - /bin/sh
        - -c
        - touch /tmp/healthy;sleep 30;rm -rf /tmp/healthy;sleep 600
      readinessProbe:
        exec:
         command:
          - cat
          - /tmp/healthy
        initialDelaySeconds: 10
        periodSeconds: 5
kubectl apply -f busy_live.yml

这个配置文件只是将前面例子中的 liveness替换成 readiness

     podreadiness的ready状态经历了如下变化:

     刚被创建时,ready状态为不可用。

    15秒后,第一次进行readiness探测并成功返回,设置ready为可用。

    30秒后 /tmp/healthy被删除,连续3次readiness探测均失败后,ready被设置为不可用。

  liveness探测和readiness探测作比较:

 

六、在scale Up中使用health check

    对于多副本应用,当执行scale up操作时,新副本会作为backend添加到service的负责均衡中,以有副本一起处理客户的请求。 烤炉到应用启动通常都需要一个准备阶段,被逼入加载缓存数据,连接数据库等,从容器启动到正真能够提供服务是需要一段时间的。我们可以通过readiness探测判断容器是否就绪,避免将请求发送到还没有ready的backend

  1.案例:

mkdir scale_health

vim scale.yml

apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: web
  name: web
spec:
  replicas: 3
  selector:
    matchLabels:
      app: web
  template:
    metadata:
      labels:
        app: web
    spec:
      containers:
      - image: httpd
        name: httpd
        ports:
         - containerPort: 80
        readinessProbe:
         httpGet:
           scheme: HTTP
           path: /health
           port: 80
         initialDelaySeconds: 10
         periodSeconds: 5
---
apiVersion: v1
kind: Service
metadata:
     name: httpd-svc
spec:
  type: NodePort
  selector:
     app: web
  ports:
   - protocol: TCP
     nodePort: 30000
     port: 8080
     targetPort: 80

kubectl apply -f  scale.yml

重点关注readinessProbe部分。这里我们使用了不同于exec的另一种探测方法--httpGet。kubernetes对于该方法探测成功的判断天剑是http请求的返回代码在200-400之间。

schema指定协议,支持http和https
path指定访问路径。
port指定端口。

       配置作用:

验证结果:

七、在滚动更新中使用health check

             health check另一个重要的应用场景是rolling update。

    1.案例:

apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: app
  name: app
spec:
  replicas: 10
  selector:
    matchLabels:
      app: app
  template:
    metadata:
      labels:
        app: app
    spec:
      containers:
      - image: busybox
        name: app
        args:
         - /bin/sh
         - -c
         - sleep 10;touch /tmp/healthy;sleep 300000000
        readinessProbe:
         exec:
            command:
             - cat
             - /tmp/healthy
         initialDelaySeconds: 10
         periodSeconds: 5

kubectl apply -f app.yml  --record

    部署结果:

 2.滚动更新应用,配置文件app.v2.yml如下:

apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: app
  name: app
spec:
  replicas: 10
  selector:
    matchLabels:
      app: app
  template:
    metadata:
      labels:
        app: app
    spec:
      containers:
      - image: busybox
        name: app
        args:
         - /bin/sh
         - -c
         - sleep 300000000
        readinessProbe:
         exec:
            command:
             - cat
             - /tmp/healthy
         initialDelaySeconds: 10
         periodSeconds: 5

kubectl apply -f app_v2.yml --record

验证结果:

       

 kubectl get pod输出:

    ①、maxSurge

   此参数控制滚动更新过程中副本总数的超过desired的上限。maxsurge可以是具体的整数(比如3)也可以是百分百,向上取整。maxsurge默认值为25%。

   在上边的例子中 desired 为10 ,那么副本总数的最大值为

        roudup(10+10*25%)=13

    所以我们看到current就是13

②、maxunavailable

  而我们的实际情况是在第四步就卡住了,新副本无法通过readiness探测。

3.如果滚动更新失败 可以通过kubectl rollout undo 回滚到上一个版本。

kubectl rollout history deployment app

kubectl rollout undo deployment app --to-revision=1

如果要定制maxsurge和maxunavailable,可以增加如下配置:

   1.先运行基础环境

kubectl apply -f app.yml  --record

  2.增加定制maxsurge和maxunavailable:


apiVersion: apps/v1
kind: Deployment
metadata:
  labels:
    app: app
  name: app
spec:
  strategy:
    rollingUpdate:
       maxSurge: 35%
       maxUnavailable: 35%
  replicas: 10
  selector:
    matchLabels:
      app: app
  template:
    metadata:
      labels:
        app: app
    spec:
      containers:
      - image: busybox
        name: app
        args:
         - /bin/sh
         - -c
         - sleep 300000000
        readinessProbe:
         exec:
            command:
             - cat
             - /tmp/healthy
         initialDelaySeconds: 10
         periodSeconds: 5

kubectl apply -f app_v2.yml  --record

验证结果:

 

 

Logo

开源、云原生的融合云平台

更多推荐