【資料遷移】Mysql 線上資料遷移的一點想法
阿新 • • 發佈:2019-01-25
線上資料節點新增分為2類:
1. 往主從複製的叢集中新增一個新的slave節點
這個相對簡單,根據之前sqlproxy的實現經驗,主要步驟分為線下和線上兩部分:
線下, a.選擇一個叢集中的slave節點 s,停止它的 sql thread (這種情況下dbscale會自動遮蔽這個節點)。
b. 記錄slave節點 s執行到的master binlog位置(Relay_Master_Log_File, Exec_Master_Log_Pos)
c. 通過備份工具或手工拷貝將該slave s的資料複製到新的slave節點上
d. 恢復slave s的sql thread(當同步延遲減少到可接受範圍內時dbscale會重新啟用這個節點)
e. 讓新slave節點 change master to 全域性的master節點,位置為步驟b中記錄的位置
線上, a. dbscale 上個全域性的系統鎖,將新slave的資訊新增進全域性的叢集拓撲元資料中
b. 解除全域性系統鎖
c. 當新slave的延遲減少到可接受範圍內是dbscale會啟用這個節點來提供服務
這個方案對系統的影響很小,主要是線上的全域性系統鎖,但那個很快就釋放了。 線下的操作可以由指令碼來完成。
通過把指令碼的呼叫整合到dbscale的管理介面中可以實現自動化處理。
2. 往一個sharding叢集中新增一個新的partition節點
這個過程較為複雜。 sharding指的是對一張大表的sharding, 把一張大表分散到多個邏輯節點上,而邏輯節點可能部署在不同的物理機器上。
首先是分割槽演算法的單調性,這裡主要指的是HASH分割槽演算法 (range分割槽的單調性很容易), 例如一致性HASH演算法, 可以參考下面這個連線:
http://blog.csdn.net/sparkliang/article/details/5279393
在確保了演算法的單調性之後,我們就可以確保往叢集中新增新節點的過程中發生的資料重新分佈只會是資料從舊的節點移到新的節點。
這樣問題就簡化為如何線上地將一個partition中的部分資料遷移到一個新的partition中。
假設一箇舊的partition 為p1, 新的partition為p2, p1的一個備份節點p3, p2 的備份節點p4
線下: 建立p2和p4的主從複製關係, 然後通過dbscale的管理介面將它們加入叢集
線上: 1.和之前一樣,將新的節點新增進叢集的時候會上一次全域性系統鎖。
2. 根據新的叢集拓撲計算出一個新的一致性HASH的環形分佈(我們假設舊的分佈為 hash1 新的為hash2)
3. dbscale 中斷p1 和p3之間的主從複製, 並記錄p3的執行到的master binlog位置
4. dbscale 模擬IO thread 從p1上根據步驟3記錄的位置開始拉取p1的binlog
5. dbscale 根據hash 2將拉取到的binlog中的event分為兩部分log1 和log2
log1為按照hash2應該落在p1節點的event, log2為按照hash2應該落在p2節點的event
6. dbscale根據hash 2將p3節點中相關的資料移動到p2 上
7. 當步驟6執行完, dbscale暫停從p1上拉取binlog,
1. 往主從複製的叢集中新增一個新的slave節點
這個相對簡單,根據之前sqlproxy的實現經驗,主要步驟分為線下和線上兩部分:
線下, a.選擇一個叢集中的slave節點 s,停止它的 sql thread (這種情況下dbscale會自動遮蔽這個節點)。
b. 記錄slave節點 s執行到的master binlog位置(Relay_Master_Log_File, Exec_Master_Log_Pos)
c. 通過備份工具或手工拷貝將該slave s的資料複製到新的slave節點上
d. 恢復slave s的sql thread(當同步延遲減少到可接受範圍內時dbscale會重新啟用這個節點)
e. 讓新slave節點 change master to 全域性的master節點,位置為步驟b中記錄的位置
線上, a. dbscale 上個全域性的系統鎖,將新slave的資訊新增進全域性的叢集拓撲元資料中
b. 解除全域性系統鎖
c. 當新slave的延遲減少到可接受範圍內是dbscale會啟用這個節點來提供服務
這個方案對系統的影響很小,主要是線上的全域性系統鎖,但那個很快就釋放了。 線下的操作可以由指令碼來完成。
通過把指令碼的呼叫整合到dbscale的管理介面中可以實現自動化處理。
2. 往一個sharding叢集中新增一個新的partition節點
這個過程較為複雜。 sharding指的是對一張大表的sharding, 把一張大表分散到多個邏輯節點上,而邏輯節點可能部署在不同的物理機器上。
首先是分割槽演算法的單調性,這裡主要指的是HASH分割槽演算法 (range分割槽的單調性很容易), 例如一致性HASH演算法, 可以參考下面這個連線:
http://blog.csdn.net/sparkliang/article/details/5279393
在確保了演算法的單調性之後,我們就可以確保往叢集中新增新節點的過程中發生的資料重新分佈只會是資料從舊的節點移到新的節點。
這樣問題就簡化為如何線上地將一個partition中的部分資料遷移到一個新的partition中。
假設一箇舊的partition 為p1, 新的partition為p2, p1的一個備份節點p3, p2 的備份節點p4
線下: 建立p2和p4的主從複製關係, 然後通過dbscale的管理介面將它們加入叢集
線上: 1.和之前一樣,將新的節點新增進叢集的時候會上一次全域性系統鎖。
2. 根據新的叢集拓撲計算出一個新的一致性HASH的環形分佈(我們假設舊的分佈為 hash1 新的為hash2)
3. dbscale 中斷p1 和p3之間的主從複製, 並記錄p3的執行到的master binlog位置
4. dbscale 模擬IO thread 從p1上根據步驟3記錄的位置開始拉取p1的binlog
5. dbscale 根據hash 2將拉取到的binlog中的event分為兩部分log1 和log2
log1為按照hash2應該落在p1節點的event, log2為按照hash2應該落在p2節點的event
6. dbscale根據hash 2將p3節點中相關的資料移動到p2 上
7. 當步驟6執行完, dbscale暫停從p1上拉取binlog,