Pod因CPU不足而处于挂起状态。

44
在我的GCE Kubernetes集群上,我无法再创建Pod。
Warning FailedScheduling    pod (www.caveconditions.com-f1be467e31c7b00bc983fbe5efdbb8eb-438ef) failed to fit in any node
fit failure on node (gke-prod-cluster-default-pool-b39c7f0c-c0ug): Insufficient CPU

查看该节点的分配统计信息

Non-terminated Pods:        (8 in total)
  Namespace         Name                                        CPU Requests    CPU Limits  Memory Requests Memory Limits
  ---------         ----                                        ------------    ----------  --------------- -------------
  default           dev.caveconditions.com-n80z8                            100m (10%)  0 (0%)      0 (0%)      0 (0%)
  default           lamp-cnmrc                                  100m (10%)  0 (0%)      0 (0%)      0 (0%)
  default           mongo-2-h59ly                                   200m (20%)  0 (0%)      0 (0%)      0 (0%)
  default           www.caveconditions.com-tl7pa                            100m (10%)  0 (0%)      0 (0%)      0 (0%)
  kube-system           fluentd-cloud-logging-gke-prod-cluster-default-pool-b39c7f0c-c0ug       100m (10%)  0 (0%)      200Mi (5%)  200Mi (5%)
  kube-system           kube-dns-v17-qp5la                              110m (11%)  110m (11%)  120Mi (3%)  220Mi (5%)
  kube-system           kube-proxy-gke-prod-cluster-default-pool-b39c7f0c-c0ug              100m (10%)  0 (0%)      0 (0%)      0 (0%)
  kube-system           kubernetes-dashboard-v1.1.0-orphh                       100m (10%)  100m (10%)  50Mi (1%)   50Mi (1%)
