[Kubernetes] Deployment Management of Pod

Get into the habit of writing together! This is the 10th day of my participation in the "Nuggets Daily New Plan · April Update Challenge", click to view the details of the event .

I. Introduction

Deploy, upgrade, and rollback Deploymentusing .Pod

DeploymentProvides a declarative definition method for and , which can be used in place of the previously used to Podmanage applications.ReplicaSetReplicationController(RC)

DeploymentResource Podobjects provide declarative definitions for and ReplicaSet( upgrades of), describing the desired target state in the file.ReplicationControllerDeployment YAML

Deployment Controllerwill create a sum that matches the target state, ReplicaSetand Podif updated Deployment, the corresponding ReplicaSetand Podwill also change the state to match the new target state.

(1) Typical application scenarios

  1. define Deploymentto create ReplicaSetandPod

Use Deploymentto create ReplicaSet, which ReplicaSetwill be created in the background Pod. You can check Podthe startup status of , to see if it succeeded or failed. You can Deploymentalso judge whether the online is hanglive or not according to the status of .

  1. Rolling upgrades and rollbacks of applications

通过更新 DeploymentPodTemplateSpec 字段来声明 Pod 的新状态,更新 Deployment 后会创建一个新的 ReplicaSetDeployment 会按照控制的速率删除由旧的 ReplicaSet 创建的 Pod、并使用新的 ReplicaSet 创建新的 Pod,当新生成的 Pod 达到要求的目标状态后,会清除旧的 ReplicaSet

如果当前状态不稳定,可以回滚到之前的 Deployment revision,每次回滚都会更新 Deploymentrevision

  1. 扩容和缩容

根据系统负载进行 Deployment 的扩容和缩容。

  1. 暂停和继续 Deployment

暂停 Deployment 并修改 PodTemplateSpec 字段,然后重新恢复上线。

(2)举个例子

  1. 定应Deployment文件 nginx-deployment.yaml

它可以创建一个 Replica Set 来启动 3个 nginx pod

apiVersion: apps/v1
kind: Deployment
metadata:
  name: nginx-deployment
spec:
  selector:
    matchLabels:
      app: nginx
  replicas: 3
  template:
    metadata:
      labels:
        app: nginx
    spec:
      containers:
        - name: nginx
          image: nginx:1.7.9
          ports:
            - containerPort: 80
复制代码
  1. 执行创建
$ kubectl create -f nginx-deployment.yaml
deployment.apps/nginx-deployment created
复制代码
  1. 查看Deployment的状态、RS的状态,以及运行的 Pod 副本数量
# 可以看到已经创建了 3 个符合要求的 Pod,这 3 个 Pod 都是最新的、都处于可用状态
$ kubectl get deployments
NAME               READY   UP-TO-DATE   AVAILABLE   AGE
nginx-deployment   3/3     3            3           39s

# 该 RS 需要 3 个 Pod,当前符合要求的有 3 个 Pod 并且已经创建好,RS 名字的组成:<Deployment 的名字>-<Pod template 的 hash 值>
$ kubectl get rs
NAME                          DESIRED   CURRENT   READY   AGE
nginx-deployment-5754944d6c   3         3         3       6m18s

# 使用 nginx-deployment-5754944d6c RS 创建的 3 个 Pod
$ kubectl get pods
NAME                                READY   STATUS    RESTARTS   AGE
nginx-deployment-5754944d6c-gv8x8   1/1     Running   0          6m36s
nginx-deployment-5754944d6c-hsp99   1/1     Running   0          6m36s
nginx-deployment-5754944d6c-qqh42   1/1     Running   0          6m36s
复制代码
  1. 查看nginx-deployment的详细信息
$ kubectl describe deployment nginx-deployment
# 在 Annotations 记录了版本 revision: 1
# 默认更新策略使用的是 RollingUpdate
# max unavailable 和 max surge 的默认值都为 25%
# ReplicaSet 为 nginx-deployment-5754944d6c
复制代码



二、Deployment 升级

Kubernetes 提供滚动升级,就不用暂停与该服务相关的所有pod

通常使用 Deployment 来创建 Pod 资源对象,当Pod 在运行中,可以修改 DeploymentPod 定义或是镜像名称,并应用到 Deployment 对象上,这样就完成了 Deployment 的自动更新操作。

