引發Pod驅逐的原因

語言: CN / TW / HK

最近在處理一個專案的k8s叢集時,頻繁遇到pod在不同節點驅逐的現象。

如此頻繁的驅逐引發了"節點狀態振盪",是某node節點或多個Node節點出發了"驅逐訊號"造成的。

叢集由1個master和4臺node組成,經仔細檢查發現存在如下問題:

  1. 其中master-node節點和另外3臺node節點核心為3.10版本,只有一臺node節點為5.4的新版核心
  2. 其中一臺node節點檔案控制代碼數沒有修改為,1024
  3. 五臺的磁碟空間均比較小,但是經查有3臺可以通過邏輯卷擴容
  4. 磁碟佔用率,已經發現有2臺出現磁碟佔用率超過80%的現象
    kubelet 有如下所示的預設硬驅逐閾值:
    memory.available<100Mi
    nodefs.available<10%
    nodefs.inodesFree<5%
    imagefs.available<15%

    由上可見,檔案控制代碼數過小和磁碟空間使用過高都會觸發閾值,核心版本過低可能造成資源分配不平衡及記憶體佔用高(記憶體洩漏風險)也會引發驅逐。

    如上逐一解決後,觀察一週時間,至今還沒有發生驅逐現象

    總結:在叢集規模較小的情況下,要充分保障各資源情況,否則發生驅逐後到其它節點仍然無法滿足資源需求,會引起節點震盪。叢集機器數量較多,被驅逐到其它節點上的pod,在多臺機器上資源不滿足的概率較小。

    以下是一些相關說明:

    驅逐訊號

    什麼是驅逐訊號呢?簡單理解就是,kubelet什麼時候什麼場景下開始驅逐pod呢?總的有幾個參考值吧,這就是驅逐訊號,k8s提供了以下幾種驅逐訊號

驅逐訊號 描述

memory.available    node.status.capacity[memory] - node.stats.memory.workingSet
nodefs.available    node.stats.fs.available
nodefs.inodesFree   node.stats.fs.inodesFree
imagefs.available   node.stats.runtime.imagefs.available
imagefs.inodesFree  node.stats.runtime.imagefs.inodesFree
memory.available是針對記憶體資源,其餘4個驅逐訊號都是針對磁碟空間的。

上面的每個訊號都支援字面值或百分比的值。基於百分比的值的計算與每個訊號對應的總容量相關。

memory.available 的值從 cgroupfs 獲取,而不是通過類似 free -m 的工具。 這很重要,因為 free -m 不能在容器中工作

kubelet 只支援兩種檔案系統分割槽。

nodefs 檔案系統,kubelet 將其用於卷和守護程式日誌等。

imagefs 檔案系統,容器執行時用於儲存映象和容器可寫層。

imagefs 可選。kubelet 使用 cAdvisor 自動發現這些檔案系統。 kubelet 不關心其它檔案系統。當前不支援配置任何其它型別。 例如,在專用 filesytem 中儲存卷和日誌是 不可以 的。

我們可以想想worker節點中什麼最耗磁碟空間,無非也就下面幾項

映象檔案:有的很大,幾百M。每次更新deployment,都會拉取新的映象,長此以往,不通版本的映象肯定要消耗很大磁碟空間的。imagefs檔案系統正是管理這些映象的,如果我們配置的驅逐訊號中有imagefs.available或者imagefs.inodesFree,且觸發驅逐閥值後,k8s將會主動清理一些沒有使用的版本映象,以此來釋放更多的磁碟空間。
日誌:隨著應用的長時間執行,日誌會越來越龐大,volume不管你使用的是emptyDir,hostPath,還是nfs,clustersfs,都會將日誌儲存在節點上的,佔用worker節點的磁碟空間也將會越來越大。docker中的日誌分為倆種,docker主程序的標準輸出日誌和專案中使用者產生的檔案日誌,正好對應nodefs檔案系統中的卷和守護程式日誌。如果我們配置的驅逐訊號中有nodefs.available或者nodefs.inodesFree且觸發驅逐閥值後,k8s將會清理這些日誌,清理這些的日誌的方式只能是驅逐pod了。

軟碟機逐閾值

使用一對由驅逐閾值和寬限期組成的配置對。在寬限期內持續超過閥值則進行驅逐。比如下面這倆行配置,表示的意義是當節點的memory.available小於500Mi,且在1分30內持續小於500Mi時,開啟觸發驅逐。下面這倆行是成對出現的。

軟碟機逐閾值使用關鍵字eviction-soft

--eviction-soft=memory.available<500Mi
--eviction-soft-grace-period=memory.available=1m30s

硬驅逐閾值

相對於軟碟機逐閾值,區別就是沒有緩衝時間,只要觸發驅逐訊號,就立即開始驅逐而不是優雅的終止。

硬驅逐閾值使用關鍵字eviction-hard。比如下面例子

--eviction-hard=memory.available<500Mi,nodefs.available<20%