k8s--容器探测

本文涉及的产品
容器服务 Serverless 版 ACK Serverless,952元额度 多规格
容器服务 Serverless 版 ACK Serverless,317元额度 多规格
简介: k8s--容器探测

容器探测介绍


容器探测用于检测容器中的应用实例是否正常工作,是保障业务可用性的一种传统机制。如果经过探测,实例的状态不符合预期,那么 k8s 就会把该问题实例“摘除”,不承担业务流量,k8s 提供了两种探针来实现容器探测,分别是

  • liveness probes:存活性探针,用于检测应用实例当前是否处于正常运行状态,如果不是,k8s 会重启容器
  • readness probes:就绪性探针,用于检测应用实例当前是否可以接受请求,如果不能,k8s 不会转发流量

上面两种探针目前均支持三种探测方式

  • Exec命令:在容器内执行一次命令,如果命令执行的退出码为0,则认为程序正常,否则不正常
……
  livenessProbe:
    exec:
      command:
      - cat
      - /tmp/healthy
……
  • TCPSocket:将会尝试访问一个用户容器的端口,如果能够建立这条连接,则认为程序正常,否则不正常
……      
  livenessProbe:
    tcpSocket:
      port: 8080
……
  • HTTPGet:调用容器内 Web 应用的 URL,如果返回的状态码在 200 和 399 之间,则认为程序正常,否则不正常
……
  livenessProbe:
    httpGet:
      path: / #URI地址
      port: 80 #端口号
      host: 127.0.0.1 #主机地址
      scheme: HTTP #支持的协议,http 或者 https
……

下面以 liveness probes 为例,做几个演示


方式一:Exec


创建 pod-liveness-exec.yaml

apiVersion: v1
kind: Pod
metadata:
  name: pod-liveness-exec
  namespace: zouzou
spec:
  containers:
  - name: nginx
    image: nginx:1.14
    ports: 
    - name: nginx-port
      containerPort: 80
    livenessProbe:
      exec:
        command: ["/bin/cat","/tmp/hello.txt"] # 执行一个查看文件的命令,是容器内部的文件,但容器内部没有这个文件

创建 pod,观察效果

# 创建 pod
[root@dce-10-6-215-215 tmp]# kubectl apply -f pod-liveness-exec.yaml
pod/pod-liveness-exec created
# 查看 pod,发现 pod 重启了 2 次
[root@dce-10-6-215-215 tmp]# kubectl get pod pod-liveness-exec -n zouzou
NAME                READY   STATUS    RESTARTS   AGE
pod-liveness-exec   1/1     Running   2          70s
# 查看 pod 的详细信息,可以看到  Liveness probe failed: /bin/cat: /tmp/hello.txt: No such file or directory
[root@dce-10-6-215-215 tmp]# kubectl describe pod pod-liveness-exec -n zouzou
Name:         pod-liveness-exec
Namespace:    zouzou
Priority:     0
.....
Events:
  Type     Reason     Age                From               Message
  ----     ------     ----               ----               -------
  Normal   Scheduled  85s                default-scheduler  Successfully assigned zouzou/pod-liveness-exec to dce-10-6-215-200
  Normal   Pulled     22s (x3 over 82s)  kubelet            Container image "nginx:1.14" already present on machine
  Normal   Created    22s (x3 over 81s)  kubelet            Created container nginx
  Normal   Killing    22s (x2 over 52s)  kubelet            Container nginx failed liveness probe, will be restarted
  Normal   Started    21s (x3 over 81s)  kubelet            Started container nginx
  Warning  Unhealthy  2s (x8 over 72s)   kubelet            Liveness probe failed: /bin/cat: /tmp/hello.txt: No such file or directory # 这里说了错误信息

可以看到,容器一直在重启,因为容器里面没有那个文件,接下来,我们删除这个 pod,在修改文件,改为一个正确的

kubectl delete -f pod-liveness-exec.yaml # 删除 pod

修改 pod-liveness-exec.yaml 文件,修改后的如下

apiVersion: v1
kind: Pod
metadata:
  name: pod-liveness-exec
  namespace: zouzou
spec:
  containers:
  - name: nginx
    image: nginx:1.14
    ports: 
    - name: nginx-port
      containerPort: 80
    livenessProbe:
      exec:
        command: ["/bin/ls","/tmp"] # 执行一个查看文件的命令,是容器内部的文件,这个肯定是可以的,因为 /tmp 目录存在

创建 pod,查看效果