(1)举个栗子

  1. pod的镜像更新为 nginx:1.9.1
$ kubectl set image deployment/nginx-deployment nginx=nginx:1.9.1
deployment.extensions/nginx-deployment image updated

# 也可以使用 kubectl edit 命令进行更新,把 image 字段下的 nginx:1.7.9 更改为 nginx:1.9.1
$ kubectl edit deployment/nginx-deployment
deployment.extensions/nginx-deployment edited
复制代码
  1. 修改了镜像名,就会触发系统完成Deployment所有运行pod的滚动升级操作,查看rollout状态

Tips: 当且仅当 Deployment.spec.template 字段下的 labels 或是 image 更新时才会触发 rollout,其它的更新并不会触发 rollout

$ kubectl rollout status deployment/nginx-deployment
deployment "nginx-deployment" successfully rolled out
复制代码
  1. 查看更新后的 DeploymentRSPod
# 可以看到 UP-TO-DATE 的数量已经变成了 3,说明已经全部更新完成
$ kubectl get deployment
NAME               READY   UP-TO-DATE   AVAILABLE   AGE
nginx-deployment   3/3     3            3           143m

# 查看两个 RS 的最终状态,可以看到旧的 RS 已经没有 Pod 在运行了,新的 RS 创建好了 3 个新的 Pod
$ kubectl get rs
NAME                          DESIRED   CURRENT   READY   AGE
nginx-deployment-5754944d6c   0         0         0       143m
nginx-deployment-7448597cd5   3         3         3       6m11s

# 由新 nginx-deployment-7448597cd5 RS 创建出来的 3 个 Pod
$ kubectl get pods
NAME                                READY   STATUS    RESTARTS   AGE
nginx-deployment-7448597cd5-7c9ms   1/1     Running   0          6m19s
nginx-deployment-7448597cd5-h6k89   1/1     Running   0          5m58s
nginx-deployment-7448597cd5-m8dnk   1/1     Running   0          5m25s
复制代码
  1. 查看nginx-deployment详细信息
$ kubectl describe deployments/nginx-deployment
# ReplicaSet 更新为 nginx-deployment-7448597cd5
复制代码

(2)分析更新过程

Event事件,可以看到Pod的更新过程:

  1. 系统创建了一个新的 RS(nginx-deployment-7448597cd5),将其副本数量扩展到 1;将旧的 RS(nginx-deployment-5754944d6c)副本数量缩减为 2
  2. 新的 RS 副本数量扩展到了 2,旧的 RS 副本数量缩减为 1
  3. 新的 RS 副本数量扩展到了 3,旧的 RS 副本数量缩减为 0

(3)更新策略

Deployment 通过字段 spec.strategy 设置 Pod 更新策略。

上面创建的 Deployment 的相关默认设置如下:

spec:
  strategy:
    rollingUpdate:
      maxSurge: 25%
      maxUnavailable: 25%
    type: RollingUpdate
复制代码

Deployment 的更新策略有两种:

  • Recreat(重建): 先 kill 掉所有正在运行的 Pod,然后创建新的 Pod
  • RollingUpdate(滚动更新): 逐个更新 Pod。可以在字段 spec.strategy.rollingUpdate 下设置两个参数 maxSurgemaxUnavailable 来控制滚动更新的过程。

关于两个参数的详细说明:

  • maxUnavailable

指定更新过程中不可用状态的 Pod 数量上限。默认值 25% 指的是:Pod 期望副本数的 25%,然后系统会以向下取整的方式计算出绝对值(整数)。对于这里而言,当开始滚动更新时,旧的 RS 立即将副本数缩小到所需副本总数的 75%(3 * 75% = 2.25,然后向下取整,绝对值为 2),一旦新的 Pod 创建并准备好,旧的 RS 会进一步缩容,新的 RS 会进一步扩容,整个过程中系统在任意时刻都可以确保可用状态的 Pod 总数至少占 Pod 期望副本总数的 75%。

  • maxSurge:指定更新过程中 Pod 总数超过 Pod 期望副本数部分的最大值。默认值 25% 指的是:Pod 期望副本数的 25%,然后系统会以向上取整的方式计算出绝对值(整数)。对于这里而言,新的 RS 可以在滚动更新开始时立即进行副本数扩容,只要保证新旧 RSPod 副本总数之和不超过期望副本数的 125% 即可。一旦旧的 Pod 被 kill 掉,新的 RS 会进一步扩容。在整个过程中系统在任意时刻都能确保新旧 RSPod 副本总数之和不超过所需副本数的 125%。

