GitHub工程團隊執行了一個稱作Cyclops的專案,實作並且更新許多方法,改進大型單一儲存庫的效能,減少推送失敗,並且提高單一儲存庫更新速率至少一個量級,使得當前架構仍有多年的發展空間,來應付目前最大的單一儲存庫成長。

GitHub上目前已經有超過2億個程式碼儲存庫,並且服務超過5,600萬使用者,官方提到,像GitHub這麼大的系統,有些問題可能要在部分極限情況才會出現,像是在每天有上千開發者對同一儲存庫更新時。幾個擁有龐大單一儲存庫的用戶向GitHub反應,他們儲存庫的效能問題,影響他們推送操作,而GitHub的github/github儲存庫,本身也是個龐大的單一儲存庫,甚至連GitHub自己偶爾也會遇到推送失敗。

為此GitHub展開了調查行動,除了與內部團隊,他們也與用戶合作,共同了解並最佳化他們在GitHub上的操作,經過了一些調整,不正常的推送失敗仍然存在,因此GitHub決定以專案處理這個問題,創建了Cyclops專案,跨Git系統部門合作,包括Git儲存、協定和客戶端團隊,並與上游Git專案貢獻者和工程師,共同尋找問題的解決方案。

GitHub首先改善了儲存庫維護工作,在預設情況下,GitHub每執行50次git push操作,或是在收到40 MB解壓縮檔案後,系統就會執行一次儲存庫維護例程,以更新packfile並且維持複製和擷取的效能,並清理儲存庫中的複製資料,而維護時間會依儲存庫的大小而有不同,可能需要數秒鐘到數分鐘的時間。

對大量開發人員共同使用的大型單一儲存庫來說,不需要太久的時間,就能累積50次推送操作,因此在開發人員持續推送更新的同時,儲存庫也會頻繁地進行維護工作,有些儲存庫無法在最大時間限制內完成維護工作,使得推送和參照更新效能受影響,而現在GitHub透過改進git repack和重新嘗試維護排程,將維護故障機率降低接近零。

大部分的維護故障是由於git repack指令造成,在儲存庫維護期間,GitHub系統會執行git repack來壓縮鬆散物件,而為了將一組物件壓縮在一起,Git需要尋找相對應的物件,部分物件不是以完整的內容儲存,而是儲存其他相關物件的增量內容,尋找這些增量內容需要花費時間,因此將每個物件互相比較很快地變得不可行。

Git透過在打包物件的陣列,使用滑動視窗演算法來搜尋增量與基礎物件配對,這樣的啟發式方法,可以迅速篩掉視窗中的部分增量候選物件,但是缺點是必須花費較多的CPU資源進行比較,GitHub調校了一個最佳參數,以限制高成本運算的次數,減少花費的CPU時間,並且略增加生成的packfile大小,這項改進消除了幾乎所有維護故障。

在過去,當儲存庫因為特定原因導致維護失敗,系統在7日內不會再次執行維護,但是現在的單一儲存庫已經無法等待這麼久的時間,因此GitHub對特定類型的維護失敗,通常是因為在維護期間,所產生的大量推送流量造成的失敗,加入一種偽失敗狀態,在這種狀態,儲存庫會每4小時重新嘗試維護一次,最多3次,而這消除了剩餘的維護故障。

另外,由於早前GitHub對伺服器的推送限制,也產生了許多推送相關的錯誤。官方解釋,因為GitHub是一個多租戶服務,為了確保來自單一用戶的操作,不會壟斷伺服器上的資源,影響其他用戶的使用,因此特別設定參數,減慢推送操作的速度,但經過GitHub的調查,現在系統架構已經夠強健,即便立即處理所有推送操作,也不會產生任何問題,於是GitHub現在刪除了相關程式碼,進而減少了許多與推送相關的錯誤。

經過了這些更改,大型單一儲存庫用戶,幾乎不再發生推送失敗,官方提到,其中有一些故障是因為隨機的網際網路問題所引起,這超出GitHub可控制範圍。GitHub也仍在處理一些剩餘的故障問題,同時繼續提升GitHub的執行速度,官方還提到,他們正在分解使用Ruby語言開發的單體程式,並且以Go重新編寫新的微服務程式,以提高儲存庫效能。


熱門新聞

Advertisement