唯品會11.11:峰值系統應對實踐

jopen 9年前發布 | 35K 次閱讀 架構


ArchSummit全球架構師峰會北京站將于2015年12月18日~19日在北京國際會議中心召開,大會設置了《 揭秘雙十一背后的技術較量 》專題來深入解讀雙十一背后的技術故事,歡迎關注。

區別于其他網購品牌唯品會定位是“一家專門做特賣的網站”, 商業模式為“名牌折扣+限時搶購+正品保險”,即“閃購”(flash sales)模式。每天上新品,以低至1折的深度折扣及充滿樂趣的限時搶購模式,為消費者提供一站式優質購物體驗,

這種閃購限時特賣業務特點決定了網站隨時都需要處理高并發、大流量的用戶請求。大量買家在每次新的品牌檔期上線后,大量涌入,搶購商品,造成網站承擔大量流量。尤其碰到熱門商品,網站并發訪問劇增,會造成整個網站負載過重,響應延遲,嚴重時甚至會出現服務宕機的情況。

唯品會11.11:峰值系統應對實踐

另外唯品會有眾多的業務銷售模式,如自營銷售模式、JIT、直發、海淘、O2O等等,這些業務銷售模式導致系統非常復雜。系統外部需要通過開放平 臺對接供應商系統和第三方物流系統。內部系統包括諸多系統,如供應商管理、商品選品、商品交易、支付系統、物流倉儲、客服系統、商品配送等等。這些系統功 能模塊之間關聯性非常強,邏輯擴展非常復雜,如何快速滿足業務發展的需要,是一個非常迫切的問題。

為了保證系統在高并發、大流量訪問下工作,并且使系統有較強的擴展性,我們的設計主要從以下幾個方面展開:

  • 系統模塊有效切分
  • 服務化解耦,集中服務治理
  • 增加異步訪問
  • 多階段緩存,降低后端壓力
  • 優化數據庫訪問
  • 加強系統監控

系統模塊有效切分

唯品會整個業務系統雖然已經拆分成幾個相對獨立的子系統如交易平臺(B2C)、VIS、WMS、TMS、ODS、CS、EBS等,但是這些業務系 統在實際運作中業務耦合嚴重。碰到新業務邏輯加入,就需要每個模塊做大量修改,各個開發團隊之間為了業務邏輯放在那里爭論不休,浪費了大量的時間,導致開 發效率比較低。這主要由于模塊劃分不合理,導致模塊之間邊界不清楚。所以我們架構團隊從整個系統角度出發,梳理整個流程,重新做系統定位,將不同業務子系 統做物理分離,減少彼此之間的依賴,使各個子系統獨立部署,出現問題后能快速采取措施,隔離出問題模塊,將故障影響降到最低。

服務化解耦,集中服務治理

服務化設計已經被主流電商系統證明是一個切實可行的方向。通過SOA服務化改造,實現了服務使用者和服務提供者的分離,使系統間的服務解耦和系統內高內聚,大大簡化了系統復雜性,具有更強的伸縮性和擴展性,滿足了業務快速發展的需要。

我們怎么有效管理這些服務呢?

Venus是唯品會自開發的一款基于Spring的Java開發框架, 以降低開發的復雜度, 提高開發人員的開發效率, 提升代碼質量, 規范開發流程。

Venus框架涵蓋了以下內容:

  • 數據庫訪問層封裝,支持分庫、分表,連接池優化
  • 緩存(Redis/Memcached)接口封裝,連接池優化
  • CRUD服務代碼自動生成(包含數據庫操作)
  • OSP/REST服務調用接口封裝及異步支持
  • ValidateInternals
  • 單元/集成測試模版代碼自動生成
  • 配置中心
  • 中央文檔中心

唯品會11.11:峰值系統應對實踐

Venus生態體系