(4)多重更新(Rollover)

“多重更新”也就是多个滚动更新(Rollout)同时进行。

每当 Deployment Controller 检测到有新的 Deployment 创建时,如果没有已存在的 ReplicaSet 来创建期望个数的PodDeployment Controller 就会创建一个新的 ReplicaSet 来执行改变,已存在的 ReplicaSet 控制 ``label匹配字段spec.selector但是template不匹配字段spec.templatePod进行缩容,然后新的ReplicaSet将会扩容出匹配字段spec.replicas指定数目的Pod,旧的 ReplicaSet` 将会缩容到 0。

举个例子:比如创建了一个有 5 个 nginx:1.7.9 replicaDeployment,当刚刚创建到 3 个 nginx:1.7.9 replica 时,开始更新 Deployment 将其镜像修改为 nginx:1.9.1。在这种情况下,Deployment 会立即 kill 掉已创建的 3 个 nginx:1.7.9Pod,并开始创建 nginx:1.9.1Pod,它不会等到所有 5 个 nginx:1.7.9Pod 都创建完成后才开始执行滚动更新。

更新 Deployment 的标签选择器(Label Selector

通常情况下不建议更新 Deployment 的标签选择器,因为这样会导致 Deployment 选择的 Pod 列表发生变化,可能与其他控制器发生冲突。

步骤如下:

  1. 添加标签选择器

在添加标签选择器时,注意要同步修改 Deployment 配置的 Pod 标签,为 Pod 添加新的标签。

The difference here is that adding a tag selector is not backward compatible, the new tag selector will not match and use the ReplicaSetsand Pod, so adding a new selector will cause all of the old ReplicaSetsand created by the old ReplicaSetsto Podbe in Orphaned state, ie: not automatically deleted by the system and not under new ReplicaSetcontrol .

To add labels to both fields spec.selector.matchLabelsand fields , modify them with the following command:spec.template.matedata.labelsk8s: nginx-pod

$ kubectl edit deployment/nginx-deployment
deployment.extensions/nginx-deployment edited
复制代码

View the updated Deployment, RS, Pods:

# 可以看到更新完成
$ kubectl get deployment/nginx-deployment
NAME               READY   UP-TO-DATE   AVAILABLE   AGE
nginx-deployment   3/3     3            3           3h58m

# 创建了新的 RS:
$ kubectl get rs nginx-deployment-8ff4cd577
NAME                          DESIRED   CURRENT   READY   AGE
nginx-deployment-5754944d6c   0         0         0       3h58m
nginx-deployment-7448597cd5   3         3         3       101m
nginx-deployment-8ff4cd577    3         3         3       88s

# 使用新的 RS nginx-deployment-8ff4cd577 创建了 3 个 Pod,可以发现之前的 3 个 Pod 依然存在着,没有被删除
$ kubectl get pods
NAME                                READY   STATUS    RESTARTS   AGE
nginx-deployment-7448597cd5-7c9ms   1/1     Running   0          101m
nginx-deployment-7448597cd5-h6k89   1/1     Running   0          100m
nginx-deployment-7448597cd5-m8dnk   1/1     Running   0          100m
nginx-deployment-8ff4cd577-8gxw2    1/1     Running   0          95s
nginx-deployment-8ff4cd577-8plkw    1/1     Running   0          95s
nginx-deployment-8ff4cd577-g7bc2    1/1     Running   0          95s
复制代码
  1. Update tag selector

For example, updating the key or value of a tag in a selector has a similar effect as adding a new selector tag.

  1. remove tag selector

Deleting one or more tags from Deploymentthe tag selector of , the andDeployment of the will not be affected, except that the deleted tags will still exist on the existing and .ReplicaSetPodReplicaSetPod

Guess you like

Origin juejin.im/post/7084670154344235038