vpa updater 源碼分析

1. updater整體邏輯

updater整體邏輯是比較簡單的琐簇。

(1)定義了一個NewUpdater的對象

(2)然后每隔1分鐘,執(zhí)行NewUpdater.RunOnce

1.1 updater參數(shù)

updater輪轉周期碉怔,默認是1分鐘
updaterInterval = flag.Duration("updater-interval", 1*time.Minute, `How often updater should run`)

rs最小可用的副本數(shù)酌儒。比如默認是2表示弯予,如果一個rs當前只有2個副本可用肛跌,本輪是不會驅逐的,保障rs服務的可用性
minReplicas = flag.Int("min-replicas", 2, `Minimum number of replicas to perform update`)

pod每輪的驅逐比例
evictionToleranceFraction = flag.Float64("eviction-tolerance", 0.5,`Fraction of replica count that can be evicted for update, if more than one pod can be evicted.`)

驅逐限速郑临,這里用了令牌桶算法栖博,就個就是令牌桶的QPS。如果是0或者-1表示不限速厢洞,默認是不限速
evictionRateLimit = flag.Float64("eviction-rate-limit", -1,`Number of pods that can be evicted per seconds. A rate limit set to 0 or -1 will disable the rate limiter.`)

令牌桶的burst大小
evictionRateBurst = flag.Int("eviction-rate-burst", 1, `Burst of pods that can be evicted.`)

暴露Prometheus metrics指標的地址
address = flag.String("address", ":8943", "The address to expose Prometheus metrics.")

是否檢驗AdmissionControllerStatus仇让。如果開啟的話,updater必須等
useAdmissionControllerStatus = flag.Bool("use-admission-controller-status", true,
      "If true, updater will only evict pods when admission controller status is valid.")

vpa作用的命名空間躺翻,默認是所有命名空間
namespace          = os.Getenv("NAMESPACE")
vpaObjectNamespace = flag.String("vpa-object-namespace", apiv1.NamespaceAll, "Namespace to search for VPA objects. Empty means all namespaces will be used.")
)

1.2 NewUpdater結構體對象

// NewUpdater creates Updater with given configuration
func NewUpdater(
    cgClient dynamic.Interface,                          // 為了操作cgroups資源丧叽,增加的dynamic客戶端
    cgGvr schema.GroupVersionResource,                   // cgroups的 gvr
    kubeClient kube_client.Interface,                   
    vpaClient *vpa_clientset.Clientset,                  
    minReplicasForEvicition int,                        
    evictionRateLimit float64,
    evictionRateBurst int,
    evictionToleranceFraction float64,
    useAdmissionControllerStatus bool,
    statusNamespace string,
    recommendationProcessor vpa_api_util.RecommendationProcessor,   //  處理推薦資源相關的process,在vertical-pod-autoscaler/pkg/utils/vpa/capping.go
    evictionAdmission priority.PodEvictionAdmission,                 // 默認為空
    selectorFetcher target.VpaTargetSelectorFetcher,                 // selector相關
    priorityProcessor priority.PriorityProcessor,                    // 驅逐優(yōu)先級處理公你。會更加資源diff進行過濾
    namespace string,
) (Updater, error) {
    evictionRateLimiter := getRateLimiter(evictionRateLimit, evictionRateBurst)
    factory, err := eviction.NewPodsEvictionRestrictionFactory(kubeClient, minReplicasForEvicition, evictionToleranceFraction)
    if err != nil {
        return nil, fmt.Errorf("Failed to create eviction restriction factory: %v", err)
    }
    return &updater{
        cgClient:                     cgClient,
        cgGvr:                        cgGvr,
        vpaLister:                    vpa_api_util.NewVpasLister(vpaClient, make(chan struct{}), namespace),
        podLister:                    newPodLister(kubeClient, namespace),
        eventRecorder:                newEventRecorder(kubeClient),
        evictionFactory:              factory,
        recommendationProcessor:      recommendationProcessor,
        evictionRateLimiter:          evictionRateLimiter,
        evictionAdmission:            evictionAdmission,
        priorityProcessor:            priorityProcessor,
        selectorFetcher:              selectorFetcher,
        useAdmissionControllerStatus: useAdmissionControllerStatus,
        statusValidator: status.NewValidator(
            kubeClient,
            status.AdmissionControllerStatusName,
            statusNamespace,
        ),
    }, nil
}


1.3 updater流程

