在前面兩篇中,我們從基本概念理解了canal是一個什么項目,能應用於什么場景,然后通過一個demo體驗,有了基本的體感和認識。
從這一篇開始,我們將從源碼入手,深入學習canal的實現方式。了解canal相關功能的實現方式,其中有很多機制是非常值得深入了解的,從代碼實現角度去學習實時數據訂閱與同步的實現與核心技術點。當然,如果要在生產中使用這個開源項目,了解源碼更是必不可少,是解決問題和新特性定制的前提條件。
本文使用的版本是1.1.4,這也是筆者寫這篇博客時的最新穩定版。
1.准備工作
下載源碼
git clone https://github.com/alibaba/canal.git
切換到1.1.4這個tag
git checkout canal-1.1.4
或者可以關注我的源碼注釋版本(正在不斷更新中)
https://github.com/saigu/JavaKnowledgeGraph/tree/master/code_reading/canal
2.canal項目模塊介紹
canal項目是基於maven構建的,將不同的功能模塊划分了不同的子模塊。
我們可以簡單執行可執行模塊deployer,也可以將模塊通過maven依賴的方式,將你需要的子模塊引入到你自己的項目中進行使用開發。

簡單介紹下核心模塊的功能:
- deployer模塊:獨立部署模塊,用於canal-server的獨立啟動,包括本地配置解析、拉取遠程配置、啟動canal-server。
- server模塊:canal-server的實現邏輯,一個canal-server一般是一個jvm進程。重點關注兩種canal-server的實現方式,內嵌型的canalServerEmbed和獨立使用的canalServerWithNetty。新版本中新增了直接對接mq的canal-server實現。
- instance模塊:具體實時訂閱任務是由一個個instance組成的,每個canal-server中可以同時運行多個instance。instance由parser、sink、store三個重點模塊組成。
- parser模塊:數據源接入,模擬slave協議和master進行交互,協議解析。parser模塊依賴於dbsync、driver模塊。
- sink模塊:將parser抓取到的數據,進行過濾,加工,然后發送到store模塊進行存儲。核心接口為CanalEventSink。
- store模塊:數據存儲模塊,類似內存模式到消息隊列,本質上是一個RingBuffer。核心接口為CanalEventStore。
- meta模塊:增量訂閱&消費信息管理器,核心接口為CanalMetaManager,主要用於記錄canal消費到的mysql binlog的位置
- client模塊:項目最早的消費客戶端,通過將client模塊引入自己的項目中,然后直接消費canal-server獲取的數據。
- client-adapter模塊:1.1.x后新出的模塊,可以獨立部署為canal-server的消費服務端,是一個springboot項目。通過SPI機制,能夠加載不同plugins,將消費信息投遞到ES\hbase\rdb等下游。
- admin模塊:1.1.x新出的模塊,可以獨立部署為canal-server的控制台,配置canal-server、instance相關配置,非常好用。
3.模塊關聯
那這些模塊之間是如何組織、如何關聯的呢?
我們從整體到局部來看一下。
整體架構關聯,包括admin模塊、server模塊、client-adapter模塊

1)server模塊是服務端核心模塊,用來拉取binlog的實時變更,然后投遞到客戶端。
2)server可以通過配置,選擇投遞到MQ,或者是啟動一個netty,讓客戶端來拉取。
3)client-adapter就是一個獨立部署到服務,可以直接拉取canal-server的消息(或者拉取mq的消息),轉發到對應RDS/Redis/HBase,當然,你也可以自己實現一個轉發到redis的adapter
4)admin模塊是管理控制台,可以調度canal-server組成一個個集群實現instance的高可用、可以更改server、instance的配置信息。
Canal-server模塊局部關系,包括deployer模塊、server模塊、instance模塊、parser模塊、sink模塊、store模塊、meta模塊、client模塊。

1)deployer模塊是一個啟動模塊,可以啟動canal-server。
2)一個server是一個獨立應用,是一個jvm進程,里面可以有多個instance對象。
3)instance內包括了parser、sink、store、meta
4)parser負責獲取binlog變更,然后sink將parser獲取的binlog變更轉換為event,存入store。
5)meta是元信息管理器
6)client模塊可以內嵌入你的應用,用來消費canal-server的消息事件。
基本上核心模塊的關系就是這樣了,后續會按照模塊的維度進行源碼分析,敬請期待。
都看到最后了,原創不易,點個關注,點個贊吧~
文章持續更新,可以微信搜索「阿丸筆記 」第一時間閱讀,回復關鍵字【學習】有我准備的一線大廠面試資料。
知識碎片重新梳理,構建Java知識圖譜: github.com/saigu/JavaK…(歷史文章查閱非常方便)