1. 程式人生 > >Java高併發、分散式框架,從無到有微服務架構設計

Java高併發、分散式框架,從無到有微服務架構設計

微服務架構模式(Microservice Architect Pattern)。近兩年在服務的瘋狂增長與雲端計算技術的進步,讓微服務架構受到重點關注

微服務架構是一種架構模式,它提倡將單一應用程式劃分成一組小的服務,服務之間互相協調、互相配合,為使用者提供最終價值。每個服務執行在其獨立的程序中,服務與服務間採用輕量級的通訊機制互相溝通(通常是基於HTTP的RESTful API)。每個服務都圍繞著具體業務進行構建,並且能夠被獨立地部署到生產環境、類生產環境等。另外,應儘量避免統一的、集中式的服務管理機制,對具體的一個服務而言,應根據業務上下文,選擇合適的語言、工具對其進行構建。

微服務架構優勢

首先簡單介紹了微服務(Microservices)的內涵及優勢,微服務架構的本質,是用一些功能比較明確、業務比較精練的服務去解決更大、更實際的問題。微服務架構將服務拆分,分別採用相對獨立的服務對各方面進行管理,彼此之間使用統一的介面來進行交流,架構變得複雜,優勢也很明顯:

複雜度可控:在將應用分解的同時,規避了原本複雜度無止境的積累。每一個微服務專注於單一功能,並通過定義良好的介面清晰表述服務邊界。由於體積小、複雜度低,每個微服務可由一個小規模開發團隊完全掌控,易於保持高可維護性和開發效率。

微服務架構

獨立部署:由於微服務具備獨立的執行程序,所以每個微服務也可以獨立部署。當某個微服務發生變更時無需編譯、部署整個應用。由微服務組成的應用相當於具備一系列可並行的釋出流程,使得釋出更加高效,同時降低對生產環境所造成的風險,最終縮短應用交付週期。

技術選型靈活:微服務架構下,技術選型是去中心化的。每個團隊可以根據自身服務的需求和行業發展的現狀,自由選擇最適合的技術棧。由於每個微服務相對簡單,當需要對技術棧進行升級時所面臨的風險較低,甚至完全重構一個微服務也是可行的。

容錯:當某一組建發生故障時,在單一程序的傳統架構下,故障很有可能在程序內擴散,形成應用全域性性的不可用。在微服務架構下,故障會被隔離在單個服務中。若設計良好,其他服務可通過重試、平穩退化等機制實現應用層面的容錯。

擴充套件:單塊架構應用也可以實現橫向擴充套件,就是將整個應用完整的複製到不同的節點。當應用的不同元件在擴充套件需求上存在差異時,微服務架構便體現出其靈活性,因為每個服務可以根據實際需求獨立進行擴充套件。

網際網路高併發相關名詞

頁面瀏覽數(page views )

唯一身份瀏覽量(Unique PageViews)

獨立訪問者數量(unique visitors)

重複訪問者數量(repeat visitors)

每個訪問者的頁面瀏覽數(Page Views per user)

高併發

之前我將高併發的解決方法誤認為是執行緒或者是佇列可以解決,因為高併發的時候是有很多使用者在訪問,導致出現系統資料不正確、丟失資料現象,所以想到 的是用佇列解決,其實佇列解決的方式也可以處理,比如我們在競拍商品、轉發評論微博或者是秒殺商品等,同一時間訪問量特別大,佇列在此起到特別的作用,將 所有請求放入佇列,以毫秒計時單位,有序的進行,從而不會出現資料丟失系統資料不正確的情況。

經過查資料,高併發的解決方法有倆種,一種是使用快取、另一種是使用生成靜態頁面;還有就是從最基礎的地方優化我們寫程式碼減少不必要的資源浪費:(

1.不要頻繁的new物件,對於在整個應用中只需要存在一個例項的類使用單例模式.對於String的連線操作,使用StringBuffer或者StringBuilder.對於utility型別的類通過靜態方法來訪問。

避免使用錯誤的方式,如Exception可以控制方法推出,但是Exception要保留stacktrace消耗效能,除非必要不要使用 instanceof做條件判斷,儘量使用比的條件判斷方式.使用JAVA中效率高的類,比如ArrayList比Vector效能好。)

高併發 - 需要解決的問題

一:應用快取

二:HTTP快取

三:多級快取

四:池化

五:非同步併發

六:擴容

七:佇列

高併發-應用快取

堆快取

使用Java堆記憶體來儲存快取物件。使用堆快取的好處是沒有序列化/反序列化,是最快的快取。缺點也很明顯,當快取的資料量很大時,GC(垃圾回收)暫停時間會變長,儲存容量受限於堆空間大小。一般通過軟引用/弱引用來儲存快取物件,即當堆記憶體不足時,可以強制回收這部分記憶體釋放堆記憶體空間。一般使用堆快取儲存較熱的資料。有

Guava Cache: 快取和ConcurrentMap是非常相像的,但是它們也不完全一樣。最根本的區別就是,ConcurrentMap會持有所有新增的物件,直到被顯示的移除。而快取為了限制其記憶體的使用,通常都會配置成可以自動的將物件移除。在某些情況下即使不自動移除物件也是非常有用的,如LoadingCache它會自動載入快取物件。