每隔1分鐘進行以下的運行邏輯:

  1. 獲取所有的vpa, 并進行遍歷踊淳,對于每個vpa而言,執(zhí)行以下步驟

    1.1 如果vpa.model != auto 或者vpa.model != recreate, 直接跳過這個vpa

    1.2 根據(jù)vpa對應的selector, 獲取所有的pods陕靠,假設為 allPods

    1.3 從allPods中過濾deletionTimestamp != nil 的pods, 假設為 activesPods

    1.4 從activesPods中過濾可以進行驅逐的pod, 假設為canEvictedPods. 判斷邏輯如下:

    • updater啟動時有兩個參數(shù):defaultUpdateThreshold = 0.10迂尝。podLifetimeUpdateThreshold = time.Hour * 12

      含義為:

      如果一個pod從開始運行到當前時間,沒有超過12小時(podLifetimeUpdateThreshold)剪芥,不能進行驅逐

      如果一個pod從資源改變在 0.1范圍內(nèi)垄开,不應該驅逐。這個0.1是 cpu + memory的和税肪。

    • 結合OOM事件溉躲,判斷pod是否應該Evict,這個目前待確定細節(jié)

  2. 經(jīng)過第一步益兄,得到一個map, key=vap, value= canEvictedPods (這是一個列表锻梳,表示需要驅逐的pod)

  3. 遍歷上訴map, 針對某個vpa進行以下邏輯判斷。

    updater啟動時還有兩個參數(shù)净捅,控制沒輪驅逐時pod的數(shù)量

    • evictionTolerance 表示當前沒輪驅逐的比例,默認0.5疑枯。 假設當前vpa對應的canEvictedPods有10個pod, 那么當前只會驅逐5個。
    • min-replica 表示rs最少可用的pod數(shù)量蛔六。例如一個rs 當前只有2個pod running, 就是前面滿足了驅逐條件神汹,到這里也不會驅逐庆捺。


熱升級調整的邏輯:

(1)修改 podLifetimeUpdateThreshold = 30s

(2)跳過canEvictedPods邏輯

2. updater驅逐邏輯如下:

每隔1分鐘進行以下的運行邏輯:

  1. 獲取所有的vpa, 并進行遍歷,對于每個vpa而言屁魏,執(zhí)行以下步驟

    1.1 如果vpa.model != auto 或者vpa.model != recreate, 直接跳過這個vpa

    1.2 根據(jù)vpa對應的selector, 獲取所有的pods滔以,假設為 allPods

    1.3 從allPods中過濾deletionTimestamp != nil 的pods, 假設為 activesPods

    1.4 從activesPods中過濾可以進行驅逐的pod, 假設為canEvictedPods. 判斷邏輯如下:

    • updater啟動時有兩個參數(shù):defaultUpdateThreshold = 0.10。podLifetimeUpdateThreshold = time.Hour * 12

      含義為:

      如果一個pod從開始運行到當前時間氓拼,沒有超過12小時(podLifetimeUpdateThreshold)你画,不能進行驅逐

      如果一個pod從資源改變在 0.1范圍內(nèi),不應該驅逐桃漾。這個0.1是 cpu + memory的和坏匪。

    • 結合OOM事件,判斷pod是否應該Evict撬统,這個目前待確定細節(jié)

  2. 經(jīng)過第一步适滓,得到一個map, key=vap, value= canEvictedPods (這是一個列表,表示需要驅逐的pod)

  3. 遍歷上訴map, 針對某個vpa進行以下邏輯判斷恋追。

    updater啟動時還有兩個參數(shù)凭迹,控制沒輪驅逐時pod的數(shù)量

    • evictionTolerance 表示當前沒輪驅逐的比例,默認0.5。 假設當前vpa對應的canEvictedPods有10個pod, 那么當前只會驅逐5個苦囱。
    • min-replica 表示rs最少可用的pod數(shù)量嗅绸。例如一個rs 當前只有2個pod running, 就是前面滿足了驅逐條件,到這里也不會驅逐撕彤。

2.1 總結

感覺驅逐邏輯遷移到cgroupManager可以如下:

(1)繼承上訴的步驟1鱼鸠,步驟2,因為是熱升級羹铅,所以不用關注步驟三(考慮min-replica )

(2)OOM事件會影響pod驅逐蚀狰,但是是熱升級的情況下感覺可以忽略

3.vpa的修改pod資源的邏輯

  • vap修改的都是pod的request值,但是limit值會按照比例進行擴縮

  • Deploy yaml中沒有指定limit职员,vpa也不會修改limit

  • vpa不會修改pod的QOS類型

