天天看點

阿裡巴巴的全鍊路壓測

雙十一從 2009 誕生到現在,2013 年絕對是一個分水嶺。

為什麼這麼說?因為 2013 有了全鍊路壓測。

每年的 11 月 11 日 00:00:00,阿裡巴巴集團最緊張激動的時刻到來了。多收檔的熱情這一刻開始爆發,反映到數字上是去年雙十一今人的記錄:24 小時交易額 1012 億,交易建立峰值 17.2w;而在二進制世界裡面,則是極短時間内如海嘯般湧入的超大規模流量。

流量洪峰的殺傷力,曾在 2011 年和 2012 年給技術團隊留下了午夜驚魂的難忘回憶。然而随着全鍊路壓測的登場,它改變了阿裡巴巴對應流量洪峰的态度和方式,也一次次重新整理中國網際網路世界的紀錄。

為什麼需要容量規劃?

阿裡巴巴有着非常豐富的業務形态,每種業務都由一系列不同的業務系統來提供服務,每個業務系統都分布式地部署在不同的機器上。随着業務的發展,特别是在大促營銷等活動場景下(比如雙 11),需要為每個業務系統準備多少機器對于阿裡巴巴技術團隊來說是一大難題。“容量規劃”正是為解決這個難題而誕生,容量規劃的目的在于讓每一個業務系統能夠清晰地知道:什麼時候應該加機器、什麼時候應該減機器?雙 11 等大促場景需要準備多少機器,既能保障系統穩定性、又能節約成本?

阿裡巴巴的全鍊路壓測

容量規劃四步走

在雙 11 等大促場景的準備過程當中,容量規劃一般分為四個階段:

  • 業務流量預估階段:通過曆史資料分析未來某一個時間點業務的通路量會有多大;
  • 系統容量評估階段:初步計算每一個系統需要配置設定多少機器;
  • 容量的精調階段:通過全鍊路壓測來模拟大促時刻的使用者行為,在驗證站點能力的同時對整個站點的容量水位進行精細調整;
  • 流量控制階段:對系統配置限流門檻值等系統保護措施,防止實際的業務流量超過預估業務流量的情況下,系統無法提供正常服務。

在第一個階段當中,通過合适的預測算法和豐富的曆史資料,通常能夠比較準确地預估業務的通路量。即使在第一階段預估的業務通路量跟實際的存在誤差,通過第四階段的流量控制也能夠確定站點始終處于良好的服務狀态。做完業務通路量的預估之後,容量規劃進入第二階段,為系統進行容量的初步評估。如何通過精準的容量評估,用最小的成本來支撐好預估的業務量是這個階段的核心問題。

要計算一個系統需要多少台機器,除了需要知道未來的業務調用量之外,還有一個更重要的變量,就是單台機器的服務能力。擷取單台機器的服務能力在阿裡巴巴是通過單機壓測的方式來擷取。在阿裡巴巴,為了精準地擷取到單台機器的服務能力,壓力測試都是直接在生産環境進行,這有兩個非常重要的原因:單機壓測既需要保證環境的真實性,又要保證流量的真實性。否則擷取到的單台機器服務能力值将會有比較大的誤差,影響到整個容量規劃的準确性。

生産環境進行單台機器壓力測試的方式主要分為 4 種:

阿裡巴巴的全鍊路壓測

模拟請求:通過對生産環境的一台機器發起模拟請求調用來達到壓力測試的目的

模拟請求的實作比較簡單,也有非常多的開源或者商業工具可以來做請求模拟,比如 apache ab、webbench、httpload、jmeter、loadrunner。通場情況下,新系統上線或者通路量不大的系統采用這種方式來進行單機壓測。模拟請求的缺點在于,模拟請求和真實業務請求之間存在的差異,會對壓力測試的結構造成影響。模拟請求的另一個缺點在于寫請求的處理比較麻煩,因為寫請求可能會對業務資料造成污染,這個污染要麼接受、要麼需要做特殊的處理(比如将壓測産生的資料進行隔離)。

複制請求:通過将一台機器的請求複制多份發送到指定的壓測機器

為了使得壓測的請求跟真實的業務請求更加接近,在壓測請求的來源方式上,我們嘗試從真實的業務流量進行錄制和回放,采用請求複制的方式來進行壓力測試。請求複制的方式比請求模拟請求方式的準确性更高,因為業務的請求更加真實了。從不足上來看,請求複制同樣也面臨着處理寫請求髒資料的問題,此外複制的請求必須要将響應攔截下來,是以被壓測的這台機器需要單獨提供,且不能提供正常的服務。請求複制的壓力測試方式,主要用于系統調用量比較小的場景。