Ehcache 3.x:是一種廣泛使用的開源Java分散式快取。主要面向通用快取,Java EE和輕量級容器。它具有記憶體和磁碟儲存,快取載入器,快取擴充套件,快取異常處理程式,一個gzip快取servlet過濾器,支援REST和SOAP api等特點。

MapDB: mapdb是一個內嵌的純java的資料庫,提供了併發的HashMap、TreeMap、Queue,可以基於堆外或者磁碟來儲存資料

高併發-應用快取

堆外快取

即快取資料儲存在堆外記憶體,可以減少GC暫停時間(堆物件轉移到堆外,GC掃描和移動的物件變少),但是,讀取資料時需要序列化/反序列化,因此會比堆快取要慢很多。有Ehcache 3.x、MapDB實現

磁碟快取

即快取資料儲存在磁軌上,在JVM重啟時資料還存在的,而堆快取/堆外快取資料會丟失,需要重新載入。有Ehcache 3.x、MapDB實現

分散式快取

程序內快取和磁碟快取,在多JVM例項的情況下,會存在兩個問題:

1、單機容量問題;

2、資料一致性問題(多臺JVM例項的快取資料不一致怎麼辦?),這個問題不用糾結,既然資料允許快取,則表示允許一定時間內的不一致,因此可以設定快取資料的過期時間來定期更新資料;

3、快取不命中時,需要回源到DB/服務請求多變問題:每個例項在快取不命中的情況下都會回源到DB載入資料,因此多例項後DB整體的訪問量變多瞭解決辦法是可以使用如一致性雜湊分片演算法。因此,這些情況可以考慮使用分散式快取來解決。

可以使用ehcache –clustered(配合 Terracotta server) 實現JAVA程序間分散式快取。最好的辦法是使用redis實現分散式快取。

高併發- HTTP快取

瀏覽器快取是指當我們使用瀏覽器訪問一些網站頁面或者http服務時,根據服務端返回的快取設定響應頭將響應內容快取到瀏覽器,下次可以直接使用快取內容或者僅需要去服務端驗證內容是否過期即可。這樣的好處可以減少瀏覽器和服務端之間來回傳輸的資料量,節省頻寬提升效能。

解決辦法:內容不需要動態(計算、渲染等)速度更快,內容越接近於使用者速度越快。像apache traffic server、squid、varnish、nginx等技術都可以來進行內容快取。

還有CDN就是用來加速使用者訪問的:

即使用者首先訪問到全國各地的CDN節點(使用如ATS、Squid實現),如果CDN沒命中,會回源到中央nginx叢集,該叢集如果沒有命中快取(該叢集的快取不是必須的,要根據實際命中情況等決定),最後回源到後端應用叢集。

高併發- 多級快取(分散式快取)

高併發-池化

在應用系統開發過程中,我們經常會用到池化技術,如物件池、連線池、執行緒池等,通過池化來減少一些消耗,以提升效能。

物件池通過複用物件從而減少建立物件、垃圾回收 的開銷。但是,池化不能太大,太大會影響GC時的掃描時間。

連線池如資料庫連線池、Redis連線池、Http連線池,通過複用TCP連線減少建立和釋放連線的時間來提升效能。

執行緒池也是類似的,通過複用執行緒提升效能。也就是說池化的目的就是通過複用技術提升效能。

高併發-擴容

1、讀寫分離:當資料庫訪問量還不是很大的時候,我們可以適當增加伺服器,資料庫主從複製的方式將讀寫分離

2、垂直分割槽:當寫入操作一旦增加的時候,那麼主從資料庫將花更多的時間的放在資料同步上,這個時候伺服器也是不堪重負的;那麼就有了資料的垂直分割槽,資料的垂直分割槽思路是將寫入操作比較頻繁的資料表,如使用者表_user,或者訂單表_orders,那麼我們就可以把這個兩個表分離出來,放在不同的伺服器,如果這兩個表和其他表存在聯表查詢,那麼就只能把原來的sql語句給拆分了,先查詢一個表,在查詢另一個,雖然說這個會消耗更過效能,但比起那種大量資料同步,負擔還是減輕了不少;

3、水平分割槽:但是往往事情不盡人意,可能採取垂直分割槽能撐一段時間,由於網站太火了,訪問量又每日100w,一下子蹦到了1000w,這個時候可以採取資料的進行分離,我們可以根據user的Id不同進行分配,如採取%2、 形式,當然這種形式對以後的擴充套件有了很大的限制,當我由10個分割槽增加到20個的時候,所有的資料都得重新分割槽,那麼將是一個的很龐大的計算量;幾種常見的演算法: 雜湊演算法:就是採用user_id%的方式; 範圍:可以根據user_id字元值範圍分割槽,如1-1000為一區,1001-2000則是另一個區等; 對映關係:就是將user_id存在的所對應的分割槽放在資料庫中儲存,當用戶操作時先去查詢所在分割槽,再進行操作。

喜歡就關注吧

本次給大家推薦一個免費的學習群 744677563,裡面概括Java分散式、高併發、JVM、高效能、微服務、區塊鏈、大資料等技術,以及面試資源等。

成就大神不是夢,還是要看你加不加