zoukankan      html  css  js  c++  java
  • k8s集群安装学习笔记三——资源控制器

    简介:

    资源控制器
    ReplicationController 和 ReplicaSet(RS)
    Deployment
    Deployment回退
    DaemonSet
    Job & CronJob
    StatefulSet

    资源控制器

    什么是控制器?
    Kubernetes 中内建了很多 controller(控制器),这些相当于一个状态机,用来控制 Pod 的具体状态和行为。
     
    控制器类型
    ReplicationController(基本淘汰了) 和 ReplicaSet
    Deployment
    DaemonSet
    StateFulSet
    Job/CronJob
    Horizontal Pod Autoscaling
     
    ReplicationController 和 ReplicaSet
    ReplicationController(RC)用来确保容器应用的副本数始终保持在用户定义的副本数,即如果有容器异常退
    出,会自动创建新的 Pod 来替代;而如果异常多出来的容器也会自动回收;
    在新版本的 Kubernetes 中建议使用 ReplicaSet 来取代 ReplicationController 。ReplicaSet 跟
    ReplicationController 没有本质的不同,只是名字不一样,并且 ReplicaSet 支持集合式的 selector;
     
     
    Deployment
    Deployment 为 Pod 和 ReplicaSet 提供了一个声明式定义 (declarative) 方法,用来替代以前的
    ReplicationController 来方便的管理应用。典型的应用场景包括;
    1.定义 Deployment 来创建 Pod 和 ReplicaSet
    2.滚动升级和回滚应用
    3.扩容和缩容
    4.暂停和继续 Deployment
     
    DaemonSet
    DaemonSet 确保全部(或者一些)Node 上运行一个 Pod 的副本。当有 Node 加入集群时,也会为他们新增一个
    Pod 。当有 Node 从集群移除时,这些 Pod 也会被回收。删除 DaemonSet 将会删除它创建的所有 Pod
    使用 DaemonSet 的一些典型用法:
    1.运行集群存储 daemon,例如在每个 Node 上运行 glusterd 、 ceph
    2.在每个 Node 上运行日志收集 daemon,例如 fluentd 、 logstash
    3.在每个 Node 上运行监控 daemon,例如 Prometheus Node Exporter、 collectd 、Datadog 代理、
    New Relic 代理,或 Ganglia gmond
     
    Job
    Job 负责批处理任务,即仅执行一次的任务,它保证批处理任务的一个或多个 Pod 成功结束。
     
    CronJob
    Cron Job 管理基于时间的 Job,即:
    1.在给定时间点只运行一次
    2.周期性地在给定时间点运行
    * * * * * (分时日月周)和linux的crontab有点类似
     
    使用前提条件:**当前使用的 Kubernetes 集群,版本 >= 1.8(对 CronJob)。对于先前版本的集群,版本 < 1.8,
    启动 API Server时,通过传递选项 --runtime-config=batch/v2alpha1=true可以开启 batch/v2alpha1API**
     
    典型的用法如下所示:
    1.在给定的时间点调度 Job 运行
    2.创建周期性运行的 Job,例如:数据库备份、发送邮件
     
    StatefulSet
    StatefulSet 作为 Controller 为 Pod 提供唯一的标识。它可以保证部署和 scale 的顺序
    StatefulSet是为了解决有状态服务的问题(对应Deployments和ReplicaSets是为无状态服务而设计),其应用
    场景包括:
    1.稳定的持久化存储,即Pod重新调度后还是能访问到相同的持久化数据,基于PVC来实现
    2.稳定的网络标志,即Pod重新调度后其PodName和HostName不变,基于Headless Service(即没有Cluster IP的Service)来实现。
    3.有序部署,有序扩展,即Pod是有顺序的,在部署或者扩展的时候要依据定义的顺序依次依次进行(即从0到N-1,在下一个Pod运行之前所有之前的Pod必须都是Running和Ready状态),
    基于init containers来实现。
    4.有序收缩,有序删除(即从N-1到0)
     
    Horizontal Pod Autoscaling
    应用的资源使用率通常都有高峰和低谷的时候,如何削峰填谷,提高集群的整体资源利用率,让service中的Pod
    个数自动调整呢?这就有赖于Horizontal Pod Autoscaling了,顾名思义,使Pod水平自动缩放。
     
     

    RS 与 RC 与 Deployment 关联

    RC (ReplicationController )主要的作用就是用来确保容器应用的副本数始终保持在用户定义的副本数 。
    即如果有容器异常退出,会自动创建新的Pod来替代;而如果异常多出来的容器也会自动回收。
    Kubernetes 官方建议使用 RS(ReplicaSet ) 替代 RC (ReplicationController ) 进行部署,RS 跟 RC 没有
    本质的不同,只是名字不一样,并且 RS 支持集合式的 selector。
    举例一个简单的RS模板:
    $ vim rs.yaml
    apiVersion: extensions/v1beta1 kind: ReplicaSet #kind类型 metadata: #元数据信息 name: frontend spec: #详细描述信息 replicas: 3 #副本数 selector: matchLabels: #标签 tier: frontend #匹配的key:values template: #模板(通过怎样的方式创建RS,以下可以理解为嵌套了一个pod模板信息) metadata: labels: tier: frontend spec: containers: - name: php-redis image: gcr.io/google_samples/gb-frontend:v3 env: - name: GET_HOSTS_FROM value: dns ports: - containerPort: 80
    kubectl create -f rs.yaml

    测试自主式pod和资源控制器控制的pod的区别

    查看pod状态

    kubectl get pod

    可以看到所有pod信息,包括在运行的之前创建的自主式pod和上面创建的资源控制器pod

    删除所有pod

    kubectl delete pod --all

    再次查看pod

    可以看到删除的自主式Pod没有重新创建,而资源控制器pod会根据期望副本值,重新生成pod。

    查看选择标签(标签是控制器识别副本数的标记)

    kubectl get pod --show-labels

     标签也可以修改

    kubectl label pod frontend-m8hpc tier=frontend1 --overwrite=True

    删除rs

    kubectl delete rs --all

    RS 与 Deployment 的关联图例

     

    Deployment

    Deployment 为 Pod 和 ReplicaSet 提供了一个声明式定义(declarative)方法,用来替代以前的
    ReplicationController 来方便的管理应用。典型的应用场景包括:
    1.定义Deployment来创建Pod和ReplicaSet
    2.滚动升级和回滚应用
    3.扩容和缩容
    4.暂停和继续
     
     
    Ⅰ、部署一个简单的 Nginx 应用
    $ vim deployment.yaml
    apiVersion: extensions/v1beta1 kind: Deployment metadata: name: nginx-deployment spec: replicas: 3 template: metadata: labels: app: nginx spec: containers: - name: nginx image: nginx:1.7.9 ports: - containerPort: 80
    kubectl create -f deployment.yaml --record  # --record参数可以记录命令,我们可以很方便的查看每次 revision 的变化

    查看deployment (deployment创建后随即会创建相应的RS)

    kubectl get deployment

     查看RS

     查看pod

    查看网络

    kubectl get pod -o wide

     从上面结果即可看出deployment、RS、pod的关系

    Ⅱ、扩容
    kubectl scale deployment nginx-deployment --replicas 10

    查看扩容后结果

    Ⅲ、如果集群支持 horizontal pod autoscaling 的话,还可以为Deployment设置自动扩展
    kubectl autoscale deployment nginx-deployment --min=10 --max=15 --cpu-percent=80
    Ⅳ、更新镜像也比较简单
    kubectl set image deployment/nginx-deployment nginx=wangyanglinux/myapp:v2

     

    Ⅴ、回滚(回滚到上一个版本)
    kubectl rollout undo deployment/nginx-deployment

     

    更新 Deployment
    假如我们现在想要让 nginx pod 使用
    nginx:1.9.1 的镜像来代替原来的 nginx:1.7.9 的镜像 
    $ kubectl set image deployment/nginx-deployment nginx=nginx:1.9.1 
    deployment "nginx-deployment" image updated
    可以使用 edit 命令来编辑 Deployment 
    $ kubectl edit deployment/nginx-deployment 
    deployment "nginx-deployment" edited
     
    查看 rollout 的状态
    $ kubectl rollout status deployment/nginx-deployment 
    Waiting for rollout to finish: 2 out of 3 new replicas have been updated... 
    deployment "nginx-deployment" successfully rolled out
    查看历史 RS 
    $ kubectl get rs 
    NAME               DESIRED   CURRENT   READY   AGE 
    nginx-deployment-1564180365   3       3     0     6s 
    nginx-deployment-2035384211   0       0     0     36s
    Deployment 更新策略 
    Deployment 可以保证在升级时只有一定数量的 Pod 是 down 的。默认的,它会确保至少有比期望的Pod数量少一个是up状态(最多一个不可用)
    Deployment 同时也可以确保只创建出超过期望数量的一定数量的 Pod。默认的,它会确保最多比期望的Pod数量多一个的 Pod 是 up 的(最多1个 surge )
    未来的 Kuberentes 版本中,将从1-1变成25%-25% 
    $ kubectl describe deployments

    Rollover(多个rollout并行)

    假如您创建了一个有5个 niginx:1.7.9  replica的 Deployment,但是当还只有3个nginx:1.7.9的 replica 创建出来的时候您就开始更新含有5个 nginx:1.9.1  replica 的 Deployment。
    在这种情况下,Deployment 会立即杀掉已创建的3个 nginx:1.7.9 的 Pod,并开始创建 nginx:1.9.1 的 Pod。它不会等到所有的5个nginx:1.7.9 的Pod 都创建完成后才开始改变航道。
     
    回退 Deployment 
    kubectl set image deployment/nginx-deployment nginx=nginx:1.91 
    kubectl rollout status deployments nginx-deployment kubectl get pods kubectl rollout history deployment/nginx-deployment #查看回滚历史 kubectl rollout undo deployment/nginx-deployment #回滚上一个操作版本 kubectl rollout undo deployment/nginx-deployment --to-revision=2 # 可以使用 --revision参数指定 某个历史版本 kubectl rollout pause deployment/nginx-deployment # 暂停deployment 的更新

    可以用 kubectl rollout status 命令查看 Deployment 是否完成。
    如果 rollout 成功完成, kubectl rollout status 将返回一个0值的 Exit Code 
    $ kubectl rollout status deployment/nginx-deployment 
    Waiting for rollout to finish: 2 of 3 updated replicas are available... deployment "nginx-deployment" successfully rolled out 
    $ echo $? 
    0
    清理 Policy
    可以通过设置 .spec.revisonHistoryLimit项来指定 deployment 最多保留多少 revision 历史记录。
    默认的会保留所有的 revision;如果将该项设置为0,Deployment 就不允许回退了。
     
     
     

    DaemonSet

    什么是 DaemonSet ?
    DaemonSet 确保全部(或者一些)Node 上运行一个 Pod 的副本。当有 Node 加入集群时,也会为他们新增一
    个 Pod 。当有 Node 从集群移除时,这些 Pod 也会被回收。删除 DaemonSet 将会删除它创建的所有 Pod
    使用 DaemonSet 的一些典型用法:
    1.运行集群存储 daemon,例如在每个 Node 上运行 glusterd 、 ceph
    2.在每个 Node 上运行日志收集 daemon,例如 fluentd 、 logstash
    3.在每个 Node 上运行监控 daemon,例如 Prometheus Node Exporter、 collectd 、Datadog 代理、New Relic 代理,或 Ganglia gmond
     
    $ vim deamonset.yaml
    apiVersion: apps/v1 kind: DaemonSet metadata: name: deamonset-example labels: app: deamonset spec: selector: matchLabels: name: deamonset-example #和上面对应,必须一样,否创建不成功(创建出来一个新的pod,标签是deamonset-example,和上面的元数据信息匹配才能成功创建) template: metadata: labels: name: deamonset-example spec: containers: - name: daemonset-example image: wangyanglinux/myapp:v1
    kubectl create -f deamonset.yaml
     
    Job
    Job 负责批处理任务,即仅执行一次的任务,它保证批处理任务的一个或多个 Pod 成功结束
    特殊说明
    1.spec.template格式同Pod
    2.RestartPolicy仅支持Never或OnFailure
    3.单个Pod时,默认Pod成功运行后Job即结束
     
    4..spec.completions标志Job结束需要成功运行的Pod个数,默认为1
    5..spec.parallelism标志并行运行的Pod的个数,默认为1
    6.spec.activeDeadlineSeconds 标志失败Pod的重试最大时间,超过这个时间不会继续重试。
     
    在 Job 对象中,负责并行控制的参数有两个:
    1. spec.parallelism,它定义的是一个 Job 在任意时间最多可以启动多少个 Pod 同时运行;
    2. spec.completions,它定义的是 Job 至少要完成的 Pod 数目,即 Job 的最小完成数
     
    Example
    apiVersion: batch/v1 
    kind: Job 
    metadata: 
      name: pi 
    spec: 
      parallelism: 2 #最大并行数
      completions: 4 #最小完成数
      template: 
        metadata: 
          name: pi 
        spec: 
          containers: 
          - name: pi 
            image: perl 
            command: ["perl", "-Mbignum=bpi", "-wle", "print bpi(2000)"] 
          restartPolicy: Never   
          #执行成功后不重启,执行失败后Job Controller就会不断地尝试创建一个新Pod,默认重试次数在spec.backoffLimit定义,默认为6
     
    CronJob
    Cron Job 管理基于时间的 Job,即:
    1.在给定时间点只运行一次
    2.周期性地在给定时间点运行
     
    使用条件:当前使用的 Kubernetes 集群,版本 >= 1.8(对 CronJob)
     
    典型的用法如下所示:
    1.在给定的时间点调度 Job 运行
    2.创建周期性运行的 Job,例如:数据库备份、发送邮件
     
    CronJob Spec
    1).spec.schedule :调度,必需字段,指定任务运行周期,格式同 Cron
    2).spec.jobTemplate :Job 模板,必需字段,指定需要运行的任务,格式同 Job
    3).spec.startingDeadlineSeconds :启动 Job 的期限(秒级别),该字段是可选的。
      如果因为任何原因而错过了被调度的时间,那么错过执行时间的 Job 将被认为是失败的。如果没有指定,则没有期限
    4).spec.concurrencyPolicy :并发策略,该字段也是可选的。它指定了如何处理被 Cron Job 创建的 Job 的并发执行。只允许指定下面策略中的一种:
      Allow (默认):允许并发运行 Job
      Forbid :禁止并发运行,如果前一个还没有完成,则直接跳过下一个
      Replace :取消当前正在运行的 Job,用一个新的来替换
      注意,当前策略只能应用于同一个 Cron Job 创建的 Job。如果存在多个 Cron Job,它们创建的 Job 之间总是允许并发运行
    5).spec.suspend :挂起,该字段也是可选的。如果设置为 true ,后续所有执行都会被挂起。
      它对已经开始执行的 Job 不起作用。默认值为 false 。
    6).spec.successfulJobsHistoryLimit 和 .spec.failedJobsHistoryLimit :历史限制,是可选的字段。
      它们指定了可以保留多少完成和失败的 Job。默认情况下,它们分别设置为 3 和 1 。
      设置限制的值为 0 ,相关类型的 Job 完成后将不会被保留。
     
    Example
    apiVersion: batch/v1beta1 
    kind: CronJob 
    metadata: 
      name: hello 
    spec: 
      schedule: "*/1 * * * *"   #每分钟执行一次
      jobTemplate: 
        spec: 
          template: 
            spec:
              containers: 
              - name: hello 
                image: busybox 
                args: 
                - /bin/sh 
                - -c 
                - date; echo Hello from the Kubernetes cluster 
              restartPolicy: OnFailure #任务执行失败后,Job Controller 不会去尝试创建新的 Pod,但是,它会不断地尝试重启Pod里的容器

     

     一段时间后,可看到pod状态变为了Completed,说明任务执行完成,此时查看任务日志,可看到执行结果。

    如前所述,当一个 Job 的 Pod 运行结束后,它会进入 Completed 状态。但是,如果这个 Pod 因为某种原因一直不肯结束呢?

    在 Job 的 API 对象里,有一个 spec.activeDeadlineSeconds 字段可以设置最长运行时间,比如:

    spec:
     backoffLimit: 5
     activeDeadlineSeconds: 100

    一旦运行超过了 100 s,这个 Job 的所有 Pod 都会被终止。并且,你可以在 Pod 的状态里看到终 止的原因是 reason: DeadlineExceeded

     删除任务

    $ kubectl get cronjob 
    NAME SCHEDULE SUSPEND ACTIVE LAST-SCHEDULE 
    hello */1 * * * * False 0 <none> 
    $ kubectl get jobs 
    NAME DESIRED SUCCESSFUL AGE 
    hello-1202039034 1 1 49s 
    $ pods=$(kubectl get pods --selector=job-name=hello-1202039034 --output=jsonpath= {.items..metadata.name}) 
    $ kubectl logs $pods 
    Mon Aug 29 21:34:09 UTC 2016 Hello from the Kubernetes cluster 
    # 注意,删除 cronjob 的时候不会自动删除 job,这些 job 可以用 kubectl delete job 来删除 
    $ kubectl delete cronjob hello 
    cronjob "hello" deleted
    CrondJob 本身的一些限制

    Cron Job 在每次调度运行时间内 大概 会创建一个 Job 对象。我们之所以说 大概 ,是因为在特定的环境下可能会创建两个 Job,或者一个 Job 都没创建。我们尝试少发生这种情况,但却不能完全避免。因此,创建 Job 操作应该是 幂等的。

    Job 根据它所创建的 Pod 的并行度,负责重试创建 Pod,并就决定这一组 Pod 的成功或失败。Cron Job 根本就不会去检查 Pod

     
    好记性不如烂笔头,最难不过坚持
  • 相关阅读:
    networktool3
    networktool2
    networktool
    Intel Zepher 介绍
    使用IPMI发送事件1让BMC log 填满
    Knights Landing
    Intel历代处理器
    Intel Datacenter Group Public Roadmap
    django的url路由
    position用法
  • 原文地址:https://www.cnblogs.com/dannylinux/p/15266586.html
Copyright © 2011-2022 走看看