by kimminjava
使用kubernetes爲測試工具Gatling進行大規模壓測,壓測期間發現Jenkins調度壓測實例較慢,單批幾百實例須要十分鐘左右也不能保證完整調度。git
結合Jenkins Master源碼 和Jenkins Kubernetes插件源碼,對調度進行了細節的優化。調優過程當中目標實例個數都設爲300,調優後能夠大致上容許一分鐘內從Jenkins Master調度完畢。若是目標實例個數線性增長,調度的時間也不會有明顯變化。
通過調優後,目前生成動態Jenkins Slave主要的耗時瓶頸是在Jenkins Master的任務隊列的填充上,目前可能已經將消費者端監聽隊列而且計算期待實例個數的算法調整到了最aggressive的策略,可是生產者喂Queue的效率低下致使消費者出於飢餓狀態。github
繼續對Queue生產者端進行調優,應該須要修改Jenkins Master的源碼而且會對正常的構建任務進Queue產生未知影響,可能短時間不會考慮。算法
若是要對Jenkins Master進行調優,能夠從如下幾點着手:異步
大致上,Kubernetes插件只是實現了Jenkins Master裏Cloud類的provision接口和ComputerLauncher的launch接口,provision接口是Jenkins Master想要生成一個Slave的時候調用的,那麼Kubernetes插件只奉命作事和Kubernetes APIserver通訊按照Pod Template建立一個用做Slave的Pod進行工做,launch接口是用來讓Jenkins Master的啓動一個Slave的,可是因爲Kubernetes裏面容器實例的建立是異步的過程,因此插件裏launch只是在作輪詢Pod狀態來等待Pod建立完畢結束launch的過程。Kubernetes的Scale效率遠大於目前壓測實例的建立效率,因此咱們定位瓶頸也是從Jenkins Master和Kubernetes插件上開始。工具
按從消費者到生產者的順序進行分析,首先咱們把Jenkins Master計算集羣負載的快照間隔hudson.model.LoadStatistics.clock
從10秒縮短到了2秒,btw,Jenkins Master防守式地用時間戳快照間隔最小限定到了1秒,可是爲了可能更快的進行調度。咱們而且且將進行provision的間隔hudson.slaves.NodeProvisioner.recurrencePeriod
從6秒縮短到了2秒,這裏參數比較危險的是當provision間隔小於快照間隔,可能致使短期內無限建立slave的bug。性能
Jenkins服務啓動後的第一次provision是由參數hudson.slaves.NodeProvisioner.initialDelay
決定的,這個參數是爲了確保讓靜態的Jenkins Slave和Master創建起來鏈接,因爲咱們使用的Kubernetes插件其實並不存在雙向的通訊,因此咱們把初始的調度delay從100秒縮小到了20秒。測試
hudson.model.LoadStatistics.decay用於EMA抑制負載的抖動,這個參數本來的意義是用於抑制評估master負載的抖動,而且容許給使用者人肉反應時間來終止一些畸形的Job。默認decay是0.9。好比上一次快照負載爲1,那麼下次入隊列的快照評分就會是**_1 + (1-0.9)*當前負載_**,咱們把快照decay設成了0.1,容許負載大幅度變化。從而每次provision的時候,Jenkins Master評估的負載就是在當前儘量真實的負載之上評估的新實例個數。這個也是主要提高調度性能的參數之一。優化
hudson.slaves.NodeProvisioner.MARGIN_DECAY hudson.slaves.NodeProvisioner.MARGIN hudson.slaves.NodeProvisioner.MARGIN0
如上圖所示,把調整這裏的參數使負載作整數對齊的時候儘可能向上對齊,從而多provision一個slave,以此來提升效率。插件
另外發現一處可能的BUG,提交給了社區。