其中開放服務平臺(OSP)的主要目標是提供服務化的核心遠程調用機制。契約化的服務接口保證系統間的解耦清晰、干凈;基于Thrift的通信和 協議層確保系統的高性能;服務可以自動注冊并被發現,易于部署;配合配置中心,服務配置可以動態更新;客戶端與治理邏輯的分離使服務接入得到極大簡化;除 此之外,OSP提供了豐富的服務治理能力,如路由、負載均衡、服務保護和優雅降級等,通過OSP,有效的實現了流量控制。

服務分流

首先OSP Proxy具有軟負載的作用,系統不需要硬件負載均衡,可以將服務請求均衡地分配到不同服務主機上。另外OSP可以配置服務的路由,服務請求可以被分配到不同版本的服務中處理,這樣很容易實現灰度發布。

服務限流

在系統流量達到極限時的情況,有自動熔斷機制。熔斷器是在服務或者周邊環境(如網絡)出現了異常后主動斷開客戶端后續的使用,從而避免服務崩潰無 法恢復。但是在后續時間熔斷將使用小量請求嘗試偵測服務是否已經恢復,如果恢復則將服務再次提供給客戶端調用。熔斷器的機制即保護了服務也減少了人工干 預。相關的閥值都在是在配置中心中配置,并支持動態修改生效。限流一定要謹慎使用,要使用恰當的限流策略,區分正常訪問和惡意請求,不能將正常的用戶請求 抹殺掉。如果無法區分是否是惡意請求,需要將應用分級,確保優先級最高的應用能被訪問到,比如所有上線的商品信息。而對于下線的商品信息,可以根據請求容 量作適當的限流。

Nginx Rate Limiter是一個自主開發的防刷工具,通過Nginx上的LUA腳本插件,實現在Nginx上對本機的HTTP訪問進行限流控制的工具,以提高在促銷等高業務量環境下保障系統穩定運行的能力。

Nginx Rate Limiter通過RESTful API接口進行配置以及信息查看,可以對全局進行開關等配置,也可以針對指定URL分別添加多個限流配置,包括全局的限流。限流配置可以選擇以下一種方式:

  1. 最大訪問請求速率,超出則丟棄請求
  2. 按比例丟棄請求。

服務降級

對于電商系統,為了保證用戶體驗,在資源有限的條件下,我們必須保證關鍵系統的穩定性。通過對不同業務級別定義不同的降級策略,對除核心主流程以 外的功能,根據系統壓力情況進行有策略的關閉,從而達到服務降級的目的,例如在線商品信息,我們必須保證優先訪問,而對于下線的商品信息,我們可以容許在 訪問容量受限情況下,容許關閉下線商品詳情頁面的訪問等。

增加異步訪問

對于系統間實時性要求不高的操作,如果執行時比較耗時,可通過異步處理提高調用者性能,提高響應能力,尤其通過異步調用通知非主要流程,加快了系 統主要業務流程的反應速度和性能,異步處理機制可起到緩沖的作用,被通知的下游系統可依據自身能力控制處理數據量,避免遭受超負荷的沖擊,保證系統穩定運 行,增加了系統可用性。

分布式異步消息隊列服務器可在宕機后確保消息不丟失,異步系統有重試機制,從而提高系統可用性、健壯性和擴展性。

在用戶下單后,其他系統如物流、供應商系統、配送、財務等系統需要獲取訂單詳情、訂單狀態,訂單系統通過異步消息方式將訂單的變化通知其它系統, 異步調用實現系統間隔離解耦,上下游系統業務邏輯分離,下游系統只需要解析異步消息進行處理,不需要依賴上游系統的業務邏輯,從而降低了系統之間的依賴。 即使下游系統出現異常,訂單系統仍然能正常處理數據。

多階段緩存,降低后端壓力

1、動靜分離,靜態化

