默认情况下,容器可以无限制地使用节点上所有的可用资源(如CPU、内存)。
假设在一个节点上运行多个Pod,其中一个Pod的访问量突然增加,该Pod将不断请求节点资源。最终,该Pod可能占用大量资源,导致其他Pod缺乏足够的资源可用,从而引发访问速度非常慢,甚至无法正常提供服务的问题。
为了避免出现这类问题,可以对Pod中的容器进行资源限制,确保它们不会超出指定的资源配额。资源限制相关配置字段如下。
resources.limits.cpu:限制容器的CPU使用量。你可以指定以CPU核心(例如,0.5表示半个核心,1表示一个核心)或以millicores(例如,500 m表示半个核心,1000 m表示一个核心)为单位的CPU限制。
resources.limits.memory:限制容器的内存使用量。你可以指定以Ki、Mi、Gi等为单位的内存限制。
resources.limits.hugepages-<size>:用于限制容器的HugePages使用量。你可以指定限制的HugePages大小(如2 Mi、1 Gi等)。
此外,还可以为容器配置资源请求,用于指定容器所需的最小资源量,以确保这个Pod被调度到能够满足其最小资源需求的节点上。资源请求相关配置字段如下。
resources.requests.cpu:指定容器所需的最小CPU资源。
resources.requests.memory:指定容器所需的最小内存资源。
resources.requests.hugepages-<size>:指定容器所需的最小HugePages资源。
资源请求和资源限制配置如下:
在上述配置中,“resources”部分定义了容器的资源请求和资源限制,具体配置如下。
“requests”定义容器的资源请求。这里告知调度器,这个Pod需要被调度到至少满足64 Mi内存和0.25核CPU的节点上。
“limits”定义容器的资源限制。这里表示该容器不允许超过128 Mi内存和0.5核CPU。容器如果尝试使用更多资源,容器资源将受到限制。
创建Pod资源:
[root@k8s-master ~]# kubectl apply -f pod-nginx.yaml
接下来,使用stress工具对该容器进行压力测试,以验证容器的资源限制。
进入容器中,首先安装stress工具:
[root@k8s-master ~]# kubectl exec -it pod-nginx -- bash root@pod-nginx:/# apt update root@pod-nginx:/# apt install stress -y
然后,使用stress工具对CPU进行压力测试:
root@pod-nginx:/# stress -c 2
其中,“-c”参数用于指定压测时生成的进程数量。这些进程在工作时会持续计算随机数的平方根,从而消耗更多的CPU。
此时,可以使用“kubectl top”命令查看Pod的资源利用率:
可以看到,该Pod的CPU使用受到限制,正常不会超出500 m,内存也会限制在128 Mi范围内。
如果容器内存使用量超过限制值,kubelet组件会重新启动容器,并将容器的状态标记为“OOMKilled”。当CPU使用量超过限制值时,kubelet组件不会触发容器的重启。这是因为超出内存限制通常会导致应用程序无法正常工作,而重启容器可以简单地解决这种问题。相比之下,超出CPU限制并不会直接导致应用程序无法正常工作,只是降低了处理性能,这是一种可接受的情况。
资源限制主要目的是防止容器无限制地占用节点的计算资源。为了保障节点的稳定性和性能,通常不建议限制值超过节点硬件配置的80%,以确保容器在可接受的最大资源范围内运行,有效地平衡各Pod之间的资源利用,从而提高整个集群的可靠性。
需要注意的是,“kubectl top”命令依赖于“metric-server”服务,需要额外地部署(详见https://github.com/kubernetes-sigs/metrics-server)。