在kubernetes集群中,每個node節點(又稱minion)上都會啟動乙個kubelet服務進行。該程序用於處理master節點下發到本節點的任務,管理pod及pod中的容器。每個kubelet程序會在api server上註冊節點自身資訊,定期向master節點匯報節點資源的使用情況,並通過cadvise監控容器和節點資源。
此原始碼分析基於 k8s 1.14.6若想解讀 kubelet 原始碼,首先我們需要了解 kubelet 的主要架構及元件。
kubelet 的主函式入口在cmd/kubelet/kubelet.go
中,啟動**很簡潔:
func main()
}
解析引數,載入當前flag,對引數的合法性進行判斷。flag 包含兩種:
構造 cobra.command 物件,此物件用於執行使用者輸入的命令列互動。此物件結構體為
,
}
其中的run
則是用於具體執行使用者命令的函式,這個函式的流程也就是 kubelet的主流程,建立 kubelet 物件,建立各種服務。
這一部分解析一下 run 函式。首先我們需要了解兩個比較重要的配置結構體kubeletflags
kubeletconfig.kubeletconfiguration
:
啟動流程如下:
新建乙個watch的功能,主要是用來watch kubelet的配置檔案是否改變,如果已經改變,那麼就重新load kubelet的配置檔案 用的是kubernetes常用到的controller,也就是informer的架構,watch configmap物件
> controller 相關**在 `pkg/kubelet/kubeletconfig/controller.go`中 *//todo 介紹下 controller informer 機制*
構造 kubelet server物件,
kubelet server 物件由 kubelet 各種配置組成,其結構體如下:
type kubeletserver struct
根據 server 建立kubeletdeps
物件,它並不會啟動任何程序,僅返回適合執行的依賴項或錯誤。這個是比較重要的部分,其結構體為:
kubelet.dependencies,
volumeplugins: probevolumeplugins(),
dynamicpluginprober: getdynamicpluginprober(s.volumeplugindir, pluginrunner),
tlsoptions: tlsoptions}, nil
我們可以看到,返回的這些包含底層docker 客戶端、掛載器等。其實就是可以供 server 使用的工具包。
執行 run 函式,啟動 kubelet。注意此 run 函式並非上文的 command 中的 run
func run(s *options.kubeletserver, kubedeps *kubelet.dependencies, stopch
// 這裡啟動 kubelet
if err := run(s, kubedeps, stopch); err != nil
return nil
}
通過setfrommap
設定 kubelet 的 feature gate
驗證初始化的 server
註冊端點/configz
獲取並配置各種客戶端,包括:
構建認證器authinte***ce
,呼叫buildauth
func buildauth(nodename types.nodename, client clientset.inte***ce, config kubeletconfig.kubeletconfiguration) (server.authinte***ce, error)
authenticator, err := buildauthn(tokenclient, config.authentication)
if err != nil
attributes := server.newnodeauthorizerattributesgetter(nodename)
authorizer, err := buildauthz(sarclient, config.authorization)
if err != nil
return server.newkubeletauth(authenticator, attributes, authorizer), nil
}
構建cadvisorinte***ce
,主要用於監控功能,包括資訊有
type inte***ce inte***ce
kubereserved 包含節點的相關資源,包括 cpu memory pid數量等
systemreserved 節點資源,支援 cpu memory
experimentalqosreserved 即--qos-reserve-requests引數
devicepluginenabled(deviceplugins feature gate)
最終構建的結構體為:
kubedeps.containermanager, err = cm.newcontainermanager(
kubedeps.mounter,
kubedeps.cadvisorinte***ce,
cm.nodeconfig,
qosreserved: *experimentalqosreserved,
experimentalcpumanagerpolicy: s.cpumanagerpolicy,
experimentalcpumanagerreconcileperiod: s.cpumanagerreconcileperiod.duration,
experimentalpodpidslimit: s.podpidslimit,
enforcecpulimits: s.cpucfsquota,
cpucfsquotaperiod: s.cpucfsquotaperiod.duration,
},s.failswapon,
devicepluginenabled,
kubedeps.recorder)
進行許可權驗證,需要以 uid 為 0 的使用者啟動。
呼叫runkubelet
啟動 kubelet 程序
呼叫 runkubelet
runkubelet 主要流程:
獲取主機名
建立並初始化 event recorder
獲取以下資源(均讀取自kubeletflags
):
若設定runonce
引數,則只拉取一次容器組配置,並在啟動容器組後退出,否則將以 server 形式保持
至此,kubelet 整體的啟動流程完畢,進入無限迴圈中,實時同步不同元件的狀態。同時也對埠進行監聽,響應 http 請求。
kubelet啟動pod原始碼分析(二)
func kl kubelet syncloopiteration configch syncch type podrecord struct 很簡單,就是記錄當前pod狀態和之前記錄狀態的兩個屬性。func g genericpleg relist 更新本地快取 g.updatecache pod...
Zookeeper 原始碼分析 啟動
本文主要介紹了zookeeper啟動的過程 執行zkserver.sh start命令可以啟動zookeeper。入口的main函式在類中quorumpeermain。main函式主要呼叫了runfromconfig函式,建立了 quorumpeer物件,並且呼叫了start函式,從而啟動了zook...
原始碼分析SpringBoot啟動
none,不是web專案 servlet,是web專案 reactive 之後新加的,響應式專案 private collectiongetspringfactoriesinstances classtype,class parametertypes,object.args 首先得到classloa...