請求轉發:将分布式環境中多台機器的請求轉發到一台機器上

對于系統調用量比較大的場景,我們有更好的處理辦法。其中的一種做法我們稱為請求的引流轉發,阿裡巴巴的系統基本上都是分布式的,通過将多台機器的請求轉發到一台機器上,讓一台機器承受更大的流量,進而達到壓力測試的目的。請求的引流轉發方式不僅壓測結果非常精準、不會産生髒資料、而且操作起來也非常友善快捷,在阿裡巴巴也是用的非常廣泛的一種單機壓測方式。當然,這種壓測方式也有一個前提條件就是系統的調用量需要足夠大,如果系統的調用量非常小,即使把所有的流量都引到一台機器,還是無法壓測到瓶頸。

調整負載均衡:修改負載均衡裝置的權重,讓壓測的機器配置設定更多的請求

與請求引流轉發的方式類似,最後一種壓測方式同樣是讓分布式環境下的某一台機器配置設定更多的請求。不同的地方在于采用的方式是通過去調整負載均衡裝置的權重。調整負載均衡方式活的的壓測結果非常準确、并且不會産生髒資料。前提條件也需要分布式系統的調用量足夠大。

在阿裡巴巴,單機壓測有一個專門的壓測平台。壓測平台在前面介紹的 4 種壓測方式基礎上,構件了一套自動化的壓測系統。在這個系統上,可以配置定時任務定期對系統進行壓測,也可以在任意想壓測的時間點手動觸發一次壓測。在進行壓測的同時,實時探測壓測機器的系統負載,一旦系統負載達到預設的門檻值即立刻停止壓測,同時輸出一份壓測報告。

因為是在生産環境進行壓測,我們必須非常小心,保障壓測過程不影響到正常的業務。在單機壓測平台上,每個月将進行 5000 次以上的壓測,系統釋出或者大的變更都将通過單機壓測來驗證性能是否有變化,通過單機壓測擷取的單機服務能力值也是容量規劃一個非常重要的參考依據。

有了預估的業務通路量,也知道了系統單台機器的服務能力,粗略的要計算需要多少台機器就非常簡單了。

最小機器數 = 預估的業務通路量 / 單機能力。

通常情況下,我們會預留少量的 buffer 來防止評估的誤差和意外情況。

為什麼需要全鍊路壓測?

阿裡巴巴的全鍊路壓測

進行到這一步,我們已經完成了系統容量的粗略評估,然而做到這一步是不是就夠了呢?過去的教訓曾經狠狠地給我們上了一課。

我們對每一個系統都做好了粗略的容量計算,以為一切都會比較順利了,可是真實場景并非如此,當雙 11 的零點到來的時候,許多系統的運作情況比我們想象的要更壞。原因在于真實的業務場景下,每個系統的壓力都比較大,而系統之間是有互相依賴關系的,單機壓測沒有考慮到依賴環節壓力都比較大的情況,會引入一個不确定的誤差。這就好比,我們要生産一個儀表,每一個零件都經過了嚴密的測試,最終把零件組裝成一個儀表,儀表的工作狀态會是什麼樣的并不清楚。

事實上我們也有一些血的教訓。在 2012 年的雙 11 零點,我們一個系統的資料庫的網卡被打滿了,進而導緻部分使用者無法正常購物,盡管當時我們做了非常充分的準備,但還有一些事情是我們沒考慮到的。

需要怎麼樣才能解決這個問題?在 2013 年的雙 11 備戰過程當中,在很長一段時間内這都是我們面臨的一個難題。在中國,學生通常都會有期末考試,為了在期末考試中取得比較好的成績,老師通常會讓學生們在考試前先做幾套模拟題。雙 11 對我們的系統來說就是一年一度的期末考試,是以我們冒出了這麼一個想法:“如果能讓雙 11 提前發生,讓系統提前經曆雙 11 的模拟考驗,這個問題就解決了”。通過對雙 11 零點的使用者行為進行一次高仿真的模拟,驗證整個站點的容量、性能和瓶頸點,同時驗證之前進行的容量評估是否合理,不合理的地方再進行适當的微調。

我們為此研發了一套新的壓測平台——“全鍊路壓測”。雙 11 的模拟可不是一件簡單的事情,上億的使用者在阿裡巴巴平台上挑選、購買好幾百萬種不同類型的商品,場景的複雜性非常高。有三個最主要的難點需要解決:

  • 用于的請求量非常大,在雙 11 零點,每秒的使用者請求數超過 1000w;
  • 模拟的場景要跟雙 11 零點盡可能的貼近,如果模拟的場景跟雙 11 零點差距太大,将不具備實際的參考價值,而雙 11 零點的業務場景非常複雜;
  • 我們需要在生産環節去模拟雙 11,如何去做到模拟的使用者請求不對正常的業務和資料造成影響。