舉例說明會更清楚一點:

場景1 deploy yaml中設置了requet, limit

假設deploy yaml中定義的資源為:(這里limit:request=2:1)

    resources:
      limits:
        cpu: 2
        memory: 2Gi
      requests:
        cpu: 1
        memory: 1Gi

而vpa推薦值為:cpu=25m mem=262144k造锅。那么這個pod實際運行時的request如下:

    resources:
      limits:                 //limit會改變,會維持limit:request=2:1的關系
        cpu: 50m
        memory: 500Mi
      requests:              // request采用的是vpa的值
        cpu: 25m
        memory: 262144k


場景2 pod yaml只中設置了requet沒有設置limit

假設pod yaml中定義的資源為:(這里沒有l(wèi)imit)

 resources:
      requests:
        cpu: 1
        memory: 1Gi

而vpa推薦值為:cpu=25m mem=262144k。那么這個pod實際運行時的request如下:

    resources:     
      requests:              // request采用的是vpa的值廉邑。也不會有l(wèi)imit
        cpu: 25m
        memory: 262144k

場景3 pod yaml沒有設置resources

假設pod yaml中定義沒有定義資源:(besteffort)

而vpa推薦值為:cpu=25m mem=262144k。那么這個pod實際運行時的request如下:

resources:     
  requests:              // request采用的是vpa的值倒谷。也不會有l(wèi)imit
    cpu: 25m
    memory: 262144k
?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末蛛蒙,一起剝皮案震驚了整個濱河市,隨后出現(xiàn)的幾起案子渤愁,更是在濱河造成了極大的恐慌牵祟,老刑警劉巖,帶你破解...
    沈念sama閱讀 206,378評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件抖格,死亡現(xiàn)場離奇詭異诺苹,居然都是意外死亡咕晋,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,356評論 2 382
  • 文/潘曉璐 我一進店門收奔,熙熙樓的掌柜王于貴愁眉苦臉地迎上來掌呜,“玉大人,你說我怎么就攤上這事坪哄≈式叮” “怎么了?”我有些...
    開封第一講書人閱讀 152,702評論 0 342
  • 文/不壞的土叔 我叫張陵翩肌,是天一觀的道長模暗。 經(jīng)常有香客問我,道長念祭,這世上最難降的妖魔是什么兑宇? 我笑而不...
    開封第一講書人閱讀 55,259評論 1 279
  • 正文 為了忘掉前任,我火速辦了婚禮粱坤,結果婚禮上隶糕,老公的妹妹穿的比我還像新娘。我一直安慰自己比规,他們只是感情好若厚,可當我...
    茶點故事閱讀 64,263評論 5 371
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著蜒什,像睡著了一般测秸。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上灾常,一...
    開封第一講書人閱讀 49,036評論 1 285
  • 那天霎冯,我揣著相機與錄音,去河邊找鬼钞瀑。 笑死沈撞,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的雕什。 我是一名探鬼主播缠俺,決...
    沈念sama閱讀 38,349評論 3 400
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼贷岸!你這毒婦竟也來了壹士?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 36,979評論 0 259
  • 序言:老撾萬榮一對情侶失蹤偿警,失蹤者是張志新(化名)和其女友劉穎躏救,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 43,469評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡盒使,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 35,938評論 2 323
  • 正文 我和宋清朗相戀三年崩掘,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片少办。...
    茶點故事閱讀 38,059評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡苞慢,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出凡泣,到底是詐尸還是另有隱情枉疼,我是刑警寧澤,帶...
    沈念sama閱讀 33,703評論 4 323
  • 正文 年R本政府宣布鞋拟,位于F島的核電站骂维,受9級特大地震影響,放射性物質發(fā)生泄漏贺纲。R本人自食惡果不足惜航闺,卻給世界環(huán)境...
    茶點故事閱讀 39,257評論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望猴誊。 院中可真熱鬧潦刃,春花似錦、人聲如沸懈叹。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,262評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽澄成。三九已至胧洒,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間墨状,已是汗流浹背卫漫。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留肾砂,地道東北人列赎。 一個月前我還...
    沈念sama閱讀 45,501評論 2 354
  • 正文 我出身青樓,卻偏偏與公主長得像镐确,于是被迫代替她去往敵國和親包吝。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 42,792評論 2 345

推薦閱讀更多精彩內(nèi)容