日日操夜夜添-日日操影院-日日草夜夜操-日日干干-精品一区二区三区波多野结衣-精品一区二区三区高清免费不卡

公告:魔扣目錄網為廣大站長提供免費收錄網站服務,提交前請做好本站友鏈:【 網站目錄:http://www.ylptlb.cn 】, 免友鏈快審服務(50元/站),

點擊這里在線咨詢客服
新站提交
  • 網站:51998
  • 待審:31
  • 小程序:12
  • 文章:1030137
  • 會員:747

 

從 kube-scheduler 的角度來看,它是通過一系列算法計算出最佳節點運行 Pod,當出現新的 Pod 進行調度時,調度程序會根據其當時對 Kube.NETes 集群的資源描述做出最佳調度決定,但是 Kubernetes 集群是非常動態的,由于整個集群范圍內的變化,比如一個節點為了維護,我們先執行了驅逐操作,這個節點上的所有 Pod 會被驅逐到其他節點去,但是當我們維護完成后,之前的 Pod 并不會自動回到該節點上來,因為 Pod 一旦被綁定了節點是不會觸發重新調度的,由于這些變化,Kubernetes 集群在一段時間內就可能會出現不均衡的狀態,所以需要均衡器來重新平衡集群。

當然我們可以去手動做一些集群的平衡,比如手動去刪掉某些 Pod,觸發重新調度就可以了,但是顯然這是一個繁瑣的過程,也不是解決問題的方式。為了解決實際運行中集群資源無法充分利用或浪費的問題,可以使用 descheduler 組件對集群的 Pod 進行調度優化,descheduler 可以根據一些規則和配置策略來幫助我們重新平衡集群狀態,其核心原理是根據其策略配置找到可以被移除的 Pod 并驅逐它們,其本身并不會進行調度被驅逐的 Pod,而是依靠默認的調度器來實現,目前支持的策略有:

  • RemoveDuplicates
  • LowNodeUtilization
  • HighNodeUtilization
  • RemovePodsViolatingInterPodAntiAffinity
  • RemovePodsViolatingNodeAffinity
  • RemovePodsViolatingNodeTaints
  • RemovePodsViolatingTopologySpreadConstraint
  • RemovePodsHavingTooManyRestarts
  • PodLifeTime
  • RemoveFailedPods

這些策略都是可以啟用或者禁用的,作為策略的一部分,也可以配置與策略相關的一些參數,默認情況下,所有策略都是啟用的。另外,還有一些通用配置,如下:

  • nodeSelector:限制要處理的節點
  • evictLocalStoragePods: 驅逐使用 LocalStorage 的 Pods
  • ignorePvcPods: 是否忽略配置 PVC 的 Pods,默認是 False
  • maxNoOfPodsToEvictPerNode:節點允許的最大驅逐 Pods 數

我們可以通過如下所示的 DeschedulerPolicy 來配置:

apiVersion: "descheduler/v1alpha2"
kind: "DeschedulerPolicy"
nodeSelector: "node=node1" # 如果沒有設置,所有內容都將被處理,無需進行此設置。
maxNoOfPodsToEvictPerNode: 5000 # 如果沒有設置,就不需要進行限制。
maxNoOfPodsToEvictPerNamespace: 5000
profiles:
  - name: ProfileName
    pluginConfig:
    - name: "DefaultEvictor"
      args:
        evictSystemCriticalPods: true
        evictFailedBarePods: true
        evictLocalStoragePods: true
        nodeFit: true
    plugins:
      evict:
        enabled:
          - "DefaultEvictor"
      deschedule:
        enabled:
          - ...
      balance:
        enabled:
          - ...
      [...]
 

安裝

descheduler? 可以以 CronJob? 或者 Deployment? 的形式運行在 k8s 集群內,同樣我們可以使用 Helm Chart 來安裝 descheduler:

 

? helm repo add descheduler https://kubernetes-sigs.Github.io/descheduler/

 

通過 Helm Chart 我們可以配置 descheduler? 以 CronJob? 或者 Deployment? 方式運行,默認情況下 descheduler? 會以一個 critical pod? 運行,以避免被自己或者 kubelet 驅逐了,需要確保集群中有 system-cluster-critical? 這個 Priorityclass:

? kubectl get priorityclass system-cluster-critical
NAME                      VALUE        GLOBAL-DEFAULT   AGE
system-cluster-critical   2000000000   false            87d

 

使用 Helm Chart 安裝默認情況下會以 CronJob? 的形式運行,執行周期為 schedule: "*/2 * * * *"?,這樣每隔兩分鐘會執行一次 descheduler 任務,默認的配置策略如下所示:

apiVersion: v1
kind: ConfigMap
metadata:
  name: descheduler
data:
  policy.yaml: |
    apiVersion: "descheduler/v1alpha1"
    kind: "DeschedulerPolicy"
    strategies:
      LowNodeUtilization:
        enabled: true
        params:
          nodeResourceUtilizationThresholds:
            targetThresholds:
              cpu: 50
              memory: 50
              pods: 50
            thresholds:
              cpu: 20
              memory: 20
              pods: 20
      RemoveDuplicates:
        enabled: true
      RemovePodsHavingTooManyRestarts:
        enabled: true
        params:
          podsHavingTooManyRestarts:
            includingInitContainers: true
            podRestartThreshold: 100
      RemovePodsViolatingInterPodAntiAffinity:
        enabled: true
      RemovePodsViolatingNodeAffinity:
        enabled: true
        params:
          nodeAffinityType:
          - requiredDuringSchedulingIgnoredDuringExecution
      RemovePodsViolatingNodeTaints:
        enabled: true
      RemovePodsViolatingTopologySpreadConstraint:
        enabled: true
        params:
          includeSoftConstraints: false

 

通過配置 DeschedulerPolicy? 的 strategies?,可以指定 descheduler 的執行策略,這些策略都是可以啟用或禁用的,下面我們會詳細介紹,這里我們使用默認策略即可,使用如下命令直接安裝即可:

? helm upgrade --install descheduler descheduler/descheduler --set image.repository=cnych/descheduler -n kube-system

 

部署完成后會創建一個 CronJob 資源對象來平衡集群狀態:

? kubectl get cronjob -n kube-system
NAME          SCHEDULE      SUSPEND   ACTIVE   LAST SCHEDULE   AGE
descheduler   */2 * * * *   False     1        8s              117s
? kubectl get job -n kube-system
NAME                   COMPLETIONS   DURATION   AGE
descheduler-28032982   1/1           15s        17s
? kubectl get pods -n kube-system -l job-name=descheduler-28032982
NAME                         READY   STATUS      RESTARTS   AGE
descheduler-28032982-vxn24   0/1     Completed   0          31s

 

正常情況下就會創建一個對應的 Job 來執行 descheduler 任務,我們可以通過查看日志可以了解做了哪些平衡操作:

? kubectl logs -f descheduler-28032982-vxn24 -nkube-system
I0420 08:22:10.019936       1 named_certificates.go:53] "Loaded SNI cert" index=0 certName="self-signed loopback" certDetail=""apiserver-loopback-client@1681978930" [serving] validServingFor=[apiserver-loopback-client] issuer="apiserver-loopback-client-ca@1681978929" (2023-04-20 07:22:09 +0000 UTC to 2024-04-19 07:22:09 +0000 UTC (now=2023-04-20 08:22:10.019885292 +0000 UTC))"
I0420 08:22:10.020138       1 secure_serving.go:210] Serving securely on [::]:10258
I0420 08:22:10.020301       1 tlsconfig.go:240] "Starting DynamicServingCertificateController"
I0420 08:22:10.021237       1 policyconfig.go:211] converting Deschedule plugin: %sRemovePodsViolatingInterPodAntiAffinity
I0420 08:22:10.021255       1 policyconfig.go:211] converting Deschedule plugin: %sRemovePodsViolatingNodeAffinity
I0420 08:22:10.021262       1 policyconfig.go:211] converting Deschedule plugin: %sRemovePodsViolatingNodeTaints
I0420 08:22:10.021269       1 policyconfig.go:202] converting Balance plugin: %sRemovePodsViolatingTopologySpreadConstraint
I0420 08:22:10.021280       1 policyconfig.go:202] converting Balance plugin: %sLowNodeUtilization
I0420 08:22:10.021296       1 policyconfig.go:202] converting Balance plugin: %sRemoveDuplicates
I0420 08:22:10.021312       1 policyconfig.go:211] converting Deschedule plugin: %sRemovePodsHavingTooManyRestarts
# ......
I0420 08:22:11.630980       1 removeduplicates.go:162] "Duplicate found" pod="kruise-system/kruise-controller-manager-7d78fc5c97-pxsqx"
I0420 08:22:11.630997       1 removeduplicates.go:103] "Processing node" node="node2"
I0420 08:22:11.631052       1 removeduplicates.go:103] "Processing node" node="node3"
I0420 08:22:11.631113       1 removeduplicates.go:103] "Processing node" node="master1"
I0420 08:22:11.631184       1 removeduplicates.go:194] "Adjusting feasible nodes" owner={namespace:kruise-system kind:ReplicaSet name:kruise-controller-manager-7d78fc5c97 imagesHash:openkruise/kruise-manager:v1.3.0} from=4 to=3
I0420 08:22:11.631200       1 removeduplicates.go:203] "Average occurrence per node" node="node1" ownerKey={namespace:kruise-system kind:ReplicaSet name:kruise-controller-manager-7d78fc5c97 imagesHash:openkruise/kruise-manager:v1.3.0} avg=1
I0420 08:22:11.647438       1 evictions.go:162] "Evicted pod" pod="kruise-system/kruise-controller-manager-7d78fc5c97-pxsqx" reasnotallow="" strategy="RemoveDuplicates" node="node1"
I0420 08:22:11.647494       1 descheduler.go:408] "Number of evicted pods" totalEvicted=1
I0420 08:22:11.647583       1 reflector.go:227] Stopping reflector *v1.Namespace (0s) from k8s.io/client-go/informers/factory.go:150
I0420 08:22:11.647702       1 reflector.go:227] Stopping reflector *v1.PriorityClass (0s) from k8s.io/client-go/informers/factory.go:150
I0420 08:22:11.647761       1 tlsconfig.go:255] "Shutting down DynamicServingCertificateController"
I0420 08:22:11.647764       1 reflector.go:227] Stopping reflector *v1.Node (0s) from k8s.io/client-go/informers/factory.go:150
I0420 08:22:11.647811       1 secure_serving.go:255] Stopped listening on [::]:10258
......

 