為了能夠發出每秒 1000w 以上的使用者請求,全鍊路壓測構件了一套能夠發出超大規模使用者請求的流量平台。流量平台由一個控制節點和上千個 worker 節點組成,每一個 worker 節點上都部署了我們自己研發的壓測引擎。壓測引擎除了需要支援阿裡巴巴業務的請求協定,還需要具備非常好的性能,要不然 1000w 的使用者請求,我們将無法提供足夠多的 worker 節點。上千個壓測引擎彼此配合、緊密合作,我們能像控制一台機器一樣控制整個壓測叢集,随心所欲的發出 100w/s 或者 1000w/s 的使用者請求。

阿裡巴巴的全鍊路壓測

1000w+/s 的使用者請求量不僅要能夠發送出來,而且還需要跟雙 11 的使用者行為盡可能的接近,而雙 11 是一個非常複雜的業務場景。為了使得模拟能夠更加真實,我們做了非常多的工作。首先,我們從生産環境提取一份跟雙 11 同等數量級的基礎資料(包含:買家、賣家、店鋪、商品、優惠等等),做好篩選和敏感字段的脫敏,作為全鍊路壓測的基礎資料。然後基于這些基礎資料,結合前幾年的曆史資料,通過相應的預測算法,得到今年雙 11 的業務模型。

雙 11 的業務模型包含 100 多個業務因子,比如:買家數量、買家種類、賣家數量、賣家種類、商品數量、商品種類,pc 和無線的占比,購物車裡的商品數量,每一種業務類型的通路量級等等)。有了業務模型之後,再根據業務模型構造相應的壓測請求,最終将壓測請求上傳到壓測引擎。

全鍊路壓測直接在生産環境進行雙 11 的模拟,在前面的單機壓測方式中也有提到,對于模拟請求的方式,需要考慮髒資料的處理方式。全鍊路壓測的所有資料都在生産環境做了資料隔離,包含存儲、緩存、消息、日志等一系列的狀态資料。在壓測請求上會打上特殊的标記,這個标記會随着請求的依賴調用一直傳遞下去,任何需要對外寫資料的地方都會根據這個标記的判斷寫到隔離的區域,我們把這個區域叫做影子區域。全鍊路壓測對粗略的容量評估起到了精調的作用,使雙 11 零點的各種不确定性變的更加确定。

阿裡巴巴的全鍊路壓測

我們在 2013 年雙 11 前夕的全鍊路壓測過程當中共發現了 700 多個系統問題,2014、2015、2016 同樣也發現了好幾百個問題。這些問題如果沒有在全鍊路壓測的過程當中被發現,很有可能會在雙 11 零點的真實業務場景當中暴露出來,将造成嚴重的可用性影響。

超限後的流量控制如何做?

前面章節我們讨論的都是”容量規劃”,我們知道容量規劃是基于一套精密的業務模型,而這個業務模型是根據曆年來的大促資料,以及複雜的預測模型推算出來的。然而,不論這個模型多麼強壯,它始終是一個預測。這就意味着我們存在着預測和現實流量有誤差。

這個并不僅僅是一個擔心,這個發生過非常多次。最近的一個例子是在 16 年的雙 11,我們為某一個重要的場景預備了足以應付 16.2 萬每秒的峰值,然而那天的峰值實際上到達了 20 萬每秒,超過我們準備能力将近 13%,你可能覺得這隻會對峰值産生影響,這些額外的 2W 請求馬上就會被消耗掉,但并不是你想的這樣。

當一台機器超負荷運轉的時候,這台處理請求的時間會變長。這會給使用者帶來不好的體驗,使用者會試圖重複送出請求,這無形中又給系統帶來了更多的請求壓力。随着請求堆積的越來越多,系統性能會逐漸下降甚至無法響應新的請求。

當一台機器挂掉以後, 負載均衡會把請求重定向到另外的機器上去,這又無形中給别的機器帶來了更多的任務,而這些機器也處于一個飽和的狀态,很快也會像第一台機器一樣,也無法響應新的請求。就這樣,在很短的時間之内,越來越多的機器會停止響應,最終導緻整個叢集都無法響應。這就使我們常常說的“雪崩效應”。一旦“雪崩”發生,就很難停止。我們必須有一個有效的機制,來監控和控制進入的流量,來防止災難的發生。