# 创建pod
kubectl apply -f pod-liveness-exec.yaml

查看 event

# 发现没有重启
[root@dce-10-6-215-215 tmp]# kubectl get pod pod-liveness-exec -n zouzou
NAME                READY   STATUS    RESTARTS   AGE
pod-liveness-exec   1/1     Running   0          50s
# 查看 event,正常的
[root@dce-10-6-215-215 tmp]# kubectl describe pod pod-liveness-exec -n zouzou
Name:         pod-liveness-exec
Namespace:    zouzou
Priority:     0
Node:         dce-10-6-215-200/10.6.215.200
......
Events:
  Type    Reason     Age   From               Message
  ----    ------     ----  ----               -------
  Normal  Scheduled  61s   default-scheduler  Successfully assigned zouzou/pod-liveness-exec to dce-10-6-215-200
  Normal  Pulled     59s   kubelet            Container image "nginx:1.14" already present on machine
  Normal  Created    59s   kubelet            Created container nginx
  Normal  Started    58s   kubelet            Started container nginx


方式二:TCPSocket


tcpSocket 就是访问某个端口,看是不是通的

创建 pod-liveness-tcpsocket.yaml,内容如下

apiVersion: v1
kind: Pod
metadata:
  name: pod-liveness-tcpsocket
  namespace: zouzou
spec:
  containers:
  - name: nginx
    image: nginx:1.14
    ports: 
    - name: nginx-port
      containerPort: 80
    livenessProbe:
      tcpSocket:
        port: 8080 # 尝试访问8080端口,因为我们只有一个 nginx 容器,只有 80 端口是正常的,所以8080是访问不通的

创建 pod,观察效果

# 创建 pod
[root@dce-10-6-215-215 tmp]# kubectl apply -f pod-liveness-tcpsocket.yaml
pod/pod-liveness-tcpsocket created
# 查看信息,发现有 RESTART
[root@dce-10-6-215-215 tmp]# kubectl get pod pod-liveness-tcpsocket -n zouzou
NAME                     READY   STATUS    RESTARTS   AGE
pod-liveness-tcpsocket   1/1     Running   1          34s
# 查看 event,报错信息说明端口是不通的
[root@dce-10-6-215-215 tmp]# kubectl describe pod pod-liveness-tcpsocket -n zouzou
Name:         pod-liveness-tcpsocket
Namespace:    zouzou
Priority:     0
Node:         dce-10-6-215-200/10.6.215.200
Start Time:   Fri, 15 Apr 2022 18:25:10 +0800
......
Events:
  Type     Reason     Age                From               Message
  ----     ------     ----               ----               -------
  Normal   Scheduled  48s                default-scheduler  Successfully assigned zouzou/pod-liveness-tcpsocket to dce-10-6-215-200
  Normal   Pulled     18s (x2 over 45s)  kubelet            Container image "nginx:1.14" already present on machine
  Normal   Killing    18s                kubelet            Container nginx failed liveness probe, will be restarted
  Normal   Created    17s (x2 over 45s)  kubelet            Created container nginx
  Normal   Started    17s (x2 over 44s)  kubelet            Started container nginx
  Warning  Unhealthy  8s (x4 over 38s)   kubelet            Liveness probe failed: dial tcp 172.29.34.232:8080: connect: connection refused # 8080 端口访问失败

可以看到,容器一直在重启,因为容器里面 8080 端口是不通的。接下来,我们删除这个 pod,在修改文件,改为一个正确的

# 删除 pod
kubectl delete -f pod-liveness-tcpsocket.yaml

修改 pod-liveness-tcpsocket.yaml,内容如下

apiVersion: v1
kind: Pod
metadata:
  name: pod-liveness-tcpsocket
  namespace: zouzou
spec:
  containers:
  - name: nginx
    image: nginx:1.14
    ports: 
    - name: nginx-port
      containerPort: 80
    livenessProbe:
      tcpSocket:
        port: 80 # 80 端口是可以正常访问的

创建 pod,查看效果

# 创建 pod
kubectl apply -f pod-liveness-tcpsocket.yaml

查看 event

