為命名空間設定最小和最大記憶體約束

定義命名空間的有效記憶體資源限制範圍,以便該命名空間中的每個新 Pod 都落在您設定的範圍內。

本頁說明如何設定在命名空間中執行的容器所使用的記憶體最小值和最大值。您可以在 LimitRange 物件中指定最小和最大記憶體值。如果 Pod 不符合 LimitRange 施加的限制,則無法在命名空間中建立它。

開始之前

您需要有一個 Kubernetes 叢集,並且必須設定 kubectl 命令列工具以與您的叢集通訊。建議在至少有兩個節點且不充當控制平面主機的叢集上執行本教學課程。如果您還沒有叢集,可以使用 minikube 建立一個,或者您可以使用以下 Kubernetes playground 之一

您必須具有在您的叢集中建立命名空間的權限。

您的叢集中的每個節點都必須至少有 1 GiB 的記憶體可用於 Pod。

建立命名空間

建立一個命名空間,以便您在本練習中建立的資源與叢集的其餘部分隔離。

kubectl create namespace constraints-mem-example

建立 LimitRange 和 Pod

這是一個 LimitRange 的範例 manifest

apiVersion: v1
kind: LimitRange
metadata:
  name: mem-min-max-demo-lr
spec:
  limits:
  - max:
      memory: 1Gi
    min:
      memory: 500Mi
    type: Container

建立 LimitRange

kubectl apply -f https://k8s.io/examples/admin/resource/memory-constraints.yaml --namespace=constraints-mem-example

查看關於 LimitRange 的詳細資訊

kubectl get limitrange mem-min-max-demo-lr --namespace=constraints-mem-example --output=yaml

輸出顯示了預期的最小和最大記憶體限制。但請注意,即使您沒有在 LimitRange 的組態檔案中指定預設值,它們也會自動建立。

  limits:
  - default:
      memory: 1Gi
    defaultRequest:
      memory: 1Gi
    max:
      memory: 1Gi
    min:
      memory: 500Mi
    type: Container

現在,每當您在 constraints-mem-example 命名空間中定義 Pod 時,Kubernetes 都會執行以下步驟

  • 如果該 Pod 中的任何容器未指定自己的記憶體請求和限制,則控制平面會將預設記憶體請求和限制指派給該容器。

  • 驗證該 Pod 中的每個容器都請求至少 500 MiB 的記憶體。

  • 驗證該 Pod 中的每個容器請求的記憶體不超過 1024 MiB (1 GiB)。

這是一個 Pod 的 manifest,其中有一個容器。在 Pod spec 中,唯一的容器指定了 600 MiB 的記憶體請求和 800 MiB 的記憶體限制。這些符合 LimitRange 施加的最小和最大記憶體限制。

apiVersion: v1
kind: Pod
metadata:
  name: constraints-mem-demo
spec:
  containers:
  - name: constraints-mem-demo-ctr
    image: nginx
    resources:
      limits:
        memory: "800Mi"
      requests:
        memory: "600Mi"

建立 Pod

kubectl apply -f https://k8s.io/examples/admin/resource/memory-constraints-pod.yaml --namespace=constraints-mem-example

驗證 Pod 正在執行且其容器運作正常

kubectl get pod constraints-mem-demo --namespace=constraints-mem-example

查看關於 Pod 的詳細資訊

kubectl get pod constraints-mem-demo --output=yaml --namespace=constraints-mem-example

輸出顯示該 Pod 中的容器具有 600 MiB 的記憶體請求和 800 MiB 的記憶體限制。這些符合此命名空間的 LimitRange 施加的限制

resources:
  limits:
     memory: 800Mi
  requests:
    memory: 600Mi

刪除您的 Pod

kubectl delete pod constraints-mem-demo --namespace=constraints-mem-example

嘗試建立一個超出最大記憶體限制的 Pod

這是一個 Pod 的 manifest,其中有一個容器。該容器指定了 800 MiB 的記憶體請求和 1.5 GiB 的記憶體限制。

apiVersion: v1
kind: Pod
metadata:
  name: constraints-mem-demo-2
spec:
  containers:
  - name: constraints-mem-demo-2-ctr
    image: nginx
    resources:
      limits:
        memory: "1.5Gi"
      requests:
        memory: "800Mi"

嘗試建立 Pod

kubectl apply -f https://k8s.io/examples/admin/resource/memory-constraints-pod-2.yaml --namespace=constraints-mem-example

