1.高并發,高可用系統的一些思考
高并發依賴于場景和邏輯
不一定每個場景都會產生高并發,不要為了高并發而盲目的設計,過度設計帶來 的問題遠比意料之外的高并發要多很多,依賴于具體場景和行為進行分析,一個 購物類網站,搶購場景,會觸發很多的讀取商品詳情,計算庫存等操作,而且不 需要每個請求都到達支付頁面,也不會在網站主頁帶來很多的請求,所以需要針 對搶購場景進行優化,而不是巨大的支付流程進行優化,當然商品數量多和用戶 多的情況,才需要也優化一下支付流程,
拋開場景,不談流量的盲目高并發設計,一般是過度設計,未來維護臃腫而復 雜的代碼會懲罰你當初的過度設計,
突如其來的高并發
基本是被人刷了,或者比預估的情況要多了幾倍,才有這種情況,前者可能性很 大,最近這兩年的金融網站,區塊鏈,xx 幣網站,基本會被羊毛黨盯上,沒做 好訪問防作弊,或者被對手 ddos 攻擊,都會造成高并發中網站癱瘓,清洗流 量一般就可以的,不要讓辣雞流量貫穿整個業務,高并發會帶來網站請求慢,但 網站請求慢不一定是高并發了,對癥下藥,
如果是網紅帶貨什么的,給網站帶來高并發了,這種情況下可以在提前流量上做 些手腳,例如:1. 用訊息佇列排隊流量,例如猴王網站的搶購 2. 采用一些高 端點的驗證碼,讓一些秒殺搶購的機器號被過濾出去,盡量不影響真實用戶的 搶購結果 3. 分層過濾,例如靜態資源放在 CDN 上,NGINX 層面使用自身的 快取,根據路由快取基礎資料,其他動態資料再讀寫資料庫,而不是每個請求 都經過整體的業務,這樣帶來的壓力太大了,而且也不值得,
并發中的整體專案穩定性
可以將高并發的業務部分分離到單獨的服務器,這種情況下能夠避免這部分業務 帶來機器性能的消耗,從而影響整個專案的穩定性,這樣的結果不太好的,也可 以預先將熱資料放到快取中,提高讀寫效率,也能讓 MySQL 比較穩定,一般 情況下能有高并發的網站,資料量也不少,舉例某個電商網站,可能有 100w 商 品資料,但大家搶購的是今天熱推的 10 個商品,將這十個資料提取放到快取 中,而不是每次去資料庫中查詢,當然 MySQL 設定合理的話,自身的 buffer pool 也能搞定這些熱資料快取,這樣相當于將這 10 條資料隔離出來,而不是影響到整體資料,關于熱點資料的發現,還有一些高端的是從 NGINX 訪問日 志層面實時分析,據說淘寶這種是這樣的,實時發現訪問很多的路由,分析路由 獲取到對應的商品資料,放到快取中,減輕服務器壓力,
穩定性不光存在于業務機器層面,也可能是網路寬帶不夠,或者程式在磁盤寫日 志的時候遇到瓶頸,或者記憶體不夠,導致可用快取空間很小,這些在測驗和計算 層面需要注意的問題,也會影響整體穩定性和性能的,應該提前解決,例如秒殺 系統需要關注 CPU,并發讀需要關注快取,靜態資源多的也需要考慮寬帶,
預先測驗
簡單可以是壓測關鍵業務部分,簡單的查詢一般不會帶來問題,這個頁面的靜態 資源太多,同時都在統一個域名下的話,相當于在現有并發的數量上加了更多, 這非常不利,對于瀏覽器的加載也是不利的,簡單業務也會體驗很差,壓力測驗 應當遵循慢慢提升流量的方式,并發量和回應時間并不是等比例上漲的,慢慢 提升并發量的測驗,會展示代碼的瓶頸部分在哪,然后在去解決和提升,測驗也 可以
在基礎的并發測驗之外,還有在正是服務器上的全鏈路壓力測驗,為了防止和真 實資料沖突,可以將請求中加上額外的標記,或者針對特定的用戶帳號測驗,在 資料中體現這部分額外標記,測驗完畢之后將資料洗掉,
同時,不要高并發的主要業務一直占用機器的 100% 的運算能力,這樣整體邏 輯和請求支持已經到了極限,基本再高一點就會造成問題,應該盡量讓業務只占 用機器 60-70% 的運算能力,留出一部分的余地,防止意外,
安全及備用方案
1. 從 NGINX 層面限制單個 IP 單位時間內請求頻率和次數,屏蔽掉機器刷 的可能性,從而不影響正常訪問, 2. 切記高并發 + 高可用不可以用單 點系統,例如不能因為熱資料少而就用一臺 Redis 服務器,或者更狠的 直接本機快取,一旦系統崩潰,相當于觸發連鎖反應,連保存現場和恢復 都很難, 3. 提前設計兜底方案 ① 降級,例如商品詳情頁面不展示推薦 商品,或者減少推薦商品展示數量等, ② 限流,不讓更多流量涌入,能 減少很多壓力 ③ 過載臨界點拒絕服務,這個是最壞的情況,直接阻斷壓 垮系統的最后一個流量,
2.面試官為什么會問你,如何設計一個高并發系統?
面試官心理分析
說實話,如果面試官問你這個題目,那么你必須要使出全身吃奶勁了,為啥?因 為你沒看到現在很多公司招聘的 JD 里都是說啥,有高并發就經驗者優先,
如果你確實有真才實學,在互聯網公司里干過高并發系統,那你確實拿 offer 基 本如探囊取物,沒啥問題,面試官也絕對不會這樣來問你,否則他就是蠢,
假設你在某知名電商公司干過高并發系統,用戶上億,一天流量幾十億,高峰期 并發量上萬,甚至是十萬,那么人家一定會仔細盤問你的系統架構,你們系統啥 架構?怎么部署的?部署了多少臺機器?快取咋用的?MQ 咋用的?資料庫咋 用的?就是深挖你到底是如何扛住高并發的,
因為真正干過高并發的人一定知道,脫離了業務的系統架構都是在紙上談兵,真 正在復雜業務場景而且還高并發的時候,那系統架構一定不是那么簡單的,用個 redis,用 mq 就能搞定?當然不是,真實的系統架構搭配上業務之后,會比這 種簡單的所謂“高并發架構”要復雜很多倍,
如果有面試官問你個問題說,如何設計一個高并發系統?那么不好意思,一定是 因為你實際上沒干過高并發系統,面試官看你簡歷就沒啥出彩的,感覺就不咋地, 所以就會問問你,如何設計一個高并發系統?其實說白了本質就是看看你有沒有 自己研究過,有沒有一定的知識積累,
最好的當然是招聘個真正干過高并發的哥兒們咯,但是這種哥兒們人數稀缺,不 好招,所以可能次一點的就是招一個自己研究過的哥兒們,總比招一個啥也不會 的哥兒們好吧!
所以這個時候你必須得做一把個人秀了,秀出你所有關于高并發的知識!
面試題剖析
其實所謂的高并發,如果你要理解這個問題呢,其實就得從高并發的根源出發, 為啥會有高并發?為啥高并發就很牛逼?
我說的淺顯一點,很簡單,就是因為剛開始系統都是連接資料庫的,但是要知道 資料庫支撐到每秒并發兩三千的時候,基本就快完了,所以才有說,很多公司, 剛開始干的時候,技術比較 low,結果業務發展太快,有的時候系統扛不住壓力 就掛了,
當然會掛了,憑什么不掛?你資料庫如果瞬間承載每秒 5000/8000,甚至上萬 的并發,一定會宕機,因為比如 mysql 就壓根兒扛不住這么高的并發量,
所以為啥高并發牛逼?就是因為現在用互聯網的人越來越多,很多 app、網站、 系統承載的都是高并發請求,可能高峰期每秒并發量幾千,很正常的,如果是什 么雙十一之類的,每秒并發幾萬幾十萬都有可能,
那么如此之高的并發量,加上原本就如此之復雜的業務,咋玩兒?真正厲害的, 一定是在復雜業務系統里玩兒過高并發架構的人,但是你沒有,那么我給你說一 下你該怎么回答這個問題:
可以分為以下 6 點:
系統拆分 快取
MQ
分庫分表
讀寫分離
ElasticSearch
系統拆分
將一個系統拆分為多個子系統,用 dubbo 來搞,然后每個系統連一個資料庫, 這樣本來就一個庫,現在多個資料庫,不也可以扛高并發么,
快取
快取,必須得用快取,大部分的高并發場景,都是讀多寫少,那你完全可以在數 據庫和快取里都寫一份,然后讀的時候大量走快取不就得了,畢竟人家 redis 輕 輕松松單機幾萬的并發,所以你可以考慮考慮你的專案里,那些承載主要請求的 讀場景,怎么用快取來抗高并發,
MQ
MQ,必須得用 MQ,可能你還是會出現高并發寫的場景,比如說一個業務操作 里要頻繁搞資料庫幾十次,增刪改增刪改,瘋了,那高并發絕對搞掛你的系統, 你要是用 redis 來承載寫那肯定不行,人家是快取,資料隨時就被 LRU 了,數 據格式還無比簡單,沒有事務支持,所以該用 mysql 還得用 mysql 啊,那你 咋辦?用 MQ 吧,大量的寫請求灌入 MQ 里,排隊慢慢玩兒,后邊系統消費 后慢慢寫,控制在 mysql 承載范圍之內,所以你得考慮考慮你的專案里,那些 承載復雜寫業務邏輯的場景里,如何用 MQ 來異步寫,提升并發性,MQ 單機 抗幾萬并發也是 ok 的,這個之前還特意說過,
分庫分表
分庫分表,可能到了最后資料庫層面還是免不了抗高并發的要求,好吧,那么就 將一個資料庫拆分為多個庫,多個庫來扛更高的并發;然后將一個表拆分為多個 表,每個表的資料量保持少一點,提高 sql 跑的性能,
讀寫分離
讀寫分離,這個就是說大部分時候資料庫可能也是讀多寫少,沒必要所有請求都 集中在一個庫上吧,可以搞個主從架構,主庫寫入,從庫讀取,搞一個讀寫分離, 讀流量太多的時候,還可以加更多的從庫,
ElasticSearch
Elasticsearch,簡稱 es,es 是分布式的,可以隨便擴容,分布式天然就可以支 撐高并發,因為動不動就可以擴容加機器來扛更高的并發,那么一些比較簡單的 查詢、統計類的操作,可以考慮用 es 來承載,還有一些全文搜索類的操作,也 可以考慮用 es 來承載,
上面的 幾點點,基本就是高并發系統肯定要干的一些事兒,大家可以仔細結合之 前講過的知識考慮一下,到時候你可以系統的把這塊闡述一下,然后每個部分要 注意哪些問題,之前都講過了,你都可以闡述闡述,表明你對這塊是有點積累的,
說句實話,畢竟你真正厲害的一點,不是在于弄明白一些技術,或者大概知道一 個高并發系統應該長什么樣?其實實際上在真正的復雜的業務系統里,做高并發 要遠遠比上面提到的點要復雜幾十倍到上百倍,你需要考慮:哪些需要分庫分表, 哪些不需要分庫分表,單庫單表跟分庫分表如何 join,哪些資料要放到快取里 去,放哪些資料才可以扛住高并發的請求,你需要完成對一個復雜業務系統的分 析之后,然后逐步逐步的加入高并發的系統架構的改造,這個程序是無比復雜的, 一旦做過一次,并且做好了,你在這個市場上就會非常的吃香,
其實大部分公司,真正看重的,不是說你掌握高并發相關的一些基本的架構知識, 架構中的一些技術,RocketMQ、Kafka、Redis、Elasticsearch,高并發這一塊, 你了解了,也只能是次一等的人才,對一個有幾十萬行代碼的復雜的分布式系統, 一步一步架構、設計以及實踐過高并發架構的人,這個經驗是難能可貴的,
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/65117.html
標籤:PHP