Allocated resources:
  (Total limits may be over 100%, i.e., overcommitted. More info: http://releases.k8s.io/HEAD/docs/user-guide/compute-resources.md)
  CPU Requests  CPU Limits  Memory Requests Memory Limits
  ------------  ----------  --------------- -------------
  910m (91%)    210m (21%)  370Mi (9%)  470Mi (12%)

我已经分配了91%的资源,无法再增加10%。但是难道不能超额使用资源吗?

服务器的使用率平均约为10%的CPU。

enter image description here

我需要做哪些更改,使得我的 Kubernetes 集群能够创建更多的 Pod?


你尝试过在 Kubernetes 中启用自动缩放吗?http://blog.kubernetes.io/2016/07/autoscaling-in-kubernetes.html - George
是的,我已经添加了自动缩放。但由于资源限制,它无法增加pod。 - Chris
5个回答

43

我最近也遇到了这个问题。经过一些研究,我发现GKE有一个默认的LimitRange,将CPU请求限制设置为100m

您可以通过运行kubectl get limitrange -o=yaml来验证这一点。 它会显示类似于以下内容:

apiVersion: v1
items:
- apiVersion: v1
  kind: LimitRange
  metadata:
    annotations:
      kubectl.kubernetes.io/last-applied-configuration: |
        {"apiVersion":"v1","kind":"LimitRange","metadata":{"annotations":{},"name":"limits","namespace":"default"},"spec":{"limits":[{"defaultRequest":{"cpu":"100m"},"type":"Container"}]}}
    creationTimestamp: 2017-11-16T12:15:40Z
    name: limits
    namespace: default
    resourceVersion: "18741722"
    selfLink: /api/v1/namespaces/default/limitranges/limits
    uid: dcb25a24-cac7-11e7-a3d5-42010a8001b6
  spec:
    limits:
    - defaultRequest:
        cpu: 100m
      type: Container
kind: List
metadata:
  resourceVersion: ""
  selfLink: ""

这个限制适用于每个容器。例如,如果您有一个4核节点,并且每个pod创建2个容器,则仅允许创建大约20个pod(4个CPU = 4000m -> / 100m = 40 -> / 2 = 20)。

“解决”方法是更改默认的 LimitRange 以更好地适应您的用例,然后删除旧的pods,以便可以使用更新的值重新创建它们。另一种(也可能更好的)选择是直接在每个部署/ pod 定义中设置CPU限制。

一些阅读材料:

https://kubernetes.io/docs/tasks/configure-pod-container/assign-cpu-resource/#specify-a-cpu-request-and-a-cpu-limit

https://kubernetes.io/docs/tasks/administer-cluster/manage-resources/cpu-default-namespace/#create-a-limitrange-and-a-pod

https://kubernetes.io/docs/concepts/configuration/manage-compute-resources-container/#how-pods-with-resource-limits-are-run

https://cloud.google.com/blog/products/gcp/kubernetes-best-practices-resource-requests-and-limits


6
伙计,这是一个非常好的资源 — 真的帮了我很多忙。感谢你的整理! - Necevil

18
当我试图将应用程序部署到集群时,我遇到了相同的问题。在我的情况下,为测试分支自动创建了不必要的Pods。为了诊断问题,我需要执行以下操作:

kubectl get po

kubectl describe po - 对于现有的某个Pod,检查它运行在哪个节点上

kubectl get nodes

kubectl describe node - 查看用于现有Pod的节点的CPU使用情况,如下所示:

Allocated resources:
  (Total limits may be over 100 percent, i.e., overcommitted.)
  Resource                       Requests      Limits
  --------                       --------      ------
  cpu                            1010m (93%)   4 (210%)

然后,可以使用以下命令删除不需要的Pod:

kubectl get deployments

kubectl delete deployment .... - 这里将"...."替换为需要删除的Pod所在的Deployment名称。

一旦我删除了足够多的未使用的Pod, 我就能部署新的Pod了。


7

5
嗨,这真是遗憾。这会导致滚动更新困难,因为由于CPU限制而无法正常工作,即使只使用10%的CPU…你有什么解决办法吗? - Chris

2
如果您使用了限制和请求,请降低CPU请求和/或限制。
背景:
我在我的情况下非常接近CPU和内存的限制,经过一段时间后发现以下情况:
假设我有以下内容:
- 一个名为node-1的节点,具有CPU / A = 2000毫核和MEM / A = 7827字节。 - 我想部署使用Helm的app-1,它可以使用理论上可用的所有资源。
在我的情况下,我将app-1配置为具有一些resources.limits.cpu、resources.limits.memory、resources.requests.cpu、resources.requests.memory,并且将resources.limits.cpu最初设置为1000m。
具体发生了什么:

所以 node-1 不仅运行 app-1,还有其他 3 个额外的应用程序用于其他事情。从上到下,CPU 请求的总和为 100m + 0 + 250m + 1 (1000m) = 1350m(也可以在以下分配资源中找到)。

一切都好吧?看起来是这样,但如果我想部署另一个版本的 app-1 呢?在那种情况下,我将不得不放弃旧版本并重新创建它。

在某些情况下,这可能是可以接受的,但当我想使用 Helm 部署 app-1 的更新时(请注意,helm update 将删除旧的 Pod 并启动一个新的 Pod),而不必先关闭旧的 Pod,那么我会收到 Insufficient CPU error

这是因为 kube-scheduler 可能会执行以下操作。它将采用您先前为 CPU 设置的任何值,并将其添加到您要部署的新 app-1 的任何限制中。理论上使 CPU 请求超出了请求的限制。换句话说,在其他 Pod 被关闭之前,它在很短的时间内执行了 1350m + 1 (1000m) = 2350m。现在这就是问题所在,因为它超出了初始限制 2000m。
解决方案:
在这种情况下,解决方案是将 CPU 请求设置为较低的数字,可能只有 500m,以便初始值为 100m + 0 + 250m + 500m = 850m,当它执行加法时,它只是 100m + 0 + 250m + 500m + 500m = 1350m,仍然低于硬限制 2000m。现在在我的情况下,helm 将删除旧的 Pod,将整个请求 CPU 使用量恢复到 850m,但存在一个非常短的时间段,在此期间它会总结剩余部分。

enter image description here


1

对我来说,将所有的部署和服务创建在一个不同的命名空间(而不是default)中解决了这个问题。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接