# 查看 pod ,发现没有重启
[root@dce-10-6-215-215 tmp]# kubectl get pod pod-liveness-tcpsocket -n zouzou
NAME                     READY   STATUS    RESTARTS   AGE
pod-liveness-tcpsocket   1/1     Running   0          93s
# 查看 event,都是正常的
[root@dce-10-6-215-215 tmp]# kubectl describe pod pod-liveness-tcpsocket -n zouzou
Name:         pod-liveness-tcpsocket
Namespace:    zouzou
Priority:     0
Node:         dce-10-6-215-200/10.6.215.200
Start Time:   Fri, 15 Apr 2022 18:30:32 +0800
.....
Events:
  Type    Reason     Age   From               Message
  ----    ------     ----  ----               -------
  Normal  Scheduled  100s  default-scheduler  Successfully assigned zouzou/pod-liveness-tcpsocket to dce-10-6-215-200
  Normal  Pulled     97s   kubelet            Container image "nginx:1.14" already present on machine
  Normal  Created    97s   kubelet            Created container nginx
  Normal  Started    96s   kubelet            Started container nginx


方式三:HTTPGet


httpget 就是访问一个 url,看能不能访问成功

创建 pod-liveness-httpget.yaml,内容如下

apiVersion: v1
kind: Pod
metadata:
  name: pod-liveness-httpget
  namespace: zouzou
spec:
  containers:
  - name: nginx
    image: nginx:1.14
    ports:
    - name: nginx-port
      containerPort: 80
    livenessProbe:
      httpGet:  # 其实就是访问http://127.0.0.1:80/hello,nginx 容器里没有这个地址  
        scheme: HTTP #支持的协议,http或者https
        port: 80 #端口号
        path: /hello #URI地址
  • host:连接使用的主机名,默认是 Pod 的 IP。也可以在 HTTP 头中设置 “Host” 来代替。
  • scheme :用于设置连接主机的方式(HTTP 还是 HTTPS)。默认是 "HTTP"。
  • path:访问 HTTP 服务的路径。默认值为 "/"。
  • httpHeaders:请求中自定义的 HTTP 头。HTTP 头字段允许重复。
  • port:访问容器的端口号或者端口名。如果数字必须在 1~65535 之间。

对于 HTTP 探测,kubelet 发送一个 HTTP 请求到指定的路径和端口来执行检测。 除非 httpGet 中的 host 字段设置了,否则 kubelet 默认是给 Pod 的 IP 地址发送探测。 如果 scheme 字段设置为了 HTTPS,kubelet 会跳过证书验证发送 HTTPS 请求。 大多数情况下,不需要设置host 字段。 这里有个需要设置 host 字段的场景,假设容器监听 127.0.0.1,并且 Pod 的 hostNetwork 字段设置为了 true。那么 httpGet 中的 host 字段应该设置为 127.0.0.1。 可能更常见的情况是如果 Pod 依赖虚拟主机,你不应该设置 host 字段,而是应该在 httpHeaders 中设置 Host