然而,流控并不僅僅用于流量高峰,它在很多的場景都可能用的到。比如在一個業務的鍊路上,有一個下遊系統出現了問題,響應時間變得很長。這個問題在鍊路上會被放大,甚至導緻整個鍊路不可用。這意味着流控也需要可以根據響應時間來控制系統的健康,當一個應用響應的時間超過門檻值,我們可以認為這個應用不可控,應該迅速将它降級。

除了流控的激發原因之外,流控也可以靈活的定義流控的方式。不同的業務場景,可以采取不同的流控方式。比如說,對于有的應用,我們可以簡單的丢棄這個請求,有的應用,則需要對下遊應用進行降級,甚至直接加入黑名單。而有的應用,則需要把這些多餘的請求排隊,等到高峰期過後,系統沒有那麼忙碌之後,再逐漸消耗這些流量。

是以,我們最終的流控架構可以從三個緯度着手,運作狀況,調用關系,流控方式。應用可以靈活的根據自己的需求,任意組合。

阿裡巴巴的全鍊路壓測

下面這個是我們流控的架構圖:

阿裡巴巴的全鍊路壓測
  • 第一步,我們在程式入口給所有的方法都進行埋點;
  • 第二步,我們把這些埋點方法的運作狀态,調用關系統計記錄下來;
  • 第三步,我們通過從預設好的規則中心接收規則,來根據第二步中統計到的系統狀态進行控制。

然而,當系統發生流控的時候,系統雖然是安全的,但是它始在一個“受損”狀态下運作。是以我們也在問題排除之後,解除流量控制。用我們上面的場景作為例子。一個鍊路上的一個下遊應用出現了問題,導緻響應時間變長,進而導緻上遊應用的系統負載過高。過了一會兒之後,這個下遊應用恢複了,響應時間大大縮短。然而這個時候,上遊應用的負載并不能馬上恢複,因為進來的請求已經堆積了一段時間了。

這就意味着,如果我們采用傳統的方式,用系統負載來判斷是否應該恢複流控,那麼即使問題已經修複,系統地負載仍然處于一個比較高的狀态。這樣就會導緻系統恢複慢。既要迅速恢複,同時也要系統穩定。最後我們采取的方式是,讓 rt,load, 允許通過的 qps 達到動态平衡。

讓我們來看一下最後取得的效果。用了新的算法之後,我們可以看到系統穩定在一定的範圍之内,同時當問題機器恢複之後,流量也能夠很快的恢複。

阿裡巴巴的全鍊路壓測

從近幾年雙 11 零點的業務穩定性上來看,全鍊路壓測是一個明顯的分水嶺,在全鍊路壓測之後整個站點的穩定性明顯好于全鍊路壓測之前。全鍊路壓測已經成為阿裡巴巴大促備戰的必要環節,無論是雙 11 大促、雙 12 大促,還是平時一些比較小的促銷活動,每一次活動之前都會進行好幾輪的全鍊路壓測來對系統進行一次全方位的模拟驗證,提前暴露各個環節的問題。全鍊路壓測的誕生使得阿裡大促備戰的系統穩定性有了質的提升,被譽為大促備戰的核武器。

除了全鍊路壓測來驗證我們的容量規劃的正确性以外,流量控制的政策在我們的大促技術規劃時也很重要,限流架構通過 自由組合運作狀态,調用鍊路,限流措施的靈活組合,覆寫了多種業務場景。同時,通過動态平衡,可以做到快恢複,最低的減低對使用者使用體驗的沖擊。流量控制和流量壓測兩者結合,讓我們的系統穩定健康地渡過各種極限業務場景。

寫在最後

阿裡研究員蔣江偉曾經說過,“今天如果有人問我怎麼做雙十一,怎麼做大促活動,我會告訴他一個非常簡單的方法,就是做好容量規劃,做好限流降級。”現在,基于阿裡在雙 11 大促上的多年的系統高可用保障經驗,全鍊路壓測服務 6 月份即将在阿裡雲上線(在原有雲産品 PTS 的基礎上進行全方位更新),大家都可以近距離的使用阿裡的這套核武器了。

聲明:本号所有文章除特殊注明,都為原創,公衆号讀者擁有優先閱讀權,未經作者本人允許不得轉載,否則追究侵權責任。

關注我的公衆号,背景回複【JAVAPDF】擷取200頁面試題!5萬人關注的大資料成神之路,不來了解一下嗎?5萬人關注的大資料成神之路,真的不來了解一下嗎?5萬人關注的大資料成神之路,确定真的不來了解一下嗎?

歡迎您關注《大資料成神之路》

繼續閱讀