輸出結果顯示 Pod 未被建立,因為它定義了一個容器,請求的記憶體超出允許的範圍

Error from server (Forbidden): error when creating "examples/admin/resource/memory-constraints-pod-2.yaml":
pods "constraints-mem-demo-2" is forbidden: maximum memory usage per Container is 1Gi, but limit is 1536Mi.

嘗試建立一個不符合最小記憶體請求的 Pod

這是一個 Pod 的 manifest 檔案,其中包含一個容器。該容器指定記憶體請求為 100 MiB,記憶體限制為 800 MiB。

apiVersion: v1
kind: Pod
metadata:
  name: constraints-mem-demo-3
spec:
  containers:
  - name: constraints-mem-demo-3-ctr
    image: nginx
    resources:
      limits:
        memory: "800Mi"
      requests:
        memory: "100Mi"

嘗試建立 Pod

kubectl apply -f https://k8s.io/examples/admin/resource/memory-constraints-pod-3.yaml --namespace=constraints-mem-example

輸出結果顯示 Pod 未被建立,因為它定義了一個容器,請求的記憶體低於強制要求的最小值

Error from server (Forbidden): error when creating "examples/admin/resource/memory-constraints-pod-3.yaml":
pods "constraints-mem-demo-3" is forbidden: minimum memory usage per Container is 500Mi, but request is 100Mi.

建立一個未指定任何記憶體請求或限制的 Pod

這是一個 Pod 的 manifest 檔案,其中包含一個容器。該容器未指定記憶體請求,也未指定記憶體限制。

apiVersion: v1
kind: Pod
metadata:
  name: constraints-mem-demo-4
spec:
  containers:
  - name: constraints-mem-demo-4-ctr
    image: nginx

建立 Pod

kubectl apply -f https://k8s.io/examples/admin/resource/memory-constraints-pod-4.yaml --namespace=constraints-mem-example

查看關於 Pod 的詳細資訊

kubectl get pod constraints-mem-demo-4 --namespace=constraints-mem-example --output=yaml

輸出結果顯示該 Pod 的唯一容器具有 1 GiB 的記憶體請求和 1 GiB 的記憶體限制。該容器是如何獲得這些值的呢?

resources:
  limits:
    memory: 1Gi
  requests:
    memory: 1Gi

因為您的 Pod 沒有為該容器定義任何記憶體請求和限制,所以叢集套用了來自 LimitRange 的預設記憶體請求和限制

這表示該 Pod 的定義顯示了這些值。您可以使用 kubectl describe 來檢查它

# Look for the "Requests:" section of the output
kubectl describe pod constraints-mem-demo-4 --namespace=constraints-mem-example

此時,您的 Pod 可能正在執行,也可能沒有執行。回想一下,此任務的先決條件是您的節點至少有 1 GiB 的記憶體。如果您的每個節點只有 1 GiB 的記憶體,那麼任何節點上都沒有足夠的可分配記憶體來容納 1 GiB 的記憶體請求。如果您碰巧使用具有 2 GiB 記憶體的節點,那麼您可能有足夠的空間來容納 1 GiB 的請求。

刪除您的 Pod

kubectl delete pod constraints-mem-demo-4 --namespace=constraints-mem-example

強制執行最小和最大記憶體限制

LimitRange 對命名空間施加的最大和最小記憶體限制僅在 Pod 建立或更新時強制執行。如果您更改 LimitRange,它不會影響先前建立的 Pod。

設定最小和最大記憶體限制的動機

作為叢集管理員,您可能希望對 Pod 可以使用的記憶體量施加限制。例如

  • 叢集中的每個節點都有 2 GiB 的記憶體。您不希望接受任何請求超過 2 GiB 記憶體的 Pod,因為叢集中沒有任何節點可以支援此請求。

  • 一個叢集由您的生產和開發部門共用。您希望允許生產工作負載最多消耗 8 GiB 的記憶體,但您希望開發工作負載限制為 512 MiB。您為生產和開發建立單獨的命名空間,並對每個命名空間應用記憶體限制。

清除

刪除您的命名空間

kubectl delete namespace constraints-mem-example

下一步

對於叢集管理員

對於應用程式開發人員

上次修改時間為 2024 年 10 月 30 日下午 5:17 PST:KEP 2837: Pod Level Resources Alpha (0374213f57)