怎样去解决MyBatis引起的线程池线程打满问题呢

电子说

1.3w人已加入

描述

背景

我们有个业务服务长期没有进行过上线,但是服务器监控经常会发生报警,提示 cpu 使用率 100% 影响线上生产。偶发的现象,所以一开始没注意,后续经过排查才发现原来是踩中了一个“坑”。

基于 Spring Boot + MyBatis Plus + Vue & Element 实现的后台管理系统 + 用户小程序,支持 RBAC 动态权限、多租户、数据权限、工作流、三方登录、支付、短信、商城等功能

项目地址:https://gitee.com/zhijiantianya/ruoyi-vue-pro

视频教程:https://doc.iocoder.cn/video/

排查过程

1、首先排除了新业务上线的问题

2、其次通过服务器的监控排除了硬件故障的问题

3、于是使用 java 线程分析工具,分析了导致 cpu 过高的都是哪些线程

RBAC

发现异常线程

排查就会发现 mybatis 执行的相关线程。

4、于是我们根据提示找到相应的源码处进行分析。mybatis 组装 sql 语句这里,这段代码,在 sql 很长的并且入参很多说的时候,下面对 sql 的拼接,将#{属性名}替换成?是很耗费 cpu 的。

RBAC

MyBatis拼接大SQL耗费性能

5、那么导致这个问题的原因是什么呢?我们针对 mapper 里的 sql 语句发现,有个查询条件入参是个 list,mapper 是这么写:

RBAC

foreach

6、为了验证问题,我们自己做了一个测试,通过入参条件的调整,来进行执行时间的监控验证,最后经过反复的测试发现「当入参 list 的数量达到 10 万级别的时候,cpu 就飙升到了 120%,执行了 29s,是造成线程等待的元凶」

基于 Spring Cloud Alibaba + Gateway + Nacos + RocketMQ + Vue & Element 实现的后台管理系统 + 用户小程序,支持 RBAC 动态权限、多租户、数据权限、工作流、三方登录、支付、短信、商城等功能

项目地址:https://gitee.com/zhijiantianya/yudao-cloud

视频教程:https://doc.iocoder.cn/video/

总结

「在使用 list 做 mapper 入参,一定要考虑上限」

另外,sql 的 in 里面的数据也太多了吧,sql 太长超过 max_allow_packet 会报错的。这个 MySQL 配置,建议不要往大了改!






审核编辑:刘清

打开APP阅读更多精彩内容
声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉

全部0条评论

快来发表一下你的评论吧 !

×
20
完善资料,
赚取积分