從日志中我們就可以清晰的知道因為什么策略驅逐了哪些 Pods。

PDB

由于使用 descheduler? 會將 Pod 驅逐進行重調度,但是如果一個服務的所有副本都被驅逐的話,則可能導致該服務不可用。如果服務本身存在單點故障,驅逐的時候肯定就會造成服務不可用了,這種情況我們強烈建議使用反親和性和多副本來避免單點故障,但是如果服務本身就被打散在多個節點上,這些 Pod 都被驅逐的話,這個時候也會造成服務不可用了,這種情況下我們可以通過配置 PDB(PodDisruptionBudget) 對象來避免所有副本同時被刪除,比如我們可以設置在驅逐的時候某應用最多只有一個副本不可用,則創建如下所示的資源清單即可:

# pdb-demo.yaml
apiVersion: policy/v1
kind: PodDisruptionBudget
metadata:
  name: pdb-demo
spec:
  maxUnavailable: 1 # 設置最多不可用的副本數量,或者使用 minAvailable,可以使用整數或百分比
  selector:
    matchLabels: # 匹配Pod標簽
      App: demo

 

關于 PDB 的更多詳細信息可以查看官方文檔:https://kubernetes.io/docs/tasks/run-application/configure-pdb/。

所以如果我們使用 descheduler? 來重新平衡集群狀態,那么我們強烈建議給應用創建一個對應的 PodDisruptionBudget 對象進行保護。

策略

PodLifeTime:驅逐超過指定時間限制的 pod

該策略用于驅逐比 maxPodLifeTimeSeconds? 更舊的 Pods,可以通過 podStatusPhases 來配置哪類狀態的 Pods 會被驅逐,建議為每個應用程序創建一個 PDB,以確保應用程序的可用性,比如我們可以配置如下所示的策略來驅逐運行超過 7 天的 Pod:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "PodLifeTime":
    enabled: true
    params:
      maxPodLifeTimeSeconds: 604800 # Pods 運行最多7天

 

RemoveDuplicates

該策略確保只有一個和 Pod 關聯的 RS、Deployment 或者 Job 資源對象運行在同一節點上。如果還有更多的 Pod 則將這些重復的 Pod 進行驅逐,以便更好地在集群中分散 Pod。如果某些節點由于某些原因崩潰了,這些節點上的 Pod 漂移到了其他節點,導致多個與 RS 關聯的 Pod 在同一個節點上運行,就有可能發生這種情況,一旦出現故障的節點再次準備就緒,就可以啟用該策略來驅逐這些重復的 Pod。

圖片

配置策略的時候,可以指定參數 excludeOwnerKinds 用于排除類型,這些類型下的 Pod 不會被驅逐:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "RemoveDuplicates":
    enabled: true
    params:
      removeDuplicates:
        excludeOwnerKinds:
          - "ReplicaSet"
 

LowNodeUtilization

該策略主要用于查找未充分利用的節點,并從其他節點驅逐 Pod,以便 kube-scheduler 重新將它們調度到未充分利用的節點上。該策略的參數可以通過字段 nodeResourceUtilizationThresholds 進行配置。

節點的利用率不足可以通過配置 thresholds 閾值參數來確定,可以通過 CPU、內存和 Pods 數量的百分比進行配置。如果節點的使用率均低于所有閾值,則認為該節點未充分利用。

圖片

此外,還有一個可配置的閾值 targetThresholds?,用于計算可能驅逐 Pods 的潛在節點,該參數也可以配置 CPU、內存以及 Pods 數量的百分比進行配置。thresholds? 和 targetThresholds 可以根據你的集群需求進行動態調整,如下所示示例:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "LowNodeUtilization":
    enabled: true
    params:
      nodeResourceUtilizationThresholds:
        thresholds:
          "cpu": 20
          "memory": 20
          "pods": 20
        targetThresholds:
          "cpu": 50
          "memory": 50
          "pods": 50

 

需要注意的是:

  • 僅支持以下三種資源類型:cpu、memory、pods
  • thresholds? 和 targetThresholds 必須配置相同的類型
  • 參數值的訪問是 0-100(百分制)
  • 相同的資源類型,thresholds? 的配置不能高于 targetThresholds 的配置

如果未指定任何資源類型,則默認是 100%,以避免節點從未充分利用變為過度利用。和 LowNodeUtilization? 策略關聯的另一個參數是 numberOfNodes,只有當未充分利用的節點數大于該配置值的時候,才可以配置該參數來激活該策略,該參數對于大型集群非常有用,其中有一些節點可能會頻繁使用或短期使用不足,默認情況下,numberOfNodes 為 0。

RemovePodsViolatingInterPodAntiAffinity

該策略可以確保從節點中刪除違反 Pod 反親和性的 Pod,比如某個節點上有 podA 這個 Pod,并且 podB 和 podC(在同一個節點上運行)具有禁止它們在同一個節點上運行的反親和性規則,則 podA 將被從該節點上驅逐,以便 podB 和 podC 運行正常運行。當 podB 和 podC 已經運行在節點上后,反親和性規則被創建就會發送這樣的問題。

圖片

要禁用該策略,直接配置成 false 即可:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "RemovePodsViolatingInterPodAntiAffinity":
    enabled: false

RemovePodsViolatingNodeTaints

該策略可以確保從節點中刪除違反 NoSchedule? 污點的 Pod,比如有一個名為 podA 的 Pod,通過配置容忍 key=value:NoSchedule 允許被調度到有該污點配置的節點上,如果節點的污點隨后被更新或者刪除了,則污點將不再被 Pods 的容忍滿足,然后將被驅逐:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "RemovePodsViolatingNodeTaints":
    enabled: true

RemovePodsViolatingNodeAffinity

該策略確保從節點中刪除違反節點親和性的 Pod。比如名為 podA 的 Pod 被調度到了節點 nodeA,podA 在調度的時候滿足了節點親和性規則 requiredDuringSchedulingIgnoredDuringExecution,但是隨著時間的推移,節點 nodeA 不再滿足該規則了,那么如果另一個滿足節點親和性規則的節點 nodeB 可用,則 podA 將被從節點 nodeA 驅逐,如下所示的策略配置示例:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "RemovePodsViolatingNodeAffinity":
    enabled: true
    params:
      nodeAffinityType:
        - "requiredDuringSchedulingIgnoredDuringExecution"

 

RemovePodsViolatingTopologySpreadConstraint

該策略確保從節點驅逐違反拓撲分布約束的 Pods,具體來說,它試圖驅逐將拓撲域平衡到每個約束的 ??maxSkew?? 內所需的最小 Pod 數,不過該策略需要 k8s 版本高于 1.18 才能使用。

默認情況下,此策略僅處理硬約束,如果將參數 ??includeSoftConstraints?? 設置為 True,也將支持軟約束。

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "RemovePodsViolatingTopologySpreadConstraint":
    enabled: true
    params:
      includeSoftConstraints: false

RemovePodsHavingTooManyRestarts

該策略確保從節點中刪除重啟次數過多的 Pods,它的參數包括 podRestartThreshold?(這是應將 Pod 逐出的重新啟動次數),以及包括InitContainers,它確定在計算中是否應考慮初始化容器的重新啟動,策略配置如下所示:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "RemovePodsHavingTooManyRestarts":
    enabled: true
    params:
      podsHavingTooManyRestarts:
        podRestartThreshold: 100
        includingInitContainers: true
 

