上周聽到公司同事分享 MySQL 同步數(shù)據(jù)到 ES 的方案,發(fā)現(xiàn)很有意思,感覺有必要將這塊知識點(diǎn)再總結(jié)提煉一下,就有了這篇文章。
本文會先講述數(shù)據(jù)同步的 4 種方案,并給出常用數(shù)據(jù)遷移工具 ,干貨滿滿!
1. 前言
在實(shí)際項(xiàng)目開發(fā)中,我們經(jīng)常將 MySQL 作為業(yè)務(wù)數(shù)據(jù)庫,ES 作為查詢數(shù)據(jù)庫,用來實(shí)現(xiàn)讀寫分離,緩解 MySQL 數(shù)據(jù)庫的查詢壓力,應(yīng)對海量數(shù)據(jù)的復(fù)雜查詢。
這其中有一個很重要的問題,就是如何實(shí)現(xiàn) MySQL 數(shù)據(jù)庫和 ES 的數(shù)據(jù)同步,今天和大家聊聊 MySQL 和 ES 數(shù)據(jù)同步的各種方案。
我們先看看下面 4 種常用的數(shù)據(jù)同步方案。
2. 數(shù)據(jù)同步方案
2.1 同步雙寫
這是一種最為簡單的方式,在將數(shù)據(jù)寫到 MySQL 時,同時將數(shù)據(jù)寫到 ES。
優(yōu)點(diǎn):
業(yè)務(wù)邏輯簡單;
實(shí)時性高。
缺點(diǎn):
硬編碼,有需要寫入 MySQL 的地方都需要添加寫入 ES 的代碼;
業(yè)務(wù)強(qiáng)耦合;
存在雙寫失敗丟數(shù)據(jù)風(fēng)險;
性能較差,本來 MySQL 的性能不是很高,再加一個 ES,系統(tǒng)的性能必然會下降。
2.2 異步雙寫
針對多數(shù)據(jù)源寫入的場景,可以借助 MQ 實(shí)現(xiàn)異步的多源寫入。
優(yōu)點(diǎn):
性能高;
不易出現(xiàn)數(shù)據(jù)丟失問題,主要基于 MQ 消息的消費(fèi)保障機(jī)制,比如 ES 宕機(jī)或者寫入失敗,還能重新消費(fèi) MQ 消息;
多源寫入之間相互隔離,便于擴(kuò)展更多的數(shù)據(jù)源寫入。
缺點(diǎn):
硬編碼問題,接入新的數(shù)據(jù)源需要實(shí)現(xiàn)新的消費(fèi)者代碼;
系統(tǒng)復(fù)雜度增加,引入了消息中間件;
MQ是異步消費(fèi)模型,用戶寫入的數(shù)據(jù)不一定可以馬上看到,造成延時。
2.3 基于 SQL 抽取
上面兩種方案中都存在硬編碼問題,代碼的侵入性太強(qiáng),如果對實(shí)時性要求不高的情況下,可以考慮用定時器來處理:
數(shù)據(jù)庫的相關(guān)表中增加一個字段為 timestamp 的字段,任何 CURD 操作都會導(dǎo)致該字段的時間發(fā)生變化;
原來程序中的 CURD 操作不做任何變化;
增加一個定時器程序,讓該程序按一定的時間周期掃描指定的表,把該時間段內(nèi)發(fā)生變化的數(shù)據(jù)提取出來;
逐條寫入到 ES 中。
優(yōu)點(diǎn):
不改變原來代碼,沒有侵入性、沒有硬編碼;
沒有業(yè)務(wù)強(qiáng)耦合,不改變原來程序的性能;
Worker 代碼編寫簡單不需要考慮增刪改查。
缺點(diǎn):
時效性較差,由于是采用定時器根據(jù)固定頻率查詢表來同步數(shù)據(jù),盡管將同步周期設(shè)置到秒級,也還是會存在一定時間的延遲;
對數(shù)據(jù)庫有一定的輪詢壓力,一種改進(jìn)方法是將輪詢放到壓力不大的從庫上。
經(jīng)典方案:借助 Logstash 實(shí)現(xiàn)數(shù)據(jù)同步,其底層實(shí)現(xiàn)原理就是根據(jù)配置定期使用 SQL 查詢新增的數(shù)據(jù)寫入 ES 中,實(shí)現(xiàn)數(shù)據(jù)的增量同步。
2.4 基于 Binlog 實(shí)時同步
上面三種方案要么有代碼侵入,要么有硬編碼,要么有延遲,那么有沒有一種方案既能保證數(shù)據(jù)同步的實(shí)時性又沒有代入侵入呢?
當(dāng)然有,可以利用 MySQL 的 Binlog 來進(jìn)行同步。
具體步驟如下:
讀取 MySQL 的 Binlog 日志,獲取指定表的日志信息;
將讀取的信息轉(zhuǎn)為 MQ;
編寫一個 MQ 消費(fèi)程序;
不斷消費(fèi) MQ,每消費(fèi)完一條消息,將消息寫入到 ES 中。
優(yōu)點(diǎn):
沒有代碼侵入、沒有硬編碼;
原有系統(tǒng)不需要任何變化,沒有感知;
性能高;
業(yè)務(wù)解耦,不需要關(guān)注原來系統(tǒng)的業(yè)務(wù)邏輯。
缺點(diǎn):
構(gòu)建 Binlog 系統(tǒng)復(fù)雜;
如果采用 MQ 消費(fèi)解析的 Binlog 信息,也會像方案二一樣存在 MQ 延時的風(fēng)險。
基于 Spring Cloud Alibaba + Gateway + Nacos + RocketMQ + Vue & Element 實(shí)現(xiàn)的后臺管理系統(tǒng) + 用戶小程序,支持 RBAC 動態(tài)權(quán)限、多租戶、數(shù)據(jù)權(quán)限、工作流、三方登錄、支付、短信、商城等功能
項(xiàng)目地址:https://github.com/YunaiV/yudao-cloud
視頻教程:https://doc.iocoder.cn/video/
3. 數(shù)據(jù)遷移工具選型
對于上面 4 種數(shù)據(jù)同步方案,“基于 Binlog 實(shí)時同步”方案是目前最常用的,也誕生了很多優(yōu)秀的數(shù)據(jù)遷移工具,這里主要對這些遷移工具進(jìn)行介紹。
這些數(shù)據(jù)遷移工具,很多都是基于 Binlog 訂閱的方式實(shí)現(xiàn),模擬一個 MySQL Slave 訂閱 Binlog 日志,從而實(shí)現(xiàn) CDC (Change Data Capture),將已提交的更改發(fā)送到下游,包括 INSERT、DELETE、UPDATE。
至于如何偽裝?大家需要先了解 MySQL 的主從復(fù)制原理,需要學(xué)習(xí)這塊知識的同學(xué),可以看我之前寫的高并發(fā)教程,里面有詳細(xì)講解。
3.1 Cannel
基于數(shù)據(jù)庫增量日志解析,提供增量數(shù)據(jù)訂閱&消費(fèi),目前主要支持 MySQL。
Canal 原理就是偽裝成 MySQL 的從節(jié)點(diǎn),從而訂閱 master 節(jié)點(diǎn)的 Binlog 日志,主要流程為:
Canal 服務(wù)端向 MySQL 的 master 節(jié)點(diǎn)傳輸 dump 協(xié)議;
MySQL 的 master 節(jié)點(diǎn)接收到 dump 請求后推送 Binlog 日志給 Canal 服務(wù)端,解析 Binlog 對象(原始為 byte 流)轉(zhuǎn)成 Json 格式;
Canal 客戶端通過 TCP 協(xié)議或 MQ 形式監(jiān)聽 Canal 服務(wù)端,同步數(shù)據(jù)到 ES。
下面是 Cannel 執(zhí)行的核心流程,其中 Binlog Parser 主要負(fù)責(zé) Binlog 的提取、解析和推送,EventSink 負(fù)責(zé)數(shù)據(jù)的過濾 、路由和加工,僅作了解即可。
3.2 阿里云 DTS
數(shù)據(jù)傳輸服務(wù) DTS(Data Transmission Service)支持 RDBMS、NoSQL、OLAP 等多種數(shù)據(jù)源之間的數(shù)據(jù)傳輸。
它提供了數(shù)據(jù)遷移、實(shí)時數(shù)據(jù)訂閱及數(shù)據(jù)實(shí)時同步等多種數(shù)據(jù)傳輸方式。相對于第三方數(shù)據(jù)流工具,DTS 提供豐富多樣、高性能、高安全可靠的傳輸鏈路,同時它提供了諸多便利功能,極大方便了傳輸鏈路的創(chuàng)建及管理。
特點(diǎn):
多數(shù)據(jù)源:支持 RDBMS、NoSQL、OLAP 等多種數(shù)據(jù)源間的數(shù)據(jù)傳輸;
多傳輸方式:支持多種傳輸方式,包括數(shù)據(jù)遷移、實(shí)時數(shù)據(jù)訂閱及數(shù)據(jù)實(shí)時同步;
高性能:底層采用了多種性能優(yōu)化措施,全量數(shù)據(jù)遷移高峰期時性能可以達(dá)到70MB/s,20萬的TPS,使用高規(guī)格服務(wù)器來保證每條遷移或同步鏈路都能擁有良好的傳輸性能;
高可用:底層為服務(wù)集群,如果集群內(nèi)任何一個節(jié)點(diǎn)宕機(jī)或發(fā)生故障,控制中心都能夠?qū)⑦@個節(jié)點(diǎn)上的所有任務(wù)快速切換到其他節(jié)點(diǎn)上,鏈路穩(wěn)定性高;
簡單易用:提供可視化管理界面,提供向?qū)降逆溌穭?chuàng)建流程,用戶可以在其控制臺簡單輕松地創(chuàng)建傳輸鏈路;
需要付費(fèi)。
再看看 DTS 的系統(tǒng)架構(gòu)。
高可用:數(shù)據(jù)傳輸服務(wù)內(nèi)部每個模塊都有主備架構(gòu),保證系統(tǒng)高可用。容災(zāi)系統(tǒng)實(shí)時檢測每個節(jié)點(diǎn)的健康狀況,一旦發(fā)現(xiàn)某個節(jié)點(diǎn)異常,會將鏈路快速切換到其他節(jié)點(diǎn)。
數(shù)據(jù)源地址動態(tài)適配:對于數(shù)據(jù)訂閱及同步鏈路,容災(zāi)系統(tǒng)還會監(jiān)測數(shù)據(jù)源的連接地址切換等變更操作,一旦發(fā)現(xiàn)數(shù)據(jù)源發(fā)生連接地址變更,它會動態(tài)適配數(shù)據(jù)源新的連接方式,在數(shù)據(jù)源變更的情況下,保證鏈路的穩(wěn)定性。
3.3 Databus
Databus 是一個低延遲、可靠的、支持事務(wù)的、保持一致性的數(shù)據(jù)變更抓取系統(tǒng)。由 LinkedIn 于 2013 年開源。
Databus 通過挖掘數(shù)據(jù)庫日志的方式,將數(shù)據(jù)庫變更實(shí)時、可靠的從數(shù)據(jù)庫拉取出來,業(yè)務(wù)可以通過定制化 client 實(shí)時獲取變更并進(jìn)行其他業(yè)務(wù)邏輯。
特點(diǎn):
多數(shù)據(jù)源:Databus 支持多種數(shù)據(jù)來源的變更抓取,包括 Oracle 和 MySQL。
可擴(kuò)展、高度可用:Databus 能擴(kuò)展到支持?jǐn)?shù)千消費(fèi)者和事務(wù)數(shù)據(jù)來源,同時保持高度可用性。
事務(wù)按序提交:Databus 能保持來源數(shù)據(jù)庫中的事務(wù)完整性,并按照事務(wù)分組和來源的提交順尋交付變更事件。
低延遲、支持多種訂閱機(jī)制:數(shù)據(jù)源變更完成后,Databus 能在毫秒級內(nèi)將事務(wù)提交給消費(fèi)者。同時,消費(fèi)者使用D atabus 中的服務(wù)器端過濾功能,可以只獲取自己需要的特定數(shù)據(jù)。
無限回溯:對消費(fèi)者支持無限回溯能力,例如當(dāng)消費(fèi)者需要產(chǎn)生數(shù)據(jù)的完整拷貝時,它不會對數(shù)據(jù)庫產(chǎn)生任何額外負(fù)擔(dān)。當(dāng)消費(fèi)者的數(shù)據(jù)大大落后于來源數(shù)據(jù)庫時,也可以使用該功能。
再看看 Databus 的系統(tǒng)架構(gòu)。
Databus 由 Relays、bootstrap 服務(wù)和 Client lib 等組成,Bootstrap 服務(wù)中包括 Bootstrap Producer 和 Bootstrap Server。
快速變化的消費(fèi)者直接從 Relay 中取事件;
如果一個消費(fèi)者的數(shù)據(jù)更新大幅落后,它要的數(shù)據(jù)就不在 Relay 的日志中,而是需要請求 Bootstrap 服務(wù),返回的將會是自消費(fèi)者上次處理變更之后的所有數(shù)據(jù)變更快照。
開源地址:https://github.com/linkedin/databus
3.4 其它
Flink
有界數(shù)據(jù)流和無界數(shù)據(jù)流上進(jìn)行有狀態(tài)計算分布式處理引擎和框架。
CloudCanal
數(shù)據(jù)同步遷移系統(tǒng),商業(yè)產(chǎn)品。
Maxwell
使用簡單,直接將數(shù)據(jù)變更輸出為json字符串,不需要再編寫客戶端。
DRD
阿里巴巴集團(tuán)自主研發(fā)的分布式數(shù)據(jù)庫中間件產(chǎn)品,專注于解決單機(jī)關(guān)系型數(shù)據(jù)庫擴(kuò)展性問題,具備輕量(無狀態(tài))、靈活、穩(wěn)定、高效等特性。
yugong
幫助用戶完成從 Oracle 數(shù)據(jù)遷移到 MySQL。
4. 后記
通過這篇文章,讓你知道 MySQL 和其它多維數(shù)據(jù)的同步方案,以及常用的數(shù)據(jù)遷移工具,幫助你更好選型。
編輯:黃飛
?
評論
查看更多