深入理解kubernetes(K8s)的Qos, requests和limits


Kubernetes的服務質量保證(QoS)

Kubernetes需要整體統籌平台資源使用情況、公平合理的將資源分配給相關pod容器使用,並且要保證容器生命周期內有足夠的資源來保證其運行。 與此同時,由於資源發放的獨占性,即資源已經分配給了某容器,同樣的資源不會在分配給其他容器,對於資源利用率相對較低的容器來說,占用資源卻沒有實際使用(比如CPU、內存)造成了嚴重的資源浪費,Kubernetes需從優先級與公平性等角度綜合考慮來提高資源的利用率。為了在資源被有效調度和分配的同時提高資源利用率,Kubernetes針對不同服務質量的預期,通過QoS(Quality of Service)來對pod進行服務質量管理,提供了個采用requestslimits兩種類型對資源進行分配和使用限制。對於一個pod來說,服務質量體現在兩個為2個具體的指標: CPU與內存。實際過程中,當NODE節點上內存資源緊張時,kubernetes會根據預先設置的不同QoS類別進行相應處理。

設置資源限制的原因

如果未做過節點 nodeSelector,親和性(node affinity)或pod親和、反親和性(pod affinity/anti-affinity)等Pod高級調度策略設置,我們沒有辦法指定服務部署到指定機器上,如此可能會造成cpu或內存等密集型的pod全部都被分配到相同的Node上,造成資源競爭。另一方面,如果未對資源進行限制,一些關鍵的服務可能會因為資源競爭因OOM(Out of Memory)等原因被kill掉,或者被限制CPU使用

資源需求(Requests)和限制( Limits)

對於每一個資源,container可以指定具體的資源需求(requests)和限制(limits),requests申請范圍是0到node節點的最大配置,而limits申請范圍是requests到無限,即0 <= requests <=Node Allocatable, requests <= limits <= Infinity。

對於CPU,如果pod中服務使用CPU超過設置的limits,pod不會被kill掉但會被限制。如果沒有設置limits,pod可以使用全部空閑的cpu資源。

對於內存,當一個pod使用內存超過了設置的limits,pod中container的進程會被kernel因OOM kill掉。當container因為OOM被kill掉時,系統傾向於在其原所在的機器上重啟該container或本機或其他重新創建一個pod。

QoS分類

Kubelet提供QoS服務質量管理,支持系統級別的OOM控制。在Kubernetes中,pod的QoS級別包括:GuaranteedBurstable與 Best-Effort。下面對各級別分別進行相應說明:

Guaranteed:pod中的所有容器都必須對cpu和memory同時設置limits如果有一個容器要設置requests,那么所有容器都要設置,並設置參數同limits一致,那么這個pod的QoS就是Guaranteed級別。
注:如果一個容器只指明limit而未設定request,則request的值等於limit

Guaranteed舉例1:容器只指明了limits而未指明requests)。

containers:
name: foo
resources:
  limits:
    cpu: 10m
    memory: 1Gi
name: bar
resources:
  limits:
    cpu: 100m
    memory: 100Mi

Guaranteed舉例2:requestslimit均指定且值相等。

containers:
name: foo
resources:
  limits:
    cpu: 10m
    memory: 1Gi
  requests:
    cpu: 10m
    memory: 1Gi

name: bar
resources:
  limits:
    cpu: 100m
    memory: 100Mi
  requests:
    cpu: 100m
    memory: 100Mi

Burstable: pod中只要有一個容器的requestslimits的設置不相同,該pod的QoS即為Burstable(即可能會停服)舉例如下:

Container bar沒有指定resources

containers:
name: foo
resources:
  limits:
    cpu: 10m
    memory: 1Gi
  requests:
    cpu: 10m
    memory: 1Gi

name: bar

Burstable舉例2:pod中只要有一個容器沒有對cpu或者memory中的request和limits都沒有明確指定。

containers:
name: foo
resources:
  limits:
    memory: 1Gi

name: bar
resources:
  limits:
    cpu: 100m

Burstable舉例3:Container foo沒有設置limits,而bar requests與 limits均未設置。

containers:
name: foo
resources:
  requests:
    cpu: 10m
    memory: 1Gi  
name: bar

Best-Effort:如果對於全部的resources來說requestslimits均未設置,該pod的QoS即為Best-Effort。舉例如下:

containers:
name: foo
resources:
name: bar
resources:

可壓縮資源與不可壓縮資源

Kubernetes根據資源能否伸縮進行分類,划分為可壓縮資源和不可以壓縮資源2種。
CPU資源是目前支持的一種可壓縮資源,而內存資源和磁盤資源為目前所支持的不可壓縮資源。

QoS優先級

3種QoS優先級從有低到高(從左向右):

Best-Effort pods -> Burstable pods -> Guaranteed pods

靜態pod

在Kubernetes中有一種DaemonSet類型pod,此類pod可以常駐在某個Node上運行,由該Node上kubelet服務直接管理而無需api server介入。靜態pod也無需關聯任何RC,完全由kubelet服務來監控,當kubelet發現靜態pod停止時,kubelet會重新啟動靜態pod。

資源回收策略

當kubernetes集群中某個節點上可用資源比較小時,kubernetes提供了資源回收策略保證被調度到該節點pod服務正常運行。當節點上的內存或者CPU資源耗盡時,可能會造成該節點上正在運行的pod服務不穩定。Kubernetes通過kubelet來進行回收策略控制,保證節點上pod在節點資源比較小時可以穩定運行。

可壓縮資源:CPU
在壓縮資源部分已經提到CPU屬於可壓縮資源,當pod使用超過其設置的limits值時,pod中的進程會被限制使用cpu,但不會被kill。

不可壓縮資源:內存
Kubernetes通過cgroup給pod設置QoS級別,當資源不足時先kill優先級低的pod,在實際使用過程中,通過OOM分數值來實現,OOM分數值從0-1000。

OOM分數值根據OOM_ADJ參數計算得出,對於Guaranteed級別的pod,OOM_ADJ參數設置成了-998,對於BestEffort級別的pod,OOM_ADJ參數設置成了1000,對於Burstable級別的POD,OOM_ADJ參數取值從2到999。對於kubernetes保留資源,比如kubelet,docker,OOM_ADJ參數設置成了-999,表示不會被OOM kill掉。OOM_ADJ參數設置的越大,通過OOM_ADJ參數計算出來OOM分數越高,表明該pod優先級就越低,當出現資源競爭時會越早被kill掉,對於OOM_ADJ參數是-999的表示kubernetes永遠不會因為OOM而被kill掉

QoS pods被kill掉的場景與順序

  • Best-Effort 類型的pods:系統用完了全部內存時,該類型pods會最先被kill掉。
  • Burstable類型pods:系統用完了全部內存,且沒有Best-Effort container可以被kill時,該類型pods會被kill掉。
  • Guaranteed pods:系統用完了全部內存、且沒有Burstable與Best-Effort container可以被kill,該類型的pods會被kill掉。
    注:如果pod進程因使用超過預先設定的limites而非Node資源緊張情況,系統傾向於在其原所在的機器上重啟該container或本機或其他重新創建一個pod, 即自動遷移服務

使用建議

  • 如果資源充足,可將QoS pods類型均設置為Guaranteed。用計算資源換業務性能和穩定性,減少排查問題時間和成本
  • 如果想更好的提高資源利用率,業務服務可以設置為Guaranteed,而其他服務根據重要程度可分別設置為BurstableBest-Effort,例如filebeat。

已知問題

不支持swap,當前的QoS策略假設swap已被禁止。

參考資料

轉自http://dockone.io/article/2592並進行了修改

Resource Quality of Service in Kubernetes: https://github.com/kubernetes/ ... os.md

Introduction to Quality Of Service and Service Level Agreement: http://www.loriotpro.com/Produ ... N.htm

Kubelet pod level resource management: https://github.com/kubernetes/ ... nt.md

Kubelet - Eviction Policy: https://github.com/kubernetes/ ... on.md


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM