1. 程式人生 > >Kuberntes 服務質量保證(QoS)_Kubernetes中文社群

Kuberntes 服務質量保證(QoS)_Kubernetes中文社群

【編者的話】Kubernetes做為目前主流的容器叢集管理平臺,需要整體統籌平臺資源使用情況、公平合理的將資源分配給相關pod容器使用,並且要保證容器生命週期內有足夠的資源來保證其執行。 與此同時,由於資源發放的獨佔性,即資源已經分配給了某容器,同樣的資源不會在分配給其他容器,對於資源利用率相對較低的容器來說,佔用資源卻沒有實際使用(比如CPU、記憶體)造成了嚴重的資源浪費,Kubernetes需從優先順序與公平性等角度提高資源的利用率。為了實現資源被有效排程和分配的同時提高資源利用率,Kubernetes針對不同服務質量的預期,通過QoS來對pod進行服務質量管理,提供了個採用requests

limits兩種型別對資源進行分配和使用限制。對於一個pod來說,服務質量體現在兩個為2個具體的指標: CPU與記憶體。實際過程中,當NODE節點上記憶體資源緊張時,kubernetes會根據預先設定的不同QoS類別進行相應處理。

設定資源限制的原因

如果未做過節點 nodeSelector,親和性(node affinity)或pod親和、反親和性(pod affinity/anti-affinity)等Pod高階排程策略 設定,我們沒有辦法指定服務部署到指定機器上,如此可能會造成cpu或記憶體等密集型的pod同時分配到相同Node,造成資源競爭。另一方面,如果未對資源進行限制,一些關鍵的服務可能會因為資源競爭因OOM等原因被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中所有容器都必須統一設定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:對Container foo與bar不同的resources(foo為memory,而bar為cpu)設定了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可以在某個節點上長期執行,由該節點上的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。

不可壓縮資源記憶體:當Node 記憶體資源不足時,那麼就會有程序因OOM會被kernel kill掉,3種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

參考資料