靜態化可降低后端壓力,一方面通過用戶瀏覽器緩存靜態資源,失效時間通過cache-control來控制。另外一方面通過CDN緩存,例如商品 詳情頁面,為了提高緩存效率,可將商品詳情頁面偽靜態化,將URL后綴顯示為HTML,商品描述信息等靜態信息在有用戶訪問情況下,緩存到靠近用戶的 CDN節點,另外為了提高CDN效率,提前將商品圖片推送到CDN。其它商品動態數據可動態加載,如商品運營信息、商品庫存、尺碼表等,從而降低了避免不 必要的后臺訪問。

2、分布式緩存

引入分布式緩存,對緩存數據服務節點做統一集中管理,可支持緩存集群彈性擴展,通過動態增加或減少節點應對變化的數據訪問負載,通過冗余機制實現高可用性,無單點失效,不會因服務器故障而導致緩存服務中斷或數據丟失。應用端使用統一的API接口訪問緩存服務器。

通過分布式緩存,可做應用對象緩存、數據庫緩存、會話狀態及應用橫向擴展時的狀態數據緩存。

3、巧用應用服務器本地緩存

分布式緩存雖然有效解決了訪問壓力,但由于緩存服務器分布在不同網絡端、不同數據中心中部署,隨著訪問量增大將導致I/O和帶寬瓶頸。為此可將那 些基本不修改的配置數據、全局數據可以在應用服務器本地緩存,減少對后端緩存服務器實例的峰值沖擊。本地緩存需要謹慎使用,如果大量使用本地緩存,可能會 導致相同的數據被不同的節點存儲多份,對內存資源造成較大的浪費。

使用緩存對提高系統性能有很多好處,但是不合理使用緩存非但不能提高系統的性能,反而成為系統的累贅,甚至影響系統運作,產生很大的風險。對于頻繁修改的數據、沒有熱點的訪問數據、數據一致性要求非常高的數據,不建議使用緩存。

優化數據庫訪問

在高并發大數據量的訪問情況下,數據庫存取瓶頸一直是個令人頭疼的問題。如果數據庫訪問出現性能問題,整個系統將受到影響。

為此需要優化數據庫訪問,從以下幾個方面解決高并發問題:

  • 優化復雜查詢,提高數據庫查詢效率,找出關鍵模塊的數據庫慢查詢進行優化。例如減少數據庫表之間的Join、重構數據庫表相關索引、對where子句進行優化等。
  • 保證在實現功能的基礎上,盡量減少對數據庫的訪問次數;通過查詢參數,盡量減少對表的訪問行數,最小化結果集,從而減輕網絡負擔;能夠分開的操作盡量分開處理,提高每次的響應速度,查詢時用到幾列就選擇幾列,降低數據庫訪問IO負載壓力。
  • 基于電商系統讀寫比很大的特性,采用讀寫分離技術,通過一主多從,寫操作只發生在主表,多操作發生在從表上,可以大大緩解對主數據庫的訪問壓力。
  • 對業務和系統的細分,對數據庫表進行垂直拆分。將數據庫想象成由很多個"數據塊"(表)組成,垂直地將這些"數據塊"切開,然后把它們分散到多臺數據庫主機上面,從而可以分散單位時間內數據庫訪問壓力。垂直切分的依據原則是:將業務緊密,表間關聯密切的表劃分在一起。
  • 垂直切分后,需要對分區后表的數據量和增速進一步分析,以確定是否需要進行水平切分。對于核心數據如訂單,采取水平分區的方式,通過一致性哈 希算法,利用用戶Id把訂單數據均勻的分配在各個數據庫分區上,在應用系統查詢時,以用戶ID調用哈希算法找到對應數據庫分區,從而將高峰時期的數據庫訪 問壓力分散到不同數據庫分區上,從而實現數據庫的線性伸縮,極大提升數據庫的承載能力。
  • 借助于分布式緩存,緩存提供了遠大于數據庫訪問的性能。當某一應用要讀取數據時,會首先從緩存中查找需要的數據,如果找到了則直接執行,找不到的話則從數據庫中找。在設計時,需要防止緩存失效帶來的緩存穿透壓力。
  • 容許一定程度的數據冗余,對于關鍵模塊,為了防止對其它模塊的依賴而影響當前模塊的性能和可靠性,可適度保存其它模塊的關鍵數據,減少由于訪問其它模塊服務帶來的系統損耗和可靠性壓力。
  • 使用NoSQL數據庫對海量大數據進行存儲和處理。

加強系統監控

業務系統通常由眾多分布式組件構成,這些組件由web類型組件,RPC服務化類型組件,緩存組件,消息組件和數據庫組件。一個通過瀏覽器或移動客 戶端的前端請求到達后臺系統后,會經過很多個業務組件和系統組件,并且留下足跡和相關日志信息。但這些分散在每個業務組件和主機下的日志信息不利于問題排 查和定位問題的根本原因。這種監控場景正是應用性能監控系統的用武之地,應用性能監控系統收集,匯總并分析日志信息達到有效監控系統性能和問題的效果。通 過監控信息,可以清晰地定位問題發生原因,讓開發人員及時修復問題。

唯品會有三級監控,系統/網絡層面監控、應用層面監控和業務層面監控。

唯品會11.11:峰值系統應對實踐

系統/網絡層面監控,主要是對下列指標進行監控:服務器指標,如CPU、內存、磁盤、流量、TCP連接數等;數據庫指標,如QPS、主從復制延時、進程、慢查詢等。

業務層面監控,通過兩種方法,第一種在指定頁面做埋點,第二種方法從業務系統的數據庫中,將需要監控的數據抽取出來,做必要的分析處理,存入運維 自己維護的數據庫中;然后通過瀏覽器頁面,展示監控數據,頁面同時提供各種時間維度上的篩選、匯總。對一些業務的關鍵指標如PV、UV、商品展示、登錄/ 注冊、轉化率、購物車、訂單數量、支付量、發貨量和各倉訂單數據。可自定義告警范圍,通知相關人以便做出響應。

應用層面監控系統Mercury,是唯品會獨立研發的應用性能監控平臺。通過在應用程序中植入探針邏輯來實現對應用代碼、關系數據庫、緩存系統的 實時監控。Mercury通過收集日志、上報日志的方式即時獲取相關性能指標并進行智能分析,及時發現分布式應用系統的性能問題以及異常和錯誤,為系統解 決性能和程序問題提供方便可靠的依據。同時通過Mercury數據展現平臺,用戶可輕松便捷的獲取應用360度監控信息。

在唯品會體系中,Mercury提供的主要功能包括:

  • 定位慢調用:包括慢Web服務(包括Restful Web服務),慢OSP服務,慢SQL
  • 定位錯誤:包括4XX,5XX,OSP Error
  • 定位異常:包括Error Exception,Fatal Exception
  • 展現依賴和拓撲:域拓撲,服務拓撲,trace拓撲
  • Trace調用鏈:將端到端的調用,以及附加在這次調用的上下文信息,異常日志信息,每一個調用點的耗時都呈現給用戶
  • 應用告警:根據運維設定的告警規則,掃描指標數據,如違反告警規則,則將告警信息上報到唯品會中央告警平臺

Mercury架構主要分以下幾大模塊:

唯品會11.11:峰值系統應對實踐

日志由客戶端傳輸到服務端后,分二條路徑。第一條路徑,裸日志(Trace log / Exception log )通過kafka,再通過flume直接落地到HBase。這些裸日志用來查詢trace調用鏈信息和異常日志。另一條路徑,日志信息通過kafka直接 送到spark stream,通過spark分析后計算后,產生data points性能指標數據,再通過flume寫入OpenTSDB。整個傳輸過程最重要的就是保證數據消費不要丟失和積壓。

一旦滿足通過運維人員事先配置的告警規則,告警模塊可觸發告警動作。告警信息可在第一時間將故障上報給中央告警平臺。

結束語

以上幾點是我們對高并發系統的一些體會,我們在不斷改進系統,為將唯品會做大做強持續努力,也希望通過本次分享給大家帶來一定收獲。

 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!