配置名稱空間的最小和最大記憶體約束

定義一個名稱空間中有效的記憶體資源限制範圍,使該名稱空間中的每個新 Pod 都落在你配置的範圍內。

本頁面展示瞭如何為在名稱空間中執行的容器設定記憶體使用的最小和最大值。你在LimitRange物件中指定最小和最大記憶體值。如果 Pod 不符合 LimitRange 施加的約束,則無法在該名稱空間中建立。

準備工作

你需要有一個 Kubernetes 叢集,並且 kubectl 命令列工具已配置為與你的叢集通訊。建議在至少有兩個不作為控制平面主機的節點叢集上執行本教程。如果你還沒有叢集,可以使用 minikube 建立一個,或者使用以下 Kubernetes 演練環境之一:

你必須有權在叢集中建立名稱空間。

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

建立名稱空間

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

kubectl create namespace constraints-mem-example

建立一個 LimitRange 和一個 Pod

這是一個 LimitRange 的示例清單:

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 的清單。在 Pod 規約中,唯一容器指定了 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 的清單。該容器指定了 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 的清單。該容器指定了 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 的清單。該容器未指定記憶體請求,也未指定記憶體限制。

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 級別資源 Alpha (0374213f57)