canal原理
MySQL主备复制原理
- MySQL master 将数据变更写入二进制日志( binary log, 其中记录叫做二进制日志事件binary log events,可以通过
show binlog events
进行查看) - MySQL slave 将 master 的 binary log events 拷贝到它的中继日志(relay log)
- MySQL slave 重放 relay log 中事件,将数据变更反映到自己的数据
canal 工作原理
- canal 模拟 MySQL slave 的交互协议,伪装自己为 MySQL slave ,向 MySQL master 发送dump 协议
- Connection获取上一次解析成功的位置 (如果第一次启动,则获取初始指定的位置或者是当前数据库的binlog位点)。MysqlEventParser findStartPosition
- Connection建立链接,发送BINLOG_DUMP指令。MysqlConnection sendBinlogDump
- // 0. write command number
- // 1. write 4 bytes bin-log position to start at
- // 2. write 2 bytes bin-log flags
- // 3. write 4 bytes server id of the slave
- // 4. write bin-log file name
- Mysql开始推送Binaly Log。MysqlConnection dump
- 接收到的 LogBuffer 通过 SimpleParserStage 进行协议解析,解析为 LogEvent
- LogEvent通过 DmlParserStage 处理,输出为 CanalEntry
- 通过 SinkStoreStage 将上述结果给存于 EventSink 中,这是一个阻塞操作,直到存储成功。(相关逻辑在 AbstractEventParser transactionBuffer)
- 存储成功后,定时记录Binaly Log位置。(相关逻辑在 AbstractEventParser transactionBuffer)
- MySQL master 收到 dump 请求,开始推送 binary log 给 slave (即 canal server)
- canal 解析 binary log 对象(原始为 byte 流)
- 整个处理过程,数据转换如下:
- binlog (Mysql)
- LogBuffer
- LogEvent
- CanalEntry
- Message
- Dml
canal应用
mysql
-
mysql主备原理
-
当前的 canal 支持源端 MySQL 版本包括 5.1.x , 5.5.x , 5.6.x , 5.7.x , 8.0.x。详情
-
- mysql配置
# sudo vim /etc/mysql/mysql.conf.d/mysqld.cnf [mysqld] log-bin=mysql-bin # 开启 binlog binlog-format=ROW # 选择 ROW 模式 server_id=1 # 配置 MySQL replaction 需要定义,不要和 canal 的 slaveId 重复
- 新建用户
CREATE USER canal IDENTIFIED BY 'canal'; # or password canal123456 GRANT SELECT, REPLICATION SLAVE, REPLICATION CLIENT ON *.* TO 'canal'@'%'; -- GRANT ALL PRIVILEGES ON *.* TO 'canal'@'%' ; FLUSH PRIVILEGES;
-
注意
- 针对阿里云 RDS for MySQL , 默认打开了 binlog , 并且账号默认具有 binlog dump 权限 , 不需要任何权限或者 binlog 设置,可以直接跳过这一步
- 阿里云 mysql 5.6 只读实例 binlog是精简过的,binlog无法使用,方案不可用。
canal server 主要配置
- deployer/src/main/resources/canal.properties
# tcp, kafka, RocketMQ
# 如果是 kafka 或者 RocketMQ,还需要配置其他 canal.mq 参数
canal.serverMode = tcp
- deployer/src/main/resources/example/instance.properties
canal.instance.master.address=127.0.0.1:3306
canal.instance.dbUsername = canal
canal.instance.dbPassword = canal
client-adapter
- client-adapter/launcher/src/main/resources/application.yml
canal.conf.mode: tcp
canal.conf.canalServerHost: 127.0.0.1:11111
how to debug
client-adapter
是通过 SPI
插件技术实现ES
、hbase
等 OuterAdapter
功能。所以,在调试 client-adapter/launcher
之前,先要执行 mvn clean install -Dmaven.test.skip -Denv=dev
,该命令会生成相关插件并把相关插件复制到 client-adapter/launcher/target
相关目录。ES插件的相关配置文件可能不会被复制到 target/classes
下,如果不在,就手动复制。具体操作实例如下:
# cd $CANAL_HOME
mvn clean install -Dmaven.test.skip -Denv=release
mvn clean install -Dmaven.test.skip -Denv=dev
cp client-adapter/elasticsearch/target/classes/es/* client-adapter/launcher/target/class/es/*
canal源码剖析
canal server UML
CanalServerWithEmbeded
: 负责从Mysql数据库获得变更CanalServerWithNetty
: 负责通知变更给 Canal ClientAbstractEventParser
: 最大化共用mysql, oracle binlog解析代码,开源Canal中不包含具体Oracle解析功能MysqlConnection
: 继承自ErosaConnection, 是模拟Mysql Slave,读取binlog的核心代码,具体见函数 connect 和 dump 函数SessionHandler
: 当变更是通过TCP方式传输时,利用netty异步网络框架与Canal Client通信,发送的消息是 Message
canal client adapter UML
SimpleCanalConnector
:TCP通信方式下,从Canal Server获得数据库并以Message,提供给消费方OuterAdapter
: 消费Message
的基类,派生类有:ESAdapter
,LoggerAdapter
,UrlAdapter
,MQAdapter
等等AbstractCanalAdapterWorker
: Adapter消费Dml
(由Message
转化而来)核心代码在该类AbstractOuterAdapter
: 核心函数 initSyncConfig, 解析同步配置文件XXXXAdapter
:待优化的方向,收到Dml,进入各自任务MQ,简化处理出错或异常情况
相关资源
来源:https://blog.csdn.net/weixin_43834662/article/details/99713561