canal 内存实现的方式是环形数组,这个是非常高效的,可以减少内存分配,在堆栈中分配内存挺耗时间的。何况,如果不使用环形数组的话的,消息有点折扣,很多开源的项目有实现了类似的环形数组。
在公司的某一段时间,在日常批量更改时间,发现 canal 挂掉了,当初得到的原因是:内存消耗完毕,被 Linux 干掉了 canal 进程了。可以在 /var/logs 目录下,找找相应的文件就知道了。
canal 内存的分配模型如下:
在使用 canal 的时候,记得 把 canal.instance.memory.buffer.size 属性的值设置小点。这个是前提哦!!!不然,海量数据过来的话,就有问题了。canal 是吃内存的。
canal 是吃内存的,万一海量数据涌过来的话,canal 是不是挂掉了?很大情况下不会的!且看一下分析。
– 这个是我自己写的分析注释。哈哈哈!!
我们可以点击 eventStore.tryPut(events) 这个进去看看。点击进去的时候,写着 如下箭头指示的类哦!
在看如下的分析:
经过上面的,我们知道,canal 在 没有足够的内存了,就会一直等待,知道有剩余的空位才 put 数据过来的。这个 我们的代码表示形式!在 发送 DUMP 协议给 MySQL 后,MySQL 会不断把 binlog 日志流推送给 canal ,如果 canal 这边 就会一直等待,知道有空间了,才 put 数据进去。但数据会一直停留在 TCP 缓存区的。这个属于内核的一部分,协议栈嘛。如果 canal 内存中的数据还没有消费的话。部署 canal 的进去会最终全部 kill 掉所有程序的。但不要害怕!只要我们 ack 了。同步数据的节点位置才能写到 zk 中。默认是 1 分钟刷一次 zk 的。