MySQL 同步 ES 實(shí)戰(zhàn),肝到爆!
大家好呀,我是樓仔。
技術(shù)是什么?就是拿來(lái)玩的,邊玩邊學(xué),才能成長(zhǎng)得更快。
之前已經(jīng)給大家講解了 MySQL 同步 ES 的幾種方案,下面就教大家如何通過(guò) Canal,將 MySQL 同步到 ES,文章內(nèi)容絕對(duì)妥妥干貨!
本文會(huì)先講解需要用到的基礎(chǔ)知識(shí),然后再是軟件安裝,最后就是實(shí)戰(zhàn)部分。
不 BB,上文章目錄:
01 基礎(chǔ)知識(shí)
1.1 主從復(fù)制原理
MySQL 的主從復(fù)制是依賴(lài)于 binlog,也就是記錄 MySQL 上的所有變化并以二進(jìn)制形式保存在磁盤(pán)上二進(jìn)制日志文件。
主從復(fù)制就是將 binlog 中的數(shù)據(jù)從主庫(kù)傳輸?shù)綇膸?kù)上,一般這個(gè)過(guò)程是異步的,即主庫(kù)上的操作不會(huì)等待 binlog 同步地完成。
詳細(xì)流程如下:
- 主庫(kù)寫(xiě) binlog:主庫(kù)的更新 SQL(update、insert、delete) 被寫(xiě)到 binlog;
- 主庫(kù)發(fā)送 binlog:主庫(kù)創(chuàng)建一個(gè) log dump 線(xiàn)程來(lái)發(fā)送 binlog 給從庫(kù);
- 從庫(kù)寫(xiě) relay log:從庫(kù)在連接到主節(jié)點(diǎn)時(shí)會(huì)創(chuàng)建一個(gè) IO 線(xiàn)程,以請(qǐng)求主庫(kù)更新的 binlog,并且把接收到的 binlog 信息寫(xiě)入一個(gè)叫做 relay log 的日志文件;
- 從庫(kù)回放:從庫(kù)還會(huì)創(chuàng)建一個(gè) SQL 線(xiàn)程讀取 relay log 中的內(nèi)容,并且在從庫(kù)中做回放,最終實(shí)現(xiàn)主從的一致性。
1.2 Cannel 基礎(chǔ)
Canel 是一款常用的數(shù)據(jù)同步工具,其原理是基于 Binlog 訂閱的方式實(shí)現(xiàn),模擬一個(gè) MySQL Slave 訂閱 Binlog 日志,從而實(shí)現(xiàn) CDC(Change Data Capture),將已提交的更改發(fā)送到下游。
主要流程如下:
- Canal 服務(wù)端向 MySQL 的 master 節(jié)點(diǎn)傳輸 dump 協(xié)議;
- MySQL 的 master 節(jié)點(diǎn)接收到 dump 請(qǐng)求后推送 Binlog 日志給 Canal 服務(wù)端,解析 Binlog 對(duì)象(原始為 byte 流)轉(zhuǎn)成 Json 格式;
- Canal 客戶(hù)端通過(guò) TCP 協(xié)議或 MQ 形式監(jiān)聽(tīng) Canal 服務(wù)端,同步數(shù)據(jù)到 ES。
下面是 Cannel 執(zhí)行的核心流程,其中 Binlog Parser 主要負(fù)責(zé) Binlog 的提取、解析和推送,EventSink 負(fù)責(zé)數(shù)據(jù)的過(guò)濾 、路由和加工,僅作了解即可。
02 軟件下載安裝
我的電腦是 Macos-x64,所以后面的軟件安裝,都是基于這個(gè)。
2.1 Java JDK
- 官網(wǎng):https://www.oracle.com/java/technologies/downloads/
- JDK 版本:11.0.19
由于 Canal 和 ES 的安裝,都強(qiáng)依賴(lài) JDK,所以這里有必要先說(shuō)明。
前方高能,這里有坑?。。?/p>
如果你選的版本不對(duì),ES 安裝可能會(huì)失敗,然后 Canal 同步數(shù)據(jù)到 ES 時(shí),也會(huì)出現(xiàn)很多詭異的問(wèn)題。
2.2 MySQL
MySQL 大家應(yīng)該都安裝了,這里需要打開(kāi) MySQL 的 BinLog。
我是 Mac,主要新建一個(gè) my.cnf 文件,然后再重啟 MySQL。
這里重啟 MySQL,我搞了半天,BinLog 開(kāi)啟后,會(huì)看到 BinLog 日志。
然后需要?jiǎng)?chuàng)建一個(gè)賬號(hào),賬號(hào)和密碼都是 Cannal,給后面 Canal 使用。
GRANT SELECT, REPLICATION SLAVE, REPLICATION CLIENT ON *.* TO 'canal'@'localhost' IDENTIFIED BY 'canal' ;
2.3 Canal
- 官網(wǎng):https://github.com/alibaba/canal/releases
- 版本:v1.1.6
下載 canal.adapter 和 canal.deployer 兩個(gè)就可以:
- canal.deployer:相當(dāng)于 canal 的服務(wù)端,啟動(dòng)它才可以在客戶(hù)端接收數(shù)據(jù)庫(kù)變更信息。
- canal.adapter:增加客戶(hù)端數(shù)據(jù)落地的適配及啟動(dòng)功能(當(dāng) deployer 接收到消息后,會(huì)根據(jù)不同的目標(biāo)源做適配,比如是 es 目標(biāo)源適配和 hbase 適配等等)。
備注:canal.admin 為 canal提供整體配置管理、節(jié)點(diǎn)運(yùn)維等面向運(yùn)維的功能,提供相對(duì)友好的 WebUI 操作界面,方便更多用戶(hù)快速和安全的操作,我這邊使用的是單機(jī)的,因此就沒(méi)有下載安裝,大家也可以拉 source code 源碼去研究下。
2.4 ES
- ES 官網(wǎng):https://www.elastic.co/cn/downloads/elasticsearch
- ES 版本:7.17.4
Mac 安裝 ES 非常簡(jiǎn)單:
brew install elasticsearch
安裝細(xì)節(jié)不贅述,安裝成功后,輸入以下網(wǎng)址:
http://localhost:9200/?pretty
2.5 Kibana
- 下載網(wǎng)址:https://www.elastic.co/cn/downloads/past-releases#kibana
- 版本:7.14.0
它是 ES 的界面化操作工具,安裝細(xì)節(jié)不贅述,安裝成功后,輸入以下網(wǎng)址:
http://localhost:5601/app/dev_tools#/console
2.6 IK 分詞器
- 下載網(wǎng)址:https://github.com/medcl/elasticsearch-analysis-ik/releases/tag/v7.17.2
- 版本:v7.17.2
它是 ES 的分詞器,安裝細(xì)節(jié)不贅述,安裝成功后,可以驗(yàn)證一下分詞效果。
2.7 小節(jié)
MySQL 開(kāi)啟 BinLog,這個(gè)不難,主要觀(guān)察是否有 BinLog 日志。
Canal 的安裝是最復(fù)雜的,涉及到很多配置修改,后面會(huì)講解。
最后是 ES + Kibana + IK 分詞器,這個(gè)其實(shí)也不難,主要關(guān)注 ES 綁定的 JDK 版本,三款軟件的安裝可以參考這篇:https://blog.csdn.net/weixin_46049028/article/details/129956485
03 Canal 配置
3.1 canal.deployer 配置
修改 conf—>example 文件夾的 instance.properties 監(jiān)聽(tīng)的數(shù)據(jù)庫(kù)配置。
這里主要修改的監(jiān)聽(tīng) MySQL 的 URL、用戶(hù)名和密碼。
這里默認(rèn)的賬號(hào)密碼就是 canal,前面已經(jīng)教大家如何創(chuàng)建了。
3.2 canal.deployer 啟動(dòng)
在 canal.deployer 中的 bin 文件下去啟動(dòng)命令 startup.sh
這樣就代表已經(jīng)啟動(dòng)了,我們可以去看下啟動(dòng)日志。
上面 start successful 代表已經(jīng)啟動(dòng)成功,并且已經(jīng)監(jiān)聽(tīng)我的 MySQL 數(shù)據(jù)庫(kù)。
3.3 canal.adapte 配置
Step1: 先把 adapter 下面的 bootstrap.yml,全部注釋掉,否則會(huì)提示你 XX 表不存在,這里坑了我好慘。
Step2: 再修改 adapter 的 application.yml 配置文件。
這里的坑,一般就是 mysql 的賬號(hào)密碼不對(duì),或者給的 es 鏈接,沒(méi)有"http://"前綴,這些都是我過(guò)踩的坑。
Step3: 修改我們?cè)?application.yml 中配置的目標(biāo)數(shù)據(jù)源 es7 文件夾內(nèi)容。
由于我們這里是對(duì)表 article 進(jìn)行去監(jiān)聽(tīng),因此我們?cè)? es7 文件夾中去創(chuàng)建 article.yml 文件。
由于我們需要把技術(shù)派項(xiàng)目中的文章查詢(xún)功能,改造成 ES 的查詢(xún)方式,所以我們就把技術(shù)派的文章表 article,同步到 ES 中。
yml文件配置如下:
dataSourceKey: defaultDS # 源數(shù)據(jù)源的key, 對(duì)應(yīng)上面配置的srcDataSources中的值
destination: example # canal的instance或者M(jìn)Q的topic
groupId: g1 # 對(duì)應(yīng)MQ模式下的groupId, 只會(huì)同步對(duì)應(yīng)groupId的數(shù)據(jù)
esMapping:
_index: article # es 的索引名稱(chēng)
_id: _id # es 的_id, 如果不配置該項(xiàng)必須配置下面的pk項(xiàng)_id則會(huì)由es自動(dòng)分配
sql: "SELECT t.id AS _id,t.id,t.user_id,t.article_type,t.title,t.short_title,t.picture,
t.summary,t.category_id,t.source,t.source_url,t.offical_stat,t.topping_stat,
t.cream_stat,t.`status`,t.deleted,t.create_time,t.update_time
FROM article t" # sql映射
commitBatch: 1 # 提交批大小
Step4: 在 Kibana 中創(chuàng)建 ES 的 article 索引
代碼如下:
PUT /article
{
"mappings" : {
"properties" : {
"id" : {
"type" : "integer"
},
"user_id" : {
"type" : "integer"
},
"article_type" : {
"type" : "integer"
},
"title" : {
"type" : "text",
"analyzer": "ik_max_word"
},
"short_title" : {
"type" : "text",
"analyzer": "ik_max_word"
},
"picture" : {
"type" : "text",
"analyzer": "ik_max_word"
},
"summary" : {
"type" : "text",
"analyzer": "ik_max_word"
},
"category_id" : {
"type" : "integer"
},
"source" : {
"type" : "integer"
},
"source_url" : {
"type" : "text",
"analyzer": "ik_max_word"
},
"offical_stat" : {
"type" : "integer"
},
"topping_stat" : {
"type" : "integer"
},
"cream_stat" : {
"type" : "integer"
},
"status" : {
"type" : "integer"
},
"deleted" : {
"type" : "integer"
},
"create_time" : {
"type" : "date"
},
"update_time" : {
"type" : "date"
}
}
}
}
3.4 canal.adapte 啟動(dòng)
我們看下啟動(dòng)日志:
上面沒(méi)有任何報(bào)錯(cuò),并且已經(jīng)啟動(dòng)了 8081 端口,說(shuō)明已經(jīng)啟動(dòng)成功,此時(shí)我們就可以操作了。
04 數(shù)據(jù)同步實(shí)戰(zhàn)
4.1 全量同步
在開(kāi)始 adapter 之后,我們應(yīng)該先來(lái)一把全量數(shù)據(jù)同步,在源碼中提供了一個(gè)接口進(jìn)行全量同步,命令如下:
curl http://127.0.0.1:8081/etl/es7/article.yml -X POST
上面就是執(zhí)行同步成功后,提示已經(jīng)導(dǎo)入 10 條。
4.2 增量同步
增量數(shù)據(jù)就是當(dāng)我在 MySQL 中 update、delete 和 insert 時(shí),那么 ES 中數(shù)據(jù)也會(huì)對(duì)應(yīng)發(fā)生變化,我下面演示下修改:
日志打印如下:
ES查詢(xún)結(jié)果如下:
上面結(jié)果中說(shuō)明 ES 已經(jīng)更改成功。
05 總結(jié)
我們?cè)倩仡櫼幌抡w執(zhí)行流程:
寫(xiě)到這里,就結(jié)束了,是不是滿(mǎn)滿(mǎn)的干貨呢?基本是手把手教你如何將 MySQL 同步到 ES,不僅是增量同步,還包括全量同步,如果你的項(xiàng)目也需要用到該場(chǎng)景,基本可以直接照搬。