近期工作上的事情太雜太瑣碎,好久沒有更新博客了。工作當中時有所思所感的東西,每次想記錄下來時,奈何心里的那個黑天使總是跳出來說“太麻煩了”,然后就真的懶得寫了,加之最近有點貪玩《爐石》,所以博客園的這一畝三分地也已荒草叢生。廢話不多說,進入本篇博客正題吧。
對于服務器程序而言,尤其是云計算時代的服務器程序,三高標準(高可用、高性能、高擴展)往往是衡量一個優秀的服務器程序的重要指標。本篇文章主要聊聊服務宕機恢復(高可用的重要內容)、負載均衡(高擴展、高可用的主要內容)。以下內容均屬個人工作中的見解,如有不妥之處,歡迎指正。 ----peakflys
一、服務的宕機恢復 服務根據功能定位的劃分,一般可以抽象為前端服務、狀態服務、各種邏輯功能服務、數據存儲服務,這里給出兩個常見的簡單服務器架構(不含數據存儲服務)


根據不同的服務類型,宕機恢復的具體操作是不同的具體的操作是不同的。
1、前端服務 前端服務一般我們又稱之為網管服務,對于這種服務宕機的情況,我們除了對其他服務做用戶下線的操作外,前端服務并沒有其他的宕機恢復操作,重啟之后,用戶重新連上來并注冊狀態即可,對于宕機重啟的間歇時間的服務,我們放在下面的高可用相關的內容來講。
2、狀態服務 如果業務量和用戶量不是特別復雜的話,我們一般情況下都是把狀態服務器設計成全局的單點服務器。就如上面圖片中所畫的那兩種簡易服務器架構里的center-end一樣。這個服務往往存儲用戶所在的網關信息或者邏輯服務器的信息,這些信息往往是比較重要的。所以對于他的宕機恢復我們一般情況下使用這幾種方案。
①、重新注冊 如果狀態服務crash重啟,所存狀態對應的所有服務都過來重新注冊相應的狀態。
優點:邏輯簡單,不易出錯,擴展起來方便。
缺點:如果用戶量達到一定的規模,此服務重啟后服務器的負載會出現瞬間飆升。
②、cache同步 使用memcache或者redis等作為所存狀態的緩存(一般和狀態服務器不在同一臺物理機)。在狀態服務更新某一狀態時,同時把對應的狀態數據刷到緩存服務器。 這樣在狀態服務宕機重啟后,直接從緩存中恢復(我稱之為積極恢復),或者其他服務來查詢對應的狀態時,如果本地內存沒有,則去緩存中找,找到時,回應狀態 查詢請求,同時把狀態恢復到本地內存中(我稱之為惰性恢復)。“積極恢復”可以馬上使狀態服務恢復到宕機前的狀態,“惰性恢復”則可以在不影響功能的情況下分散 的慢慢的恢復。
優點:邏輯較簡單,不易出錯,擴展性很好。
缺點:如果在狀態服務crash前,cache服務重啟或者關閉了,則之后狀態服務宕機恢復時,會導致部分狀態數據的缺失。(所以cache服務要保證穩定,最好直接 使用memcache等成熟的解決方案)。同時此類型不方便存儲過于復雜的數據類型。
③、master-slave 每次啟動兩臺狀態服務,先啟動的作為master服務,后啟動為slave服務,每次master服務更新某一狀態時,會同時把對應的信息同步到slave服務器(或者兩者 直接使用共享內存等方式)。當master服務宕機時,通過一些方案(例如virtual IP漂移等),使slave服務轉變為master服務,同時master服務重啟后變為 slave服務。
優點:可用性更強,服務的宕機恢復能力也比較強。所存數據的安全性和一致性都比較高,而且存儲的數據類型不受限制。
缺點:邏輯比較復雜,要做的處理比較多,而且容易出錯。
④、master-master(or more) 每次啟動兩臺(或者多臺)狀態服務,兩臺服務之間使用共享內存等方式共享狀態信息,這樣任何一臺服務的宕機重啟均不影響狀態的查詢服務,而且重啟之后不 需要恢復做什么額外的恢復操作。
優點:服務本身不存儲狀態,服務的高可用性更強,宕機恢復速度也比較快。
缺點:狀態存儲的一致性需要保證,而且使用的共享內存等存儲帶來了另外的單點隱患,一旦宕機,影響重大。
這幾種方案各有優缺點,在項目早期,用戶量不大,而且項目進度很趕的情況下,第一種方案,無疑是最適合的方案;如果所存儲的狀態是天然的key-value形式, 則第二種方案很適合;如果項目時間充裕,而且存儲的狀態很多或者很復雜的話,可以優先考慮第三或者第四種。
3、數據存儲服務 這個服務是大家討論最多,解決方案也比較成熟的話題,目前我了解到的很多都是使用master-master或者master+多slave(memcache或redis集群)的方案,另外一些數據庫提供商本身就提供了很多高可用方案(例如SQL Server的AlwaysOn,Mysql最新存儲引擎的宕機恢復機制等),開發者本身不用太過關注。反倒是開發者最為關注的應該是數據庫讀寫性能的優化。
4、邏輯功能服務
這一項是最為復雜的,需要結合具體的邏輯功能來說。一般情況下,我認為有以下幾種方案:
①、用戶重登陸處理 主要的邏輯服務宕機后,直接使用戶在其他服務做下線處理,然后客戶端程序自動做重連接,重新注冊到其他的邏輯功能服務器,恢復對應的服務。
優點:邏輯處理簡單,用戶狀態的維持不易出錯。
缺點:如果邏輯功能服務會保存一些用戶狀態,則這種方案用戶感受度不好。而且如果登陸過程比較復雜時,其他服務器的負載也會比較高(例如賬號驗證一般放 在前端服務器來做,如果認證過程過多等,前端服務的負載和出錯率都會升高)。
②、前端服務重新選擇 在用戶不斷開和前端服務器(即gateway服務器)連接的情況下,直接由前端服務器重新為用戶選擇新的邏輯功能服務。
優點:僅作前端服務和邏輯服務之間的重連,響應速度比較快。
缺點:如果邏輯功能服務會保存一些用戶狀態,則這種方案用戶感受度不好。
其他邏輯更為復雜的,只能結合著具體業務來定制方案,在此不作過多的分析。
上面的服務舉例僅僅是一個便于講述的精簡版,如果要做高強度的高可用,尤其是在云時代的大數據量的高可用,服務器架構里必然要消除單點服務!
時間不早了,負載均衡相關的東西放在下一篇博客討論,待續……