Filter Pods

在驅逐 Pods 的時候,有時并不需要所有 Pods 都被驅逐,descheduler 提供了兩種主要的方式進行過濾:命名空間過濾和優先級過濾。

命名空間過濾

該策略可以配置是包含還是排除某些名稱空間。可以使用該策略的有:

  • PodLifeTime
  • RemovePodsHavingTooManyRestarts
  • RemovePodsViolatingNodeTaints
  • RemovePodsViolatingNodeAffinity
  • RemovePodsViolatingInterPodAntiAffinity
  • RemoveDuplicates
  • RemovePodsViolatingTopologySpreadConstraint

比如只驅逐某些命令空間下的 Pods,則可以使用 include 參數進行配置,如下所示:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "PodLifeTime":
    enabled: true
    params:
      podLifeTime:
        maxPodLifeTimeSeconds: 86400
      namespaces:
        include:
          - "namespace1"
          - "namespace2"
 

又或者要排除掉某些命令空間下的 Pods,則可以使用 exclude 參數配置,如下所示:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "PodLifeTime":
    enabled: true
    params:
      podLifeTime:
        maxPodLifeTimeSeconds: 86400
      namespaces:
        exclude:
          - "namespace1"
          - "namespace2"

 

優先級過濾

所有策略都可以配置優先級閾值,只有在該閾值以下的 Pod 才會被驅逐,我們可以通過設置 thresholdPriorityClassName?(將閾值設置為指定優先級類別的值)或 thresholdPriority?(直接設置閾值)參數來指定該閾值。默認情況下,該閾值設置為 system-cluster-critical 這個 PriorityClass 類的值。

比如使用 thresholdPriority:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "PodLifeTime":
    enabled: true
    params:
      podLifeTime:
        maxPodLifeTimeSeconds: 86400
      thresholdPriority: 10000

 

或者使用 thresholdPriorityClassName 進行過濾:

apiVersion: "descheduler/v1alpha1"
kind: "DeschedulerPolicy"
strategies:
  "PodLifeTime":
    enabled: true
    params:
      podLifeTime:
        maxPodLifeTimeSeconds: 86400
      thresholdPriorityClassName: "priorityclass1"

 

不過需要注意不能同時配置 thresholdPriority? 和 thresholdPriorityClassName,如果指定的優先級類不存在,則 descheduler 不會創建它,并且會引發錯誤。

注意事項

當使用 descheduler 驅除 Pods 的時候,需要注意以下幾點:

  • 關鍵性 Pod 不會被驅逐,比如 priorityClassName? 設置為 system-cluster-critical? 或 system-node-critical 的 Pod。
  • 不屬于 RS、Deployment 或 Job 管理的 Pods 不會被驅逐。
  • DaemonSet 創建的 Pods 不會被驅逐。
  • 使用 LocalStorage? 的 Pod 不會被驅逐,除非設置 evictLocalStoragePods: true。
  • 具有 PVC 的 Pods 不會被驅逐,除非設置 ignorePvcPods: true。
  • 在 LowNodeUtilization? 和 RemovePodsViolatingInterPodAntiAffinity? 策略下,Pods 按優先級從低到高進行驅逐,如果優先級相同,Besteffort? 類型的 Pod 要先于 Burstable? 和 Guaranteed 類型被驅逐。
  • annotations? 中帶有 descheduler.alpha.kubernetes.io/evict 字段的 Pod 都可以被驅逐,該注釋用于覆蓋阻止驅逐的檢查,用戶可以選擇驅逐哪個 Pods。
  • 如果 Pods 驅逐失敗,可以設置 --v=4? 從 descheduler 日志中查找原因,如果驅逐違反 PDB 約束,則不會驅逐這類 Pods。

分享到:
標簽:Kubernetes
用戶無頭像

網友整理

注冊時間:

網站:5 個   小程序:0 個  文章:12 篇

  • 51998

    網站

  • 12

    小程序

  • 1030137

    文章

  • 747

    會員

趕快注冊賬號,推廣您的網站吧!
最新入駐小程序

數獨大挑戰2018-06-03

數獨一種數學游戲,玩家需要根據9

答題星2018-06-03

您可以通過答題星輕松地創建試卷

全階人生考試2018-06-03

各種考試題,題庫,初中,高中,大學四六

運動步數有氧達人2018-06-03

記錄運動步數,積累氧氣值。還可偷

每日養生app2018-06-03

每日養生,天天健康

體育訓練成績評定2018-06-03

通用課目體育訓練成績評定