针对 HTTP 探针,kubelet 除了必需的 Host 头部之外还发送两个请求头部字段: User-AgentAccept。这些头部的默认值分别是 kube-probe/{{ skew currentVersion >}} (其中 1.24 是 kubelet 的版本号)和 */*

创建 pod,观察效果

# 创建 pod
[root@dce-10-6-215-215 tmp]# kubectl apply -f pod-liveness-httpget.yaml
pod/pod-liveness-httpget created
# 查看 pod,发现有 RESTARTS
[root@dce-10-6-215-215 tmp]# kubectl get pod pod-liveness-httpget -n zouzou
NAME                   READY   STATUS    RESTARTS   AGE
pod-liveness-httpget   1/1     Running   1          37s
# 查看 event,发现返回的状态码为 404
[root@dce-10-6-215-215 tmp]# kubectl describe pod pod-liveness-httpget -n zouzou
Name:         pod-liveness-httpget
Namespace:    zouzou
Priority:     0
Node:         dce-10-6-215-200/10.6.215.200
Start Time:   Fri, 15 Apr 2022 18:36:18 +0800
.....
Events:
  Type     Reason     Age                From               Message
  ----     ------     ----               ----               -------
  Normal   Scheduled  49s                default-scheduler  Successfully assigned zouzou/pod-liveness-httpget to dce-10-6-215-200
  Normal   Killing    16s                kubelet            Container nginx failed liveness probe, will be restarted
  Normal   Pulled     15s (x2 over 46s)  kubelet            Container image "nginx:1.14" already present on machine
  Normal   Created    15s (x2 over 46s)  kubelet            Created container nginx
  Normal   Started    15s (x2 over 46s)  kubelet            Started container nginx
  Warning  Unhealthy  6s (x4 over 36s)   kubelet            Liveness probe failed: HTTP probe failed with statuscode: 404 # 状态码为 404

可以看到,容器一直在重启,因为容器里面没有那个地址,接下来,我们删除这个 pod,在修改文件,改为一个正确的

# 删除 pod
kubectl delete -f pod-liveness-httpget.yaml

修改 pod-liveness-httpget.yaml 文件,修改后的如下

apiVersion: v1
kind: Pod
metadata:
  name: pod-liveness-httpget
  namespace: zouzou
spec:
  containers:
  - name: nginx
    image: nginx:1.14
    ports:
    - name: nginx-port
      containerPort: 80
    livenessProbe:
      httpGet:  # 其实就是访问http://127.0.0.1:80/,nginx 容器里可以访问这个地址  
        scheme: HTTP #支持的协议,http或者https
        port: 80 #端口号
        path: / #URI地址

创建 pod,查看效果

# 创建 pod
[root@dce-10-6-215-215 tmp]# kubectl apply -f pod-liveness-httpget.yaml
pod/pod-liveness-httpget created
# 查看 pod,没有重启
[root@dce-10-6-215-215 tmp]# kubectl get pod pod-liveness-httpget -n zouzou
NAME                   READY   STATUS    RESTARTS   AGE
pod-liveness-httpget   1/1     Running   0          220s
# 查看 event,正常启动的
[root@dce-10-6-215-215 tmp]# kubectl describe pod pod-liveness-httpget -n zouzou
Name:         pod-liveness-httpget
Namespace:    zouzou
Priority:     0
Node:         dce-10-6-215-200/10.6.215.200
Start Time:   Fri, 15 Apr 2022 18:41:35 +0800
......
Events:
  Type    Reason     Age   From               Message
  ----    ------     ----  ----               -------
  Normal  Scheduled  27s   default-scheduler  Successfully assigned zouzou/pod-liveness-httpget to dce-10-6-215-200
  Normal  Pulled     24s   kubelet            Container image "nginx:1.14" already present on machine
  Normal  Created    24s   kubelet            Created container nginx
  Normal  Started    23s   kubelet            Started container nginx


其他参数配置


至此,已经使用 liveness Probe 演示了三种探测方式,但是查看 livenessProbe 的子属性,会发现除了这三种方式,还有一些其他的配置

[root@dce-10-6-215-215 tmp]# kubectl explain pod.spec.containers.livenessProbe
FIELDS:
   exec <Object>  
   tcpSocket    <Object>
   httpGet      <Object>
   initialDelaySeconds  <integer>  # 容器启动后等待多少秒执行第一次探测
   timeoutSeconds       <integer>  # 探测超时时间。默认1秒,最小1秒
   periodSeconds        <integer>  # 执行探测的频率。默认是10秒,最小1秒
   failureThreshold     <integer>  # 连续探测失败多少次才被认定为失败。默认是3。最小值是1
   successThreshold     <integer>  # 连续探测成功多少次才被认定为成功。默认是1

注意:如果设置了探针等待多少秒执行一次的话(initialDelaySeconds),如果还没到这个时间,k8s 就默认这个 pod 是失败的,只有等到了时间,并且探针通过的话,才认为这个 pod 是成功的


相关实践学习
通过Ingress进行灰度发布
本场景您将运行一个简单的应用,部署一个新的应用用于新的发布,并通过Ingress能力实现灰度发布。
容器应用与集群管理
欢迎来到《容器应用与集群管理》课程,本课程是“云原生容器Clouder认证“系列中的第二阶段。课程将向您介绍与容器集群相关的概念和技术,这些概念和技术可以帮助您了解阿里云容器服务ACK/ACK Serverless的使用。同时,本课程也会向您介绍可以采取的工具、方法和可操作步骤,以帮助您了解如何基于容器服务ACK Serverless构建和管理企业级应用。 学习完本课程后,您将能够: 掌握容器集群、容器编排的基本概念 掌握Kubernetes的基础概念及核心思想 掌握阿里云容器服务ACK/ACK Serverless概念及使用方法 基于容器服务ACK Serverless搭建和管理企业级网站应用
相关文章
|
14天前
|
运维 Kubernetes 调度
阿里云容器服务 ACK One 分布式云容器企业落地实践
3年前的云栖大会,我们发布分布式云容器平台ACK One,随着3年的发展,很高兴看到ACK One在混合云,分布式云领域帮助到越来越多的客户,今天给大家汇报下ACK One 3年来的发展演进,以及如何帮助客户解决分布式领域多云多集群管理的挑战。
阿里云容器服务 ACK One 分布式云容器企业落地实践
|
1天前
|
Kubernetes Docker 容器
容器运行时Containerd k8s
容器运行时Containerd k8s
13 2
|
7天前
|
Kubernetes Cloud Native 持续交付
云原生之旅:Docker容器化与Kubernetes集群管理
【9月更文挑战第33天】在数字化转型的浪潮中,云原生技术如同一艘航船,带领企业乘风破浪。本篇文章将作为你的航海指南,从Docker容器化的基础讲起,直至Kubernetes集群的高级管理,我们将一起探索云原生的奥秘。你将学习到如何封装应用、实现环境隔离,以及如何在Kubernetes集群中部署、监控和扩展你的服务。让我们启航,驶向灵活、可伸缩的云原生未来。
|
10天前
|
Kubernetes Cloud Native Docker
云原生时代的容器化实践:Docker与Kubernetes入门
【9月更文挑战第30天】在云计算的浪潮中,云原生技术正以前所未有的速度重塑着软件开发和运维领域。本文将通过深入浅出的方式,带你了解云原生的核心组件——Docker容器和Kubernetes集群,并探索它们如何助力现代应用的构建、部署和管理。从Docker的基本命令到Kubernetes的资源调度,我们将一起开启云原生技术的奇妙之旅。
|
1月前
|
人工智能 Prometheus 监控
使用 NVIDIA NIM 在阿里云容器服务(ACK)中加速 LLM 推理
本文介绍了在阿里云容器服务 ACK 上部署 NVIDIA NIM,结合云原生 AI 套件和 KServe 快速构建高性能模型推理服务的方法。通过阿里云 Prometheus 和 Grafana 实现实时监控,并基于排队请求数配置弹性扩缩容策略,提升服务稳定性和效率。文章提供了详细的部署步骤和示例,帮助读者快速搭建和优化模型推理服务。
113 7
使用 NVIDIA NIM 在阿里云容器服务(ACK)中加速 LLM 推理
|
14天前
|
Kubernetes API Docker
跟着iLogtail学习容器运行时与K8s下日志采集方案
iLogtail 作为开源可观测数据采集器,对 Kubernetes 环境下日志采集有着非常好的支持,本文跟随 iLogtail 的脚步,了解容器运行时与 K8s 下日志数据采集原理。
|
10天前
|
人工智能 运维 监控
阿里云ACK容器服务生产级可观测体系建设实践
阿里云ACK容器服务生产级可观测体系建设实践
|
21天前
|
存储 Kubernetes 负载均衡
深入浅出 Kubernetes:掌握容器编排的艺术
在云计算迅速发展的今天,Kubernetes 作为容器编排和管理的事实标准,提供了运行分布式系统的强大框架,支持无缝部署、扩展和管理容器化应用。本文深入探讨 Kubernetes 的核心概念与组件,介绍其自动化部署、负载均衡、存储编排等特性,并演示如何使用 Minikube、kubeadm 及 Kubernetes 服务提供商部署集群,通过 `kubectl` 和 Helm 管理资源,帮助开发者掌握这一关键技术。
|
27天前
|
存储 Kubernetes 持续交付
深入浅出 Kubernetes:掌握容器编排的艺术
Kubernetes作为容器编排领域的领头羊,提供了运行分布式系统的强大框架,支持自动化部署、扩展和管理容器化应用。本文深入浅出地介绍了Kubernetes的核心概念与关键组件,包括服务发现、存储编排及自动部署等特性。通过Minikube、kubeadm及云服务商等多种方式部署集群,并使用`kubectl`、YAML配置文件和Helm进行资源管理。掌握Kubernetes将成为软件开发者的宝贵技能。
|
3天前
|
Kubernetes 应用服务中间件 nginx
k8s学习--k8s集群使用容器镜像仓库Harbor
本文介绍了在CentOS 7.9环境下部署Harbor容器镜像仓库,并将其集成到Kubernetes集群的过程。环境中包含一台Master节点和两台Node节点,均已部署好K8s集群。首先详细讲述了在Harbor节点上安装Docker和docker-compose,接着通过下载Harbor离线安装包并配置相关参数完成Harbor的部署。随后介绍了如何通过secret和serviceaccount两种方式让Kubernetes集群使用Harbor作为镜像仓库,包括创建secret、配置节点、上传镜像以及创建Pod等步骤。最后验证了Pod能否成功从Harbor拉取镜像运行。