GreatSQL删除分区慢的跟踪
某业务系统,每天凌晨会删除分区表的一个分区(按天分区),耗时较久,从最开始的30秒,慢慢变为1分钟+,影响到交易业务的正常进行。 在测试环境进行了模拟,复现了删除分区慢的情况,本次基于GreatSQL8.0.25-17进行测试,官方mysql版本也存在相同问题。
两个分区数据量是一样,但删除第一个分区耗时较长。
从系统调用上看有大量的自适应hash相关的调用
修改配置文件,关闭自适应hash,按照上面的流程从新执行
关闭自适应hash后,相同的操作过程,删除第一个分区的时间明显变短,删除每个分区的时间基本上一致。
备注:innodb_adaptive_hash_index是全局变量,可以动态修改,不重启数据库。
自适应hash对比 | 第一次删分区 | 第二次删分区 |
---|---|---|
innodb_buffer_pool_instances=8& innodb_adaptive_hash_index=on | 13.68 | 0.07 |
innodb_buffer_pool_instances=8& innodb_adaptive_hash_index=off | 0.08 | 0.08 |
函数逻辑说明:
drop 分区和add分区都会循环每个分区调用函数btr_drop_ahi_for_table 、btr_search_drop_page_hash_index清空所有分区及索引的的AHI信息, 删除第1个分区的时ahi信息被清空, 删第2个分区的时候buffer中已经没有ahi信息了,所有删除第2个分区就很快了。
针对以上原因,线上执行 drop必须遵守以下原则:
1、关闭AHI功能,不使用AHI带来的查询加速功能,需要先在测试环境进行业务测试,确保业务性能不受影响。
2、删除表的第一个分区时,内部会清理该表在每个buffer pool实例中对应的数据块页面,耗时较久,接着删其他分区耗时很小,建议将每天一次的删除分区的操作改为每周或者每月批量执行删除分区的操作,并且需要在业务低峰期操作。