故事背景
公司有這樣一個需求,需要將某些數據用 BI 工具 Metabase 展示出來,但是這里面就涉及到多個數據庫的聯合查詢的問題。然而這些數據庫在不同的機器上面,Metabase 部署基於同一個連接聯合查詢會有問題,所以就要想辦法將這些數據庫集中在一個連接上面。
當時方案有以下一些:
1. 使用 MySQL Federated 引擎,在特定的表上面加入聯合數據庫的連接。(效率很低,很慢)
2. MyCat,連接多個數據庫,統一到一個連接。(存在問題,不支持聯合)
3. DBLE,MyCat 加強版,能夠實現。(連接查詢也沒問題,但是結合 Metabase 的時候掃描數據不出結果)
最終選擇的方式則是通過多主一從的方式將需要的數據庫都統一到一個數據庫里面,因為這個工具只是很多展示作用,所以訪問人數不多。
具體說說實現過程!
搭建方法
1. 首先我目前的服務器結構是這樣的:
有三個主從結構的數據庫,分別各有數據庫 A / B / C,我們需要通過各自的 DB Server 2 從庫將各自的數據庫都同步到 DB Server all 這台服務器上面。
具體主從實現方式可以參考我之前的博客,這里就不多做介紹了。
2. 在各自從庫上面配置文件中加入 binlog 需要記錄哪些數據庫,以 A 為例:
# 記錄的數據庫 binlog-do-db=A # 忽略的數據庫 binlog-ignore-db=information_schema binlog-ignore-db=mysql binlog-ignore-db=performance_schema binlog-ignore-db=sys
這樣的目的是為例保證同步不會出現沖突,因為系統的那幾個庫所有的都有,多要最好忽略他們。
配置完成后需要重啟沖庫。
3. 在各台數據庫的從庫上面分別備份指定的庫:
mysqldump -uroot -p -E -R --triggers --master-data=2 --single-transaction --max-allowed-packet=64M -B A > A.sql
這里以 A 庫為例,然后查看備份文件的指針:
head -50 A.sql
可以看到類似的binlog 位置和指針:
-- CHANGE MASTER TO MASTER_LOG_FILE='mysql-bin.000006', MASTER_LOG_POS=2664;
我們需要記錄下這個:mysql-bin.000006 和 2664。
4. 在 DB Server all 數據庫上面將三個庫 A / B / C 都導入:
為提升導入速度,我們可以在登錄的時候增加參數:
mysql -uroot -p --max-allowed-packet=1024M
登錄數據庫后臨時禁用檢查和自動提交,可以提升導入速度:
set foreign_key_checks=0; set unique_checks=0; set autocommit=off;
然后使用 source 將三個數據庫都導入到數據庫里面即可!
5. 修改 DB Server all 配置文件,告訴他我們需要同步哪些數據庫:
replicate_do_db=A replicate_do_db=B replicate_do_db=C replicate_ignore_db=information_schema replicate_ignore_db=mysql replicate_ignore_db=performance_schema replicate_ignore_db=sys
此時就可以重啟數據庫,然后配置同步:
6. 在 DB Server all 上配置同步,這里以 A 為例:
CHANGE MASTER TO MASTER_HOST='192.168.x.x', MASTER_PORT=3306, MASTER_USER='xxx', MASTER_PASSWORD='xxxxxxxxx', MASTER_LOG_FILE='mysql-bin.0000xxx', MASTER_LOG_POS=xxxx FOR CHANNEL '100';
這里需要注意的是:
1. 注意之前備份文件中指針和 binlog 文件,這里需要用到。
2. 同步用戶需要實現在所有從庫都存在。
3. 最重要的就是最后的 CHANNEL 配置,不同的數據庫必須使用不同的 CHANNEL,這樣才能分開同步,不會同步失敗。
7. 最終啟動 slave:
start slave;
show slave status\G
可以看到這個庫的同步狀態!