• 【k8s】五、Pod生命周期(一)


    目录

    前言

    Pod生命周期

    Pod 相位 状态值

    挂起(Pending)

    运行中(Running)

    成功(Succeeded)

    失败(Failed)

    未知(Unknown)

    Init Containers

    Init Contianers的作用

    Init Contianers实验

    特殊说明

    总结

    写在后面


    前言

    前面我们部署了k8s容器环境,也知道了怎么书写数据自己的Pod,那本节我们就一起来学习Pod的生命周期。这个是重点来的哦,因为在实际运用的过程中,对于Pod生命周期每个阶段的进行检测,进而分析和排错。

    Pod生命周期

    上图主要描述了在容器环境初始化完成之后,pod从创建到退出,中间这段时间经历的过程;

    从大的方向上看,pod生命周期分两个阶段:

    • 第一阶段是初始化容器。
    • 第二阶段是主容器的整个生命周期;

    在 Pod 启动时,pause容器总是创建的第一个容器。每个pod中都存在一个pause容器。这个是k8s自动创建的。

    对于Init Container来说,一个pod中可以定义多个初始化容器,他们必须是串行执行,只有当所有的初始化容器执行完后,对应的主容器才会启动;如上图所示,会按顺序把1、2、3的InitC都执行完成之后,才进入Main Container阶段

    Main Container生命周期又分为三个阶段:

    • 第一阶段是运行post start hook,这个阶段是主容器运行之后立即需要做的事;
    • 第二阶段是主容器正常运行的阶段,在这个阶段中,我们可以定义对容器的健康状态(liveness)检查和就绪状态(readness)检查;
    • 第三阶段是运行pre stop hook,这个阶段主要做容器即将退出前需要做的事;

    readness——就绪检测,检测成功后,Pod状态改为Ready

    liveness——生存检测,

    对于对容器的健康状态检查和就绪状态检查,我们也可以定义开始检查的延迟时长;因为有些容器存在容器显示running状态,但内部程序还没有初始化,如果立即做健康状态检查,可能存在健康状态为不健康,从而导致容器重启的状况;

    Pod 相位 状态值

    首先在介绍 Pod 的生命周期之前,我们先了解下 Pod 的状态,因为 Pod 状态可以反映出当前我们的 Pod 的具体状态信息,也是我们分析排错的一个必备的方式。

    我们可以通过命令kubectl explain pod.status查看到

    挂起(Pending)

    Pod已被K8s系统接受,但有一个或者多个容器镜像尚未创建,等待时间包括调度Pod的时间和通过网络下载镜像的时间。这可能需要花点时间。

    运行中(Running)

    该Pod已经绑定到了一个节点上,Pod中所有的容器都已被创建。至少有一个容器正在运行,或者正处于启动或者重启状态。

    成功(Succeeded)

    Pod中所有的容器都被成功终止并且不会再重启。

    失败(Failed)

    Pod中所有容器都已经终止,并且至少有一个容器是因为失败终止。也就是说,至少有一个容器以非0状态退出或者被系统终止。

    未知(Unknown)

    因为某些原因无法取得Pod的状态,通常是因为与Pod所在主机通信失败。

    Init Containers

    Init Containers是在Pod的主容器启动之前要运行的容器,主要是做一些主容器的前置工作。

    一个Pod能够具有多个容器,应用运行在应用容器里面,但是该Pod中可能有一个或多个先于应用容器启动的Init容器。

    Init容器与普通容器非常像,除了以下两点:

    • Init容器总是运行到成功完成为止,如果某个初始化容器运行失败,那么kubernetes需要重启它直至成功完成。
    • Init容器必须按照定义的顺序执行,每个Init容器都必须在下一个Init容器启动之前成功完成

    注意:如果Pod的Init容器失败,Kubernetes会不断重启该Pod,知道Init容器成功位置。然而,如果Pod对应的重启策略restartPolicy为Never时,Pod不会重新启动。

    Init Contianers的作用

    因为Init容器具有与应用程序容器分离的单独镜像,所以它们的启动相关代码具有如下优势:

    • 他们可以包含并运行实用工具,但是出于安全考虑,时不建议在应用程序容器镜像中包含这些实用工具的。
    • 特们可以包含实用工具和定制化代码来安装,但是不能出现在应用程序镜像中。例如,创建镜像没必要FROM另一个镜像,只需要在安装过程中使用类似sed、awk、python、dig这样的工具
    • 应用程序镜像可以分离出创建和部署的角色,而没有必要联合他们构建一个单独的镜像。
    • Init容器使用Linux Namespace,所以相对应用程序容器来说,具有不同的文件系统视图。因此,他们能够具有访问Secret的权限,而应用程序容器则不能。实现分权限来治理。例如,有一个文件夹里面只有一个文件是main容器要用到的,但是又不希望main容器有这个文件夹的访问权限,于是通过init容器来访问该文件,并且把该文件复制到main容器中。
    • 他们必须在应用程序容器启动之前运行完成,而应用程序容器时并行运行的,所以,Init容器能够提供一种简单的阻塞或延迟应用容器启动的方法,直到满足了一系列应用容器启动的先决条件。例如我们有两个容器,一个放数据库,一个放应用服务,服务要在数据库启动之后启动,访问才不会报错,那么此时我们可以在应用服务容器的init containers中设置一个条件,用于检测数据库容器是否完成启动,如果数据库完成启动了,则应用服务容器可以正常启动。如下图所示:

    Init Contianers实验

    下面我们通过实际例子来进一步认识init containers。

    1. # init-pod.yaml
    2. # author: 攻城狮白玉
    3. apiVersion: v1
    4. kind: Pod
    5. metadata:
    6. name: baiyu-pod
    7. namespace: baiyu-learn-k8s
    8. labels:
    9. app: baiyu-app
    10. version: v1
    11. spec:
    12. containers:
    13. - name: baiyu-app-container
    14. image: busybox:1.32
    15. command: ['sh', '-c', 'echo The app is running && sleep 3600']
    16. initContainers:
    17. - name: init-baiyu-service
    18. image: busybox:1.32
    19. command: ['sh', '-c','until nslookup baiyu-service; do echo waiting for baiyu-service; sleep 2;done;']
    20. - name: init-baiyu-db
    21. image: busybox:1.32
    22. command: ['sh', '-c', 'until nslookup baiyu-db; do echo waiting for baiyu-db; sleep 2; done;']

    上面的yaml,运行了一个pod。里面有一个main container,有两个init container

    kubectl create -f init-pod.yaml

    然后执行kubectl get pod -n baiyu-learn-k8s -o wide -w查看容器状态

     此时无论多久,上面这个容器都不会变成running状态的。这是因为我们写了两个init container的条件没有满足。

    第一个init container里面,我们执行了下面这句命令,表示在我们能解析到有这个baiyu-service名称的网络服务就打破循环。

    1. until nslookup baiyu-service;
    2. do
    3. echo waiting for baiyu-service;
    4. sleep 2;
    5. done;

    此处补充个小知识点,便是Linux中until的用法。

    until跟while类似,都是一个固定循环。

    但是until跟while又有不同,则是它们的条件满足不同。

    until是直到条件为真时,打破循环。而while是条件为真时一直循环,条件为假时打破循环。

    此时,我们通过命令

    kubectl logs baiyu-pod -n baiyu-learn-k8s --container init-baiyu-service

    查看pod中的init-baiyu-service容器的日志,可以发现它一直在循环检测服务是否起来

     为了满足我们init-pod中的init container的条件,我们准备了以下脚本实现两个service,用于满足init C的条件。

    1. # init-service.yaml
    2. # author: 攻城狮白玉
    3. kind: Service
    4. apiVersion: v1
    5. metadata:
    6. name: baiyu-service
    7. namespace: baiyu-learn-k8s
    8. spec:
    9. ports:
    10. - protocol: TCP
    11. port: 80
    12. targetPort: 9376
    13. ---
    14. kind: Service
    15. apiVersion: v1
    16. metadata:
    17. name: baiyu-db
    18. namespace: baiyu-learn-k8s
    19. spec:
    20. ports:
    21. - protocol: TCP
    22. port: 80
    23. targetPort: 9377

    执行命令启动脚本kubectl apply -f init-service.yaml

    使用kubectl get pod -n baiyu-learn-k8s -o wide -w查看我们的pod的状态。结果如下图所示,在两个init容器执行完成之后,main 容器进行执行,最终Pod完成启动Pod状态变为Running

    特殊说明

    • 在Pod启动过程中,Init容器会按顺序在网络和数据卷初始化(网络和数据卷初始化是在pause中启动的)之后启动。每个容器必须在下一个容器启动之前成功退出。
    • 如果由于运行时或失败退出,将导致容器启动失败,它会根据Pod的restartPolicy指定的策略进行重试。然而,如果Pod的restartPolicy设置为Always,Init容器失败时会使用RestartPolicy策略
    • 在所有的Init容器没有成功之前,Pod将不会变成Ready状态。Init容器的端口将不会再Service中进行聚集。正在初始化中的Pod处于Pending状态,但应该会将Initializing状态设置为true
    • 如果Pod重启,所有Init容器必须重新执行。
    • 对于Init容器spec的修改被限制在容器image字段,修改其他字段都不会生效。更改Init容器的image字段等价于重启该Pod
    • Init容器具有应用容器的所有字段,除了readinessProbe,因为Init容器无法定义不同于完成(completion)的就绪(readiness)之外的其他状态。这会在验证过程中强制执行。
    • 在Pod中的每个app和Init容器的名称必须要唯一;与任何其他容器共享同一个名称,会在验证时抛出错误。
    • Init容器执行的效果应该是幂等的。

    总结

    本文介绍了k8s整体容器的生命周期以及Init Container的基本概念和作用,并通过一个实战例子进一步加深了各位同学对init Containers的理解。限于篇幅,并没有把容器的生命周期所有知识点写完,下一篇我会介绍容器生命周期的两个探针,readness和liveness。以及启停时的动作钩子

    写在后面

    如果觉得有用的话,麻烦一键三连支持一下攻城狮白玉,并把本文分享给更多的小伙伴。你的简单支持,我的无限创作动力

  • 相关阅读:
    [机缘参悟-61]:《兵者,诡道也》-3-孙子兵法解读-敌战计
    【dyn_threshold_划痕检测】
    第五课 树与图
    总结出了这份Alibaba(P5-P9)学习进阶路线图用劲耗时两年才得!
    APM性能监测工具skywalking——k8s从入门到高并发系列教程(十三)
    Unity Job System详解(2)——如何将业务逻辑Job化
    【python】采集**本子,不要看了,快进来~
    C++实现enum反射,类似magic_enum,支持enum classes
    Megatron-LM GPT 源码分析(一) Tensor Parallel分析
    【Mysql系列】04_事务
  • 原文地址:https://blog.csdn.net/zhh763984017/article/details/127286358