日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

Kubernetes 是如何调度的?

發布時間:2024/8/23 编程问答 37 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Kubernetes 是如何调度的? 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

作者?|?阿文,責編 | 郭芮

頭圖 | CSDN 下載自東方IC

出品 | CSDN(ID:CSDNnews)

自互聯網出現以來 ,云計算的概念已經提出了有 50 年。從1957 年,John McCarthy 將計算機中的分時共享概念設計成了一種工具。從此以后,這個概念的名字經歷過數次變化:從“服務中心(service bureau)”到應用服務提供商,到互聯網即服務,到云計算,再到軟件定義的數據中心。

一直以來基礎設施是云計算的基礎核心,基礎設施服務(Infrastructure as a Service,IaaS)將IT基礎設施資源(計算、網絡與存儲)以一種彈性的服務方式對外提供。近十余年來隨著云計算不斷發展與落地,云基礎設施技術架構也在不斷往前演進,從傳統虛擬化、基礎設施資源管理走向軟件定義架構。隨著近5年來以容器和微服務為代表的云原生技術興起,云基礎設施架構需要演進以全面擁抱云原生技術。

以容器、容器編排、微服務、服務網格為代表的云原生技術正在日益體現出期在云計算領域的非凡價值,眾所周知,容器編排中 Kubernetes 已經成為容器編排領域的事實標準。

kubernetes 可以提供所需的編排和管理功能,以便針對工作負載大規模部署容器。借助 Kubernetes 編排功能,可以快速的構建跨多個容器的應用服務、跨集群調度、擴展這些容器,并長期持續管理這些容器的健康狀況。在 Kubernetes 中,調度?是指將 Pod 放置到合適的 Node上,然后對應 Node 上的 Kubelet才能夠運行這些 pod。

那么kubernetes 是如何進行調度的呢?我們來一起看下。

Kubernetes ?是如何調度的?

kube-scheduler 是 Kubernetes 集群的默認調度器,并且是集群 控制面的一部分。同時 kube-scheduler 在設計上是允許你自己寫一個調度組件并替換原有的 kube-scheduler。

對每一個新創建的 Pod 或者是未被調度的 Pod,kube-scheduler 會選擇一個最優的 Node 去運行這個 Pod。那么kube-scheduler 是如何選擇最優的 Node 呢?

kube-scheduler監聽apiserver的/api/pod/,當發現集群中有未得到調度的pod(即PodSpec.NodeName為空)時,會查詢集群各node的信息,經過Predicates(過濾)、Priorities(優選器),得到最適合該pod運行的node后,再向apiserver發送請求,將該容器綁定到選中的node上。

Kubernetes Scheduler 提供的調度流程分三步:

  • 過濾, 遍歷nodelist,選擇出符合要求的候選節點,Kubernetes內置了多種預選規則供用戶選擇。

  • 打分, 在選擇出符合要求的候選節點中,采用優選規則計算出每個節點的積分,最后選擇得分最高的。

  • 綁定, ?選出其中得分最高的 Node 來運行 Pod。之后,調度器將這個調度決定通知給 kube-apiserver,這個過程叫做綁定。

整個過程,如圖所示:

預選的算法可以參考源碼predicates.go(https://github.com/kubernetes/kubernetes/blob/master/pkg/scheduler/algorithm/predicates/predicates.go):

const?(//?MatchInterPodAffinityPred?defines?the?name?of?predicate?MatchInterPodAffinity.MatchInterPodAffinityPred?=?"MatchInterPodAffinity"//?CheckVolumeBindingPred?defines?the?name?of?predicate?CheckVolumeBinding.CheckVolumeBindingPred?=?"CheckVolumeBinding"//?GeneralPred?defines?the?name?of?predicate?GeneralPredicates.GeneralPred?=?"GeneralPredicates"//?HostNamePred?defines?the?name?of?predicate?HostName.HostNamePred?=?"HostName"//?PodFitsHostPortsPred?defines?the?name?of?predicate?PodFitsHostPorts.PodFitsHostPortsPred?=?"PodFitsHostPorts"//?MatchNodeSelectorPred?defines?the?name?of?predicate?MatchNodeSelector.MatchNodeSelectorPred?=?"MatchNodeSelector"//?PodFitsResourcesPred?defines?the?name?of?predicate?PodFitsResources.PodFitsResourcesPred?=?"PodFitsResources"//?NoDiskConflictPred?defines?the?name?of?predicate?NoDiskConflict.NoDiskConflictPred?=?"NoDiskConflict"//?PodToleratesNodeTaintsPred?defines?the?name?of?predicate?PodToleratesNodeTaints.PodToleratesNodeTaintsPred?=?"PodToleratesNodeTaints"//?CheckNodeUnschedulablePred?defines?the?name?of?predicate?CheckNodeUnschedulablePredicate.CheckNodeUnschedulablePred?=?"CheckNodeUnschedulable"//?CheckNodeLabelPresencePred?defines?the?name?of?predicate?CheckNodeLabelPresence.CheckNodeLabelPresencePred?=?"CheckNodeLabelPresence"//?CheckServiceAffinityPred?defines?the?name?of?predicate?checkServiceAffinity.CheckServiceAffinityPred?=?"CheckServiceAffinity"//?MaxEBSVolumeCountPred?defines?the?name?of?predicate?MaxEBSVolumeCount.//?DEPRECATED//?All?cloudprovider?specific?predicates?are?deprecated?in?favour?of?MaxCSIVolumeCountPred.MaxEBSVolumeCountPred?=?"MaxEBSVolumeCount"//?MaxGCEPDVolumeCountPred?defines?the?name?of?predicate?MaxGCEPDVolumeCount.//?DEPRECATED//?All?cloudprovider?specific?predicates?are?deprecated?in?favour?of?MaxCSIVolumeCountPred.MaxGCEPDVolumeCountPred?=?"MaxGCEPDVolumeCount"//?MaxAzureDiskVolumeCountPred?defines?the?name?of?predicate?MaxAzureDiskVolumeCount.//?DEPRECATED//?All?cloudprovider?specific?predicates?are?deprecated?in?favour?of?MaxCSIVolumeCountPred.MaxAzureDiskVolumeCountPred?=?"MaxAzureDiskVolumeCount"//?MaxCinderVolumeCountPred?defines?the?name?of?predicate?MaxCinderDiskVolumeCount.//?DEPRECATED//?All?cloudprovider?specific?predicates?are?deprecated?in?favour?of?MaxCSIVolumeCountPred.MaxCinderVolumeCountPred?=?"MaxCinderVolumeCount"//?MaxCSIVolumeCountPred?defines?the?predicate?that?decides?how?many?CSI?volumes?should?be?attached.MaxCSIVolumeCountPred?=?"MaxCSIVolumeCountPred"//?NoVolumeZoneConflictPred?defines?the?name?of?predicate?NoVolumeZoneConflict.NoVolumeZoneConflictPred?=?"NoVolumeZoneConflict"//?EvenPodsSpreadPred?defines?the?name?of?predicate?EvenPodsSpread.EvenPodsSpreadPred?=?"EvenPodsSpread" )

常用的預選策略:

  • PodFitsHostPorts:如果 Pod 中定義了 hostPort 屬性,那么需要先檢查這個指定端口是否 已經被 Node 上其他服務占用了。

  • PodFitsHost:若 pod 對象擁有 hostname 屬性,則檢查 Node 名稱字符串與此屬性是否匹配。

  • PodFitsResources:檢查 Node 上是否有足夠的資源(如,cpu 和內存)來滿足 pod 的資源請求。

  • PodMatchNodeSelector:檢查 Node 的 標簽 是否能匹配 Pod 屬性上 Node 的 標簽 值。

  • NoVolumeZoneConflict:檢測 pod 請求的 Volumes 在 Node 上是否可用,因為某些存儲卷存在區域調度約束。

  • NoDiskConflict:檢查 Pod 對象請求的存儲卷在 Node 上是否可用,若不存在沖突則通過檢查。

  • MaxCSIVolumeCount:檢查 Node 上已經掛載的 CSI 存儲卷數量是否超過了指定的最大值。

  • CheckNodeMemoryPressure:如果 Node 上報了內存資源壓力過大,而且沒有配置異常,那么 Pod 將不會被調度到這個 Node 上。

  • CheckNodePIDPressure:如果 Node 上報了 PID 資源壓力過大,而且沒有配置異常,那么 Pod 將不會被調度到這個 Node 上。

  • CheckNodeDiskPressure:如果 Node 上報了磁盤資源壓力過大(文件系統滿了或者將近滿了), 而且配置異常,那么 Pod 將不會被調度到這個 Node 上。

  • CheckNodeCondition:Node 可以上報其自身的狀態,如磁盤、網絡不可用,表明 kubelet 未準備好運行 pod。如果 Node 被設置成這種狀態,那么 pod 將不會被調度到這個 Node 上。

  • PodToleratesNodeTaints:檢查 pod 屬性上的 tolerations 能否容忍 Node 的 taints。

  • CheckVolumeBinding:檢查 Node 上已經綁定的和未綁定的 PVCs 能否滿足 Pod 對象的存儲卷需求。

打分策略如下:

  • SelectorSpreadPriority:盡量將歸屬于同一個 Service、StatefulSet 或 ReplicaSet 的 Pod 資源分散到不同的 Node 上。

  • InterPodAffinityPriority:遍歷 Pod 對象的親和性條目,并將那些能夠匹配到給定 Node 的條目的權重相加,結果值越大的 Node 得分越高。

  • LeastRequestedPriority:空閑資源比例越高的 Node 得分越高。換句話說,Node 上的 Pod 越多,并且資源被占用的越多,那么這個 Node 的得分就會越少。

  • MostRequestedPriority:空閑資源比例越低的 Node 得分越高。這個調度策略將會把你所有的工作負載(Pod)調度到盡量少的 Node 上。

  • RequestedToCapacityRatioPriority:為 Node 上每個資源占用比例設定得分值,給資源打分函數在打分時使用。

  • BalancedResourceAllocation:優選那些使得資源利用率更為均衡的節點。

  • NodePreferAvoidPodsPriority:這個策略將根據 Node 的注解信息中是否含有 scheduler.alpha.kubernetes.io/preferAvoidPods 來 計算其優先級。使用這個策略可以將兩個不同 Pod 運行在不同的 Node 上。

  • NodeAffinityPriority:基于 Pod 屬性中 PreferredDuringSchedulingIgnoredDuringExecution 來進行 Node 親和性調度。你可以通過這篇文章 Pods 到 Nodes 的分派 來了解到更詳細的內容。

  • TaintTolerationPriority:基于 Pod 中對每個 Node 上污點容忍程度進行優先級評估,這個策略能夠調整待選 Node 的排名。

  • ImageLocalityPriority:Node 上已經擁有 Pod 需要的 容器鏡像 的 Node 會有較高的優先級。

  • ServiceSpreadingPriority:這個調度策略的主要目的是確保將歸屬于同一個 Service 的 Pod 調度到不同的 Node 上。如果 Node 上 沒有歸屬于同一個 Service 的 Pod,這個策略更傾向于將 Pod 調度到這類 Node 上。最終的目的:即使在一個 Node 宕機之后 Service 也具有很強容災能力。

  • CalculateAntiAffinityPriorityMap:這個策略主要是用來實現pod反親和。

  • EqualPriorityMap:將所有的 Node 設置成相同的權重為 1。

自定義調度器

除了 kubernetes 自帶的調度器,考慮到實際環境中的各種復雜情況,kubernetes 的調度器采用插件化的形式實現,可以方便用戶進行定制或者二次開發,我們可以自定義一個調度器并以插件形式和 kubernetes 進行集成。你也可以編寫自己的調度器。通過 spec:schedulername 參數指定調度器的名字,可以為 pod 選擇某個調度器進行調度。

kube-scheduler在啟動的時候可以通過?--policy-config-file參數來指定調度策略文件,我們可以根據我們自己的需要來組裝Predicates和Priority函數。選擇不同的過濾函數和優先級函數、控制優先級函數的權重、調整過濾函數的順序都會影響調度過程。

比如下面的 pod 選擇 test-my-scheduler 進行調度,而不是默認的 default-scheduler:

apiVersion:?v1 kind:?Pod metadata:name:?test-schedulerlabels:name:?testscheduler-example spec:schedulername:?test-my-schedulercontainers:-?name:?pod-with-second-annotation-containerimage:?gcr.io/google_containers/pause:2.0

調度器的編寫請參考 kubernetes 默認調度器的實現,最核心的內容就是讀取 apiserver 中 pod 的值,根據特定的算法找到合適的 node,然后把調度結果會寫到 apiserver。

官方給出的范例:

#!/bin/bash SERVER='localhost:8001' while?true; dofor?PODNAME?in?$(kubectl?--server?$SERVER?get?pods?-o?json?|?jq?'.items[]?|?select(.spec.schedulerName?==?"my-scheduler")?|?select(.spec.nodeName?==?null)?|?.metadata.name'?|?tr?-d?'"') ;doNODES=($(kubectl?--server?$SERVER?get?nodes?-o?json?|?jq?'.items[].metadata.name'?|?tr?-d?'"'))NUMNODES=${#NODES[@]}CHOSEN=${NODES[$[?$RANDOM?%?$NUMNODES?]]}curl?--header?"Content-Type:application/json"?--request?POST?--data?'{"apiVersion":"v1",?"kind":?"Binding",?"metadata":?{"name":?"'$PODNAME'"},?"target":?{"apiVersion":?"v1",?"kind" :?"Node",?"name":?"'$CHOSEN'"}}'?http://$SERVER/api/v1/namespaces/default/pods/$PODNAME/binding/echo?"Assigned?$PODNAME?to?$CHOSEN"donesleep?1 done

推薦閱讀
  • 實操來了!一文告訴你如何用 Streamlit 和 Heroku 開發 Web

  • 避坑!使用 Kubernetes 最易犯的 10 個錯誤

  • 雷軍:4G 手機已清倉,全力轉 5G;QQ音樂播放中途插語音廣告引熱議;Wine 5.9 發布 | 極客頭條

  • 15 歲黑進系統,發挑釁郵件意外獲 Offer,不惑之年捐出全部財產,Twitter CEO 太牛了!

  • 必讀!53個Python經典面試題詳解

  • 贈書 | 1月以來 Tether 增發47億 USDT,美元都去哪兒了?

真香,朕在看了!

總結

以上是生活随笔為你收集整理的Kubernetes 是如何调度的?的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。