系列目錄html
目標讀者:前端
想要構建高可用應用的應用全部者,所以須要知道pod會發生哪些類型的中斷node
想要執行自動化(好比升級和自動擴容)的集羣管理員.web
pod不會自動消息,除非有人(多是一我的或者一個控制器)把它銷燬了,或者出現沒法避免的硬件或者系統軟件錯誤.api
咱們把這些稱做非自願的不可避免的應用中斷.網絡
如下是示例:工具
用於支撐節點的機會出現硬件故障翻譯
集羣管理員誤操做把VM(實例)刪除了code
虛擬機故障致使VM實例消失htm
kernel panic
因爲網絡分區致使集羣節點消失
因爲資源耗盡致使pod被驅離
除了資源耗盡外,其它狀況大部分讀者應該都很是熟悉,它們並非kubernetes特有的.
咱們稱其它的狀況爲自願中斷.這包括集羣管理員或者應用擁有者採起的動做.應用擁有者採起的典型動做有:
刪除了管理pod的deployment或者其它控制器
更新了deployment的pod模板致使重啓
直接刪除pod(好比誤刪除)
集羣管理員的動做有以下:
排幹node以便升級或修復
排幹一個node以便對集羣縮容
從節點中刪除一個pod以即可以作其它的事情
這些動做可能由集羣管理者直接觸發,或者自動觸發,或者有集羣服務提供者觸發
詢問集羣管理員或者雲服務提供商或者查詢文檔來肯定是否觸發了自願停止.若是以上都沒有發生,你能夠跳過建立Pod Disruption Budgets
注意:並不是全部的自願中斷都被
Pod Disruption Budgets
約束,好比刪除deployment或者pod會繞過Pod Disruption Budgets
如下是一些能夠減輕非自願中斷的辦法
確保pod請求須要的資源
若是你想要高可用,製做程序副本集
若是想要更高可用性,使用跨區域集羣部署應用
自願中斷的頻率根據實際狀況每每也是不一樣的.在一個基礎的集羣上,可能根本不會有自願的中斷.可是集羣管理員或者服務提供商可能會運行一些額外的服務致使自願中斷.好比滾動更新可能會致使自願中斷.一些自動集羣擴容爲了防止完整節點碎片化也會自願中斷.集羣管理員或者服務提供商應該用文檔把可能致使的自願中斷寫出來,以便查詢.
kubernetes提供了這樣一種特性,當高頻率自願中斷髮生時仍然可以保證集羣的高可用性,咱們稱之爲Disruption Budgets
Disruption Budgets
有些資料上翻譯爲中斷預算,可是更多的是沒有翻譯,你們只要知道它的大體意思就好了,這裏也不作翻譯
應用全部者能夠爲每一個應用建立一個PodDisruptionBudget(PDB)
對象.PDB限制一個包含副本集的集羣因爲自願中斷而同時宕掉的pod的個數.例如,一個基於仲裁投票的應用想要保證運行的副本數永遠不會低於某個數量以便仲裁.一個web前端想要保證運行中的副本數不會低於某一比例.
集羣管理員和服務提供商應當經過遵照Pod Disruption Budgets
的Eviction API而不是直接刪除pod或者deployment.例如可使用kubectl drain
當集羣管理員想經過kubectl drain
命令來排幹一個節點.命令會嘗試排幹節點機器上的全部pod.驅離請求可能會暫時被拒絕,命令會週期性的從新發送失敗請求直到全部pod都終止,或者達到了設定的超時時間.
PDB規定了副本集能夠容忍的副本集的數量(其實是能容忍的最小值),這是相對於它指望的數量而言的.好比一個有.spec.replicas: 5
的deployment但願在任什麼時候候都有五個副本,若是PDB容許有4個副本運行,則Eviction API
容許同一時刻有一個副本中斷,而不是2個.
指望的副本數量由pod控制器經過pod的.spec.replicas
計算得出,控制器經過.metadata.ownerReferences
被pod發現
PDB不能阻止非自願的中斷髮生,可是它們會被計入預算
因爲被刪除或者更新導到不可用的pod也會計入預算,可是控制器(好比deployment,stateful-set)滾動更新時不會被PDB限制,滾動更新致使的失敗會計入控制器的spec裏
當一個pod經過eviction API被驅離,它會優雅的停止(請看podspec裏的terminationGracePeriodSeconds
)
好比集羣有從node-1到node-3這樣的3個節點.集羣中運行着一些應用,其中一個有三個副本,叫做pod-a,pod-b和pod-c.此外還有一個無關的,包含PDB的pod稱做pod-x,它們的初始分佈狀況以下:
node-1 | node-2 | node-3 |
---|---|---|
pod-a available | pod-b available | pod-c available |
pod-x available |
同一副本集的三個節點是一個deployment的一部分,它們共享一個PDB,要求它們三個中至少有2個同時運行着.
假如集羣管理員想要重啓節點以便修復一個內核bug,集羣管理員首先嚐試經過kubectl drain
命令來排幹node-1節點.命令會嘗試把pod-a和pod-x驅離節點node-1.命令立刻執行成功,上面的pod同時進入terminating
狀態.如今集羣處於以下狀態:
node-1 draining | node-2 | node-3 |
---|---|---|
pod-a terminating | pod-b available | pod-c available |
pod-x terminating |
deployment發現其中一個節點終止了.所以它建立了一個替代節點叫做pod-d,因爲node-1被封鎖,所以它會落到其它節點.其它的控制器也會建立一個pod-y來替代pod-x
注意,對一StatefulSet,pod-a可能叫做pod-1,須要在被替代以前徹底終止,它仍然叫做pod-a,可是PID可能不一樣了.除此以外(pod的名字的區別),這個例子也適用於StatefulSet.
如今集羣處於以下狀態:
node-1 draining | node-2 | node-3 |
---|---|---|
pod-a terminating | pod-b available | pod-c available |
pod-x terminating | pod-d starting | pod-y |
在某一個時間點,node-a上的節點被終止,如今集羣的狀態以下
node-1 drained | node-2 | node-3 |
---|---|---|
pod-b available | pod-c available | |
pod-d starting | pod-y |
此時,若是一個沒有耐心的集羣管理員嘗試排幹node-2或者node-3,排幹命令會被阻止,由於只有兩個可用的節點,它的PDB要求至少運行2個,過一段時間,pod-d變得可用
node-1 drained | node-2 | node-3 |
---|---|---|
pod-b available | pod-c available | |
pod-d available | pod-y |
此時,若是集羣管理員嘗試排幹node-2,排幹命令會以必定順序驅離上面的兩個pod,好比說先是pod-b而後是pod-d,它會成功驅離pod-b.可是當嘗試驅離pod-d的時候會被拒絕,由於這會致使deployment只有一個可用pod
pod-b被驅離後並不會立刻在其它節點上落地開始工做,也就是這個節點的替代節點並不能立刻工做,此時若是再驅離pod-d會致使只有pod-c是可用的,所以會被拒絕.
deployment建立了一個pod-b的替代叫做pod-e,因爲集羣沒有足夠資源來調度pod-e所以此時drain會再入陷入阻塞.集羣最終的狀態以下:
node-1 drained | node-2 | node-3 | no node |
---|---|---|---|
pod-b available | pod-c available | pod-e pending | |
pod-d available | pod-y |
此時,集羣管理員須要添加一個節點來讓升級繼續.
你能夠看到基於如下緣由,kubernetes怎樣控制中斷的速率:
集羣須要多少個副本
優雅地停止一個實例須要多長時間
一個新的實例啓動須要多長時間
控制器的類型
集羣資源容量
一般,把集羣管理者和應用擁有者看做是對對方知之甚少不一樣的角色是有用的.這種職責分離在如下情形是有意義的:
多個開發團隊使用同一個集羣,這時候有一箇中立的專家角色
當一些第三方工具或者服務被用來作集羣的自動化管理工做.
若是你是集羣管理員,因爲節點或者系統軟件升級,你可能須要對集羣的全部節點執行可能產生中斷的動做,有如下選項:
升級過程當中接受宕機時間
故障轉移到一個完整的副本集羣中.這可以保證沒有宕機時間,可是可能須要花費高價錢來複制節點和花費人力來編排切換
使用能容忍中斷的程序和使用PDB
沒有宕機時間
最小量資源複製
容許更多的集羣自動化管理
編寫能容忍中斷的程序是頗有技巧的,可是容忍中斷的工做很大部分是與支持自動擴容和容忍非自願中斷是重疊的