原文地址:https://www.linuxprobe.com/galera-cluster.html?spm=a2c4e.11153987.0.0.17312a34IBHu4ahtml
1. 何謂Galera Clusterlinux
何謂Galera Cluster?就是集成了Galera插件的MySQL集羣,是一種新型的,數據不共享的,高度冗餘的高可用方案,目前Galera Cluster有兩個版本,分別是Percona Xtradb Cluster及MariaDB Cluster,都是基於Galera的,因此這裏都統稱爲Galera Cluster了,由於Galera自己是具備多主特性的,因此Galera Cluster也就是multi-master的集羣架構,如圖1所示:數據庫
圖1 Galera Cluster架構緩存
圖1中有三個實例,組成了一個集羣,而這三個節點與普通的主從架構不一樣,它們均可以做爲主節點,三個節點是對等的,這種通常稱爲multi-master架構,當有客戶端要寫入或者讀取數據時,隨便鏈接哪一個實例都是同樣的,讀到的數據是相同的,寫入某一個節點以後,集羣本身會將新數據同步到其它節點上面,這種架構不共享任何數據,是一種高冗餘架構。服務器
通常的使用方法是,在這個集羣上面,再搭建一箇中間層,這個中間層的功能包括創建鏈接、管理鏈接池,負責使三個實例的負載基本平衡,負責在客戶端與實例的鏈接斷開以後重連,也能夠負責讀寫分離(在機器性能不一樣的狀況下能夠作這樣的優化)等等,使用這個中間層以後,因爲這三個實例的架構在客戶端方面是透明的,客戶端只須要指定這個集羣的數據源地址,鏈接到中間層便可,中間層會負責客戶端與服務器實例鏈接的傳遞工做,因爲這個架構支持多點寫入,因此徹底避免了主從複製常常出現的數據不一致的問題,從而能夠作到主從讀寫切換的高度優雅,在不影響用戶的狀況下,離線維護等工做,MySQL的高可用,今後開始,很是完美。架構
2. 爲何須要Galera Cluster併發
MySQL在互聯網時代,可謂是深受世人矚目的。給社會創造了無限價值,隨之而來的是,在MySQL基礎之上,產生了形形×××的使用方法、架構及周邊產品。本文所關注的是架構,在這方面,已經有不少成熟的被人熟知的產品,好比MHA、MMM等傳統組織架構,而這些架構是每一個須要數據庫高可用服務方案的入門必備選型。運維
不幸的是,傳統架構的使用,一直被人們所詬病,由於MySQL的主從模式,天生的不能徹底保證數據一致,不少大公司會花很大人力物力去解決這個問題,而效果卻通常,能夠說,只能是經過犧牲性能,來得到數據一致性,但也只是在下降數據不一致性的可能性而已。因此如今就急需一種新型架構,從根本上解決這樣的問題,天生的擺脫掉主從複製模式這樣的「美中不足」之處了。異步
幸運的是,MySQL的福音來了,Galera Cluster就是咱們須要的——今後變得完美的架構。ide
相比傳統的主從複製架構,Galera Cluster解決的最核心問題是,在三個實例(節點)之間,它們的關係是對等的,multi-master架構的,在多節點同時寫入的時候,可以保證整個集羣數據的一致性,完整性與正確性。
在傳統MySQL的使用過程當中,也不難實現一種multi-master架構,可是通常須要上層應用來配合,好比先要約定每一個表必需要有自增列,而且若是是2個節點的狀況下,一個節點只能寫偶數的值,而另外一個節點只能寫奇數的值,同時2個節點之間互相作複製,由於2個節點寫入的東西不一樣,因此複製不會衝突,在這種約定之下,能夠基本實現多master的架構,也能夠保證數據的完整性與一致性。但這種方式使用起來仍是有限制,同時還會出現複製延遲,而且不具備擴展性,不是真正意義上的集羣。
3. Galera Cluster如何解決問題
3.1 Galera的引入
如今已經知道,Galera Cluster是MySQL封裝了具備高一致性,支持多點寫入的同步通訊模塊Galera而作的,它是創建在MySQL同步基礎之上的,使用Galera Cluster時,應用程序能夠直接讀、寫某個節點的最新數據,而且能夠在不影響應用程序讀寫的狀況下,下線某個節點,由於支持多點寫入,使得Failover變得很是簡單。
全部的Galera Cluster,都是對Galera所提供的接口API作了封裝,這些API爲上層提供了豐富的狀態信息及回調函數,經過這些回調函數,作到了真正的多主集羣,多點寫入及同步複製,這些API被稱做是Write-Set Replication API,簡稱爲wsrep API。
經過這些API,Galera Cluster提供了基於驗證的複製,是一種樂觀的同步複製機制,一個將要被複制的事務(稱爲寫集),不只包括被修改的數據庫行,還包括了這個事務產生的全部Binlog,每個節點在複製事務時,都會拿這些寫集與正在APPLY隊列的寫集作比對,若是沒有衝突的話,這個事務就能夠繼續提交,或者是APPLY,這個時候,這個事務就被認爲是提交了,而後在數據庫層面,還須要繼續作事務上的提交操做。
這種方式的複製,也被稱爲是虛擬同步複製,其實是一種邏輯上的同步,由於每一個節點的寫入和提交操做仍是獨立的,更準確的說是異步的,Galera Cluster是創建在一種樂觀複製的基礎上的,假設集羣中的每一個節點都是同步的,那麼加上在寫入時,都會作驗證,那麼理論上是不會出現不一致的,固然也不能這麼樂觀,若是出現不一致了,好比主庫(相對)插入成功,而從庫則出現主鍵衝突,那說明此時數據庫已經不一致,這種時候Galera Cluster採起的方式是將出現不一致數據的節點踢出集羣,實際上是本身shutdown了。
而經過使用Galera,它在裏面經過判斷鍵值的衝突方式實現了真正意義上的multi-master,Galera Cluster在MySQL生態中,在高可用方面實現了很是重要的提高,目前Galera Cluster具有的功能包括以下幾個方面:
多主架構:真正的多點讀寫的集羣,在任什麼時候候讀寫數據,都是最新的。
同步複製:集羣不一樣節點之間數據同步,沒有延遲,在數據庫掛掉以後,數據不會丟失。
併發複製:從節點在APPLY數據時,支持並行執行,有更好的性能表現。
故障切換:在出現數據庫故障時,由於支持多點寫入,切的很是容易。
熱插拔:在服務期間,若是數據庫掛了,只要監控程序發現的夠快,不可服務時間就會很是少。在節點故障期間,節點自己對集羣的影響很是小。
自動節點克隆:在新增節點,或者停機維護時,增量數據或者基礎數據不須要人工手動備份提供,Galera Cluster會自動拉取在線節點數據,最終集羣會變爲一致。
對應用透明:集羣的維護,對應用程序是透明的,幾乎感受不到。 以上幾點,足以說明Galera Cluster是一個既穩健,又在數據一致性、完整性及高性能方面有出色表現的高可用解決方案。
不過在運維過程當中,有些技術特色仍是須要注意的,這樣才能作到知此知彼,百戰百勝,由於如今MySQL主從結構的集羣已經都是被你們所熟知的了,而Galera Cluster是一個新的技術,是一個在不斷成熟的技術,因此不少想了解這個技術的同窗,可以獲得的資料不多,除了官方的手冊以外,基本沒有一些講得深刻的,用來傳道授業解惑的運維資料,這無疑爲不少同窗設置了不低的門檻,最終有不少人由於一些特性,致使最終放棄了Galera Cluster的選擇。
目前熟知的一些特性,或者在運維中須要注意的一些特性,有如下幾個方面:
Galera Cluster寫集內容:Galera Cluster複製的方式,仍是基於Binlog的,這個問題,也是一直被人糾結的,由於目前Percona Xtradb Cluster所實現的版本中,在將Binlog關掉以後,仍是可使用的,這誤導了不少人,其實關掉以後,只是不落地了,表象上看上去是沒有使用Binlog了,實際上在內部仍是悄悄的打開了的。除此以外,寫集中還包括了事務影響的全部行的主鍵,全部主鍵組成了寫集的KEY,而Binlog組成了寫集的DATA,這樣一個KEY-DATA就是寫集。KEY和DATA分別具備不一樣的做用的,KEY是用來驗證的,驗證與其它事務沒有衝突,而DATA是用來在驗證經過以後,作APPLY的。
Galera Cluster的併發控制:如今都已經知道,Galera Cluster能夠實現集羣中,數據的高度一致性,而且在每一個節點上,生成的Binlog順序都是同樣的,這與Galera內部,實現的併發控制機制是分不開的。全部的上層到下層的同步、複製、執行、提交都是經過併發控制機制來管理的。這樣才能保證上層的邏輯性,下層數據的完整性等。
圖2 galera原理圖
圖2是從官方手冊中截取的,從圖中能夠大概看出,從事務執行開始,到本地執行,再到寫集發送,再到寫集驗證,再到寫集提交的整個過程,以及從節點(相對)收到寫集以後,所作的寫集驗證、寫集APPLY及寫集提交操做,經過對比這個圖,能夠很好的理解每個階段的意義及性能等,下面就每個階段以及其併發控制行爲作一個簡單的介紹:
a. 本地執行:這個階段,是事務執行的最初階段,能夠說,這個階段的執行過程,與單點MySQL執行沒什麼區別,併發控制固然就是數據庫的併發控制了,而不是Galera Cluster的併發控制了。
b. 寫集發送:在執行完以後,就到了提交階段,提交以前首先將產生的寫集廣播出去,而爲了保證全局數據的一致性,在寫集發送時,須要串行,這個就屬於Galera Cluster併發控制的一部分了。
c. 寫集驗證:這個階段,就是咱們一般說的Galera Cluster的驗證了,驗證是將當前的事務,與本地寫集驗證緩存集來作驗證,經過比對寫集中被影響的數據庫KEYS,來發現有沒有相同的,來肯定是否是能夠驗證經過,那麼這個過程,也是串行的。
d. 寫集提交:這個階段,是一個事務執行時的最後一個階段了,驗證完成以後,就能夠進入提交階段了,由於些時已經執行完了的,而提交操做的併發控制,是能夠經過參數來控制其行爲的,即參數repl.commit_order,若是設置爲3,表示提交就是串行的了,而這也是本人所推薦的(默認值)的一種設置,由於這樣的結果是,集羣中不一樣節點產生的Binlog是徹底同樣的,運維中帶來了很多好處和方便。其它值的解釋,之後有機會再作講解。
e. 寫集APPLY:這個階段,與上面的幾個在流程上不太同樣,這個階段是從節點作的事情,從節點只包括兩個階段,即寫集驗證和寫集APPLY,寫集APPLY的併發控制,是與參數wsrep_slave_threads有關係的,自己在驗證以後,肯定了相互的依賴關係以後,若是肯定沒有關係的,就能夠並行了,而並行度,就是參數wsrep_slave_threads的事情了。wsrep_slave_threads能夠參照參數wsrep_cert_deps_distance來設置。
3.2 流量控制
在PXC中,有一個參數叫fc_limit,它的全名實際上是叫flow control limit,顧名思義,是流量控制大小限制的意思,它的做用是什麼呢?
若是一套集羣中,某個節點,或者某幾個節點的硬件資源比較差,或者因爲節點壓力大,致使複製效率低下,等等各類緣由,致使的結果是,從節點APPLY時,很是慢,也就是說,主庫在一秒鐘以內作的操做,從庫有可能會用2秒才能完成,那麼這種狀況下,就會致使從節點執行任務的堆積,接收隊列的堆積。
假設從節點真的堆積了,那麼Galera會讓它一直堆積下去麼?這樣延遲會愈來愈嚴重,這樣Galera Cluster就變成一個主從架構的集羣了,已經失去了強一致狀態的屬性了,那麼很明顯,Galera是不會讓這種事情發生的,那麼此時,就說回到開頭提到的參數了,gcs.fc_limit,這個參數是在MySQL參數wsrep_provider_options中來配置的,這個參數是Galera的一個參數集合,有關於Flow Control的,還包括gcs.fc_factor,這兩個參數的意義是,當從節點堆積的事務數量超過gcs.fc_limit的值時,從節點就發起一個Flow Control,而當從節點堆積的事務數小於gcs.fc_limit * gcs.fc_factor時,發起Flow Control的從節點再發起一個解除的消息,讓整個集羣再恢復。
但咱們通常所關心的,就是如何解決,下面有幾個通常所採用的方法:
發送FC消息的節點,硬件有可能出現問題了,好比IO寫不進去,很慢,CPU異常高等
發送FC消息的節點,自己數據庫壓力過高,好比當前節點承載太多的讀,致使機器Load高,IO壓力大等等。
發送FC消息的節點,硬件壓力都沒有太大問題,但作得比較慢,通常緣由是主庫併發高,但從節點的併發跟不上主庫,那麼此時可能須要觀察這兩個節點的併發度大小,能夠參考狀態參數wsrep_cert_deps_distance的值,來調整從節點的wsrep_slave_threads,此時應該是能夠解決或者緩解的,這個問題能夠這樣去理解,假設集羣每一個節點的硬件資源都是至關的,那麼主庫能夠執行完,從庫爲何作不過來?那麼通常思路就是像處理主從複製的延遲問題同樣。
檢查存不存在沒有主鍵的表,由於Galera的複製是行模式的,因此若是存在這樣的表時,主節點是經過語句來修改的,好比一個更新語句,更新了全表,而從節點收到以後,就會針對每一行的Binlog作一次全表掃描,這樣致使這個事務在從節點執行,比在主節點執行慢十倍,或者百倍,從而致使從節點堆積進而產生FC。
能夠看出,其實這些方法,都是用來解決主從複製延遲的方法,沒什麼兩樣,在瞭解Flow Control的狀況下,解決它並非難事兒。
3.3 有不少坑?
有不少同窗,在使用過Galera Cluster以後,發現不少問題,最大的好比DDL的執行,大事務等,從而致使服務的不友好,這也是致使不少人放棄的緣由。
DDL執行卡死傳說:使用過的同窗可能知道,在Galera Cluster中執行一個大的改表操做,會致使整個集羣在一段時間內,是徹底寫入不了任何事務的,都卡死在那裏,這個狀況確實很嚴重,致使線上徹底不可服務了,緣由仍是併發控制,由於提交操做設置爲串行的,DDL執行是一個提交的過程,那麼串行執行改表,固然執行多久,就卡多久,直到改表執行完,其它事務也就能夠繼續操做了,這個問題如今沒辦法解決,但咱們長期使用下來發現,小表能夠這樣直接操做,大一點或者更大的,都是經過osc(pt-online-schema-change)來作,這樣就很好的避免了這個問題。
擋我者死:因爲Galera Cluster在執行DDL時,是Total Ordered Isolation(wsrep_OSU_method=TOI)的,因此必需要保證每一個節點都是同時執行的,固然對於不是DDL的,也是Total Order的,由於每個事務都具備同一個GTID值,DDL也不例外,而DDL涉及到的是表鎖,MDL鎖(Meta Data Lock),只要在執行過程當中,遇到了MDL鎖的衝突,全部狀況下,都是DDL優先,將全部的使用到這個對象的事務,通通殺死,無論是讀事務,仍是寫事務,被殺的事務都會報出死鎖的異常,因此這也是一個Galera Cluster中,關於DDL的聞名遐邇的坑。不過這個如今確實沒有辦法解決,也沒辦法避免,不過這個的影響還算能夠接受,先能夠忍忍。
不死之身:繼上面的「擋我者死」,若是集羣真的被一個DDL卡死了,致使整個集羣都動不了了,全部的寫請求都Hang住了,那麼可能會有人想一個妙招,說趕忙殺死,直接在每一個節點上面輸入kill connection_id,等等相似的操做,那麼此時,很不肯意看到的信息報了出來:You are not owner of thread connection_id。此時可能有些同窗要哭了,不過這種狀況下,確實沒有什麼好的解決方法(其實這個時候,一個故障已經發生了,一年的KPI也許已經沒有了,就看敢不敢下狠手了),要不就等DDL執行完成(全部這個數據庫上面的業務都處於不可服務狀態),要不就將數據庫直接Kill掉,快速重啓,趕忙恢復一個節點提交線上服務,而後再考慮集羣其它節點的數據增量的同步等,這個坑很是大,也是在Galera Cluster中,最大的一個坑,須要很是當心,避免出現這樣的問題。
4. 適用場景
如今對Galera Cluster已經有了足夠了解,但這樣的「完美」架構,在什麼場景下才可使用呢?或者說,哪一種場景又不適合使用這樣的架構呢?針對它的缺點,及優勢,咱們能夠揚其長,避其短。能夠經過下面幾個方面,來了解其適用場景。
數據強一致性:由於Galera Cluster,能夠保證數據強一致性的,因此它更適合應用於對數據一致性和完整性要求特別高的場景,好比交易,正是由於這個特性,咱們去哪兒網纔會成爲使用Galera Cluster的第一大戶。
多點寫入:這裏要強調多點寫入的意思,不是要支持以多點寫入的方式提供服務,更重要的是,由於有了多點寫入,纔會使得在DBA正常維護數據庫集羣的時候,纔會不影響到業務,作到真正的無感知,由於只要是主從複製,就不能出現多點寫入,從而致使了在切換時,必然要將老節點的鏈接斷掉,而後齊刷刷的切到新節點,這是沒辦法避免的,而支持了多點寫入,在切換時刻容許有短暫的多點寫入,從而不會影響老的鏈接,只須要將新鏈接都路由到新節點便可。這個特性,對於交易型的業務而言,也是很是渴求的。
性能:Galera Cluster,能支持到強一致性,毫無疑問,也是以犧牲性能爲代價,爭取了數據一致性,但要問:」性能犧牲了,會不會致使性能太差,這樣的架構根本不能知足需求呢?」這裏只想說的是,這是一個權衡過程,有多少業務,QPS大到Galera Cluster不能知足的?我想是很少的(固然也是有的,能夠自行作一些測試),在追求很是高的極致性能狀況下,也許單個的Galera Cluster集羣是不能知足需求的,但畢竟是少數了,因此夠用就好,Galera Cluster必然是MySQL方案中的佼佼者。
5. 總結
綜上所述,Galera Cluster是一個徹底可依賴的,MySQL數據一致性的絕殺利器,使用中徹底不須要擔憂數據延遲,數據不一致的問題,DBA今後就從繁複的數據修復、解決複製延遲、維護時擔憂影響業務的問題中完全解脫了。能夠說Galera Cluster是DBA及業務系統的福音,也是MySQL發展的大趨勢,我但願它會愈來愈好,也但願也有愈來愈多的人使用它,共同維護這個美好的大環境。