-
Notifications
You must be signed in to change notification settings - Fork 7.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
canal整体性能优化 #726
Comments
赞赞赞 |
期待ing,期待ing |
赞! |
补充一下,ringbuffer size被设置为4096。内存是4g.由于load backup file以后就是平稳的正常traffic。因此并不想调整内存或进一步减小ringbuffer |
第一步网络优化(只做header解析,识别包大小、位点等信息,不做具体的记录级别解析) 调整前后的性能吞吐量对比: 18MB VS 117MB,提供6倍多,socket buffer优化之后基本可以跑满网卡 |
第二步优化解析的能力,跑了下简单的对象解析(不做protobuf的对象构建),刚开始速度是20MB,主要优化了时间字段的解析上,提升到了45MB. 目前遇到瓶颈了,观察系统的负载cpu最高在1.5核左右,jvm gc主要集中在young区,下一步的优化思路:多线程并行解析,最大化的使用系统负载进行优化 |
@lcybo 针对内存占用的问题,你有什么优化建议么?换掉protobuf? |
个人一点不成熟的想法:
不足的地方:
贴出一些细节: 此外,POJO还可以参考netty的Recycler或其他的对象池,理论上,ringbuffer中event占用Entry对象的峰值就是ObjectPool需要缓存的对象个数。 |
byte[]的复用倒是有, 基于ObjectPool的思路以前还真没考虑过, 对象里的各种嵌套结构体也不太一样, 不太理解复用的原理 @lcybo |
并行解析如何保证binlog event的有序性?@agapple |
办法挺多,举个栗子,把结果作为卫星数据,countdownlatch或其他的闭锁或parallelstream,最后还不用reorder |
@agapple,在外面爪机不太方便,回去再码字。 |
@lan1994 串行和并行的结合体,串行把基本的对象解析做好,并行主要处理一些耗时比较长的,比如DML的具体字段解析、protobuf对象构造等. 目前初步的测试结果,24个并发基本可以把一台24core的物理机cpu给跑满,吞吐量能跑到80MB/s (从binlog接收到生成CanalEntry整体,优化前大概7MB/s,提升一个数量级),目前瓶颈基本在cpu上了(字符串的序列化占比非常高),下午会继续测试一下从mysql -> canal server -> canal client的整体吞吐量 |
关于嵌套结构: 关于netty的Recycler,每个对象new出来会bind ThreadLocal的回收stack,如果在同一线程进行recycle/get,那么就完全不会有竞争。如果两者分离,则会涉及到潜在线程间共享的WeakOrderQueue。 BTW,sessionhandler里面的序列化: |
第三步优化已经完成,解析这块引入了ringbufer模型,分成了多个阶段:网络接收、简单解析、DML深度解析、投递到store,把中间最耗时的DML深度解析换成了并发解析的模型. 从binlog接收到生成Entry对象,测试了一下对比:
|
第四步优化已经开始,主要是关注binlog解析到client收到数据的吞吐量,目前逐步压测的情况,大概是binlog下载吞吐在8MB/s,Entry对象的吞吐大概在55MB/s,大概是1:7的数据膨胀率. 目前profile看到的瓶颈主要在server在序列化Entry对象时,相比于网络传包占了50%,测试的记录大概是100字节,换算到记录的tps,目前大概是在20w record/s左右. (我测试数据是批量insert和update,binlog里会更加紧凑) 如果优化掉这块,理论上Entry对象可以跑满网络带宽,预计可以整体提升150% (相比于未优化前,因为最后端的网络传输瓶颈比较大,所以吃掉了前面的几个优化带来的提升,如果要进一步优化,得改动protobuf协议设计) 初步优化思路 |
拜读了代码,parallel参数有些细节:Pr#737 |
赞!!!!!👍 |
非常欢迎大家提交PR哈,最近在思考protobuf的一些优化细节,目前主要瓶颈点在于protobuf的序列化和字节放大问题。 我会尽可能去保证兼容性,但也不排除极端情况下在协议设计改动出现不兼容的情况 so. 如果有好的想法,可以尽快反馈到我这里. |
enum Compression { 并行压缩+网络传输 VS 无压缩网络传输,不知道表现如何。 |
|
第四步优化已经进行了一大半,大致的效果相比于完全未优化之前提升了35%的吞吐量,可以跑到8~9万的TPS (本次压测数据和之前的批量insert不同,选择了业务上随机的一个库进行跑,19MB的binlog,大概网络传输在35MB左右) 优化点:
目前的profile分析来看,最大的瓶颈就在于构造网络传输时有多次数组拷贝。 现在的代码:
原始的10MB的记录,会至少是原先的3倍+,针对性的优化就是直代码一次性构造protobuf的数据格式,而不是通过builder + toByteString的方式,预计还能再提升10%左右. |
尝试用一次byte[]数组绕过protobuf的多次拷贝,下一步可以优化如何复用byte[]数组,避免每次请求都开辟一个新的byte[]数组,一次性开10MB的内存块,还是有一些开销的,包括client层面 |
kafka producer 适配 row data for performance #726
666,这波优化,有打算增加负载均衡能力么? |
@agapple 那个调用链的查看使用的啥工具呀? |
jvm自带的visualvm啊 |
你调整的这个参数是canal的配置canal.instance.network.receiveBufferSize和canal.instance.network.sendBufferSize 这两个参数对吗,我用的otter,在otter的manager后台,调整的这两个参数,机器配置是64核内存128g,感觉没有任何效果,是什么原因,最近otter性能总是上不去,感觉还是干canal有关系 |
@wq19880601 otter里使用canal目前默认没开并行解析的参数 |
@agapple server端这个常驻内存,随着 数据量增加总有内存溢出的情况,1.3版本后请问有没有好的解决方案 |
@agapple 为什么做大批量insert操作时canal-server端内存无明显增加,而update和delete操作,server端内存快速增加。他们有什么区别吗? |
@acuitong 可以调低一下ringbuffer的bufferSize |
@agapple 你好,这个已经调到了128,请问那个insert操作和update,delete操作有什么不同之处,现在insert操作,server端内存没什么变化,但是update和delete操作,内存会随数据量升高,调了buffer.size,虽然幅度很小,但是总会有占满堆空间的时候,同样会产生内存溢出。 |
是不是通过修改MysqlEventParser.setParallel(true)就可以修改为并行读了? |
@f-zhao parallel是有几个关联参数的,你可以看一下代 |
@agapple 请问这个测试的平均单行数据是多大? |
@acuitong update的内存问题,以前还真没留意,我到时候关注一下 |
@agapple 你好,咨询个问题,如果一条sql修改了多条记录,对这多条记录的解析还是串行的吧? |
有没有碰到过每次从grafana看到延迟好大的时候,Store remain events快达到buffer size,怀疑是client消费不及时,这个要怎么调整呢 |
我这边是同时使用logstash和canal进行同步 但是因为canal的消费慢一步 可能logstash同步到最新数据后 被canal的后消费又覆盖掉最新的 有什么好的同步方案吗 |
之前有较多的小伙伴, 反馈在大规模数据DML变更时消费速度有点跟不上, 反馈的问题列表:
这里会做一个相对完整的测试,进行针对性的优化,同时也非常欢迎大家的参与和代码MR,一起努力解决好性能和稳定性的问题. ps. 1.0.26会是一个里程碑式的版本。
最后的优化结果:https://github.com/alibaba/canal/wiki/Performance
The text was updated successfully, but these errors were encountered: