分庫分表平滑擴容

對於咱們經常使用的分庫分表方案來講,有很大的優點,分庫分表的擴容是一件頭疼的問題,若是採用對db層作一致性hash,或是中間價的支持,它的成本過於高昂了,若是不如此,只能停機維護來處理,對高可用性會產生影響。算法

那是否有方案,既能夠快速擴展,又不下降可用性?這一篇,咱們聊聊分庫分表的擴展方案,供你們一塊兒探討。數據庫

1、水平分庫擴展問題

爲了增長db的併發能力,常見的方案就是對數據進行sharding,也就是常說的分庫分表,這個須要在初期對數據規劃有一個預期,從而預先分配出足夠的庫來處理。安全

好比目前規劃了3個數據庫,基於uid進行取餘分片,那麼每一個庫上的劃分規則以下:服務器

水平分庫如何作到平滑擴展

如上咱們能夠看到,數據能夠均衡的分配到3個數據庫裏面。網絡

可是,若是後續業務發展的速度很快,用戶量數據大量上升,當前容量不足以支撐,應該怎麼辦?併發

須要對數據庫進行水平擴容,再增長新庫來分解。新庫加入以後,原先sharding到3個庫的數據,就能夠sharding到四個庫裏面了工具

水平分庫如何作到平滑擴展

不過此時因爲分片規則進行了變化(uid%3 變爲uid%4),大部分的數據,沒法命中在原有的數據庫上了,須要從新分配,大量數據須要遷移。ui

好比以前uid1經過uid1%3 分配在A庫上,新加入庫D以後,算法改成uid1%4 了,此時有可能就分配在B庫上面了。若是你有看到以前《一致性哈希的原理與實踐》,就會發現新增一個節點,大概會有90%的數據須要遷移,這個對DB同窗的壓力仍是蠻大的,那麼如何應對?blog

通常有如下幾種方式。開發

2、停服遷移

停服遷移是最多見的一種方案了,通常以下流程:

  1. 預估停服時間,發佈停服公告

  2. 停服,經過事先作好的數據遷移工具,按照新的分片規則,進行遷移

  3. 修改分片規則

  4. 啓動服務

咱們看到這種方式比較安全,停服以後沒有數據寫入,可以保證遷移工做的正常進行,沒有一致性的問題。惟一的問題,就是停服了和時間壓力了。

  1. 停服,傷害用戶體驗,同時也下降了服務器的可用性

  2. 必須在制定時間內完成遷移,若是失敗,須要擇日再次進行。同時增長了開發人員的壓力,容易發生大的事故

  3. 數據量的巨大的時候,遷移須要大量時間

那有沒有其餘方式來改進一下,咱們看下如下兩種方案。

3、升級從庫

線上數據庫,咱們爲了保持其高可用,通常都會每臺主庫配一臺從庫,讀寫在主庫,而後主從同步到從庫。以下,A,B是主庫,A0和B0是從庫。

水平分庫如何作到平滑擴展

此時,當須要擴容的時候,咱們把A0和B0升級爲新的主庫節點,如此由2個分庫變爲4個分庫。同時在上層的分片配置,作好映射,規則以下:

uid%4=0和uid%4=2的分別指向A和A0,也就是以前指向uid%2=0的數據,分裂爲uid%4=0和uid%4=2

uid%4=1和uid%4=3的指向B和B0,也就是以前指向uid%2=1的數據,分裂爲uid%4=1和uid%4=3

由於A和A0庫的數據相同,B和B0數據相同,因此此時無需作數據遷移便可。只須要變動一下分片配置便可,經過配置中心更新,無需重啓。

水平分庫如何作到平滑擴展

因爲以前uid%2的數據分配在2個庫裏面,此時分散到4個庫中,因爲老數據還存在(uid%4=0,還有一半uid%4=2的數據),因此須要對冗餘數據作一次清理。

而這個清理,不會影響線上數據的一致性,但是隨時隨地進行。

處理完成之後,爲保證高可用,以及下一步擴容需求。能夠爲現有的主庫再次分配一個從庫。

水平分庫如何作到平滑擴展

總結一下此方案步驟以下:

  1. 修改分片配置,作好新庫和老庫的映射。

  2. 同步配置,從庫升級爲主庫

  3. 解除主從關係

  4. 冗餘數據清理

  5. 爲新的數據節點搭建新的從庫

4、雙寫遷移

雙寫的方案,更多的是針對線上數據庫遷移來用的,固然了,對於分庫的擴展來講也是要遷移數據的,所以,也能夠來協助分庫擴容的問題。

原理和上述相同,作分裂擴容,只是數據的同步方式不一樣了。

1.增長新庫寫連接

雙寫的核心原理,就是對須要擴容的數據庫上,增長新庫,並對現有的分片上增長寫連接,同時寫兩份數據。

由於新庫的數據爲空,因此數據的CRUD對其沒有影響,在上層的邏輯層,仍是以老庫的數據爲主。

水平分庫如何作到平滑擴展

2.新老庫數據遷移

經過工具,把老庫的數據遷移到新庫裏面,此時能夠選擇同步分裂後的數據(1/2)來同步,也能夠全同步,通常建議全同步,最終作數據校檢的時候好處理。

水平分庫如何作到平滑擴展

3.數據校檢

按照理想環境狀況下,數據遷移以後,由於是雙寫操做,因此兩邊的數據是一致的,特別是insert和update,一致性狀況很高。但真實環境中會有網絡延遲等狀況,對於delete狀況並非很理想,好比:

A庫刪除數據a的時候,數據a正在遷移,尚未寫入到C庫中,此時C庫的刪除操做已經執行了,C庫會多出一條數據。

此時就須要作好數據校檢了,數據校檢能夠多作幾遍,直到數據幾乎一致,儘可能以舊庫的數據爲準。

4.分片配置修改

數據同步完畢,就能夠把新庫的分片映射從新處理了,仍是按照老庫分裂的方式來進行,

u以前uid%2=0,變爲uid%4=0和uid%4=2的

uid%2=1,變爲uid%4=1和uid%4=3的。

水平分庫如何作到平滑擴展

相關文章
相關標籤/搜索