代码环境:
监控系统发现健康检测接口无响应,
nacos注册中心查看服务正常注册,日志没有错误输出,内存占用max的10%,cpu占用2%,跟踪GC,发现内存占用增长缓慢,几乎没有资源消耗
查看netstat,发现大量阻塞,推测服务内大量线程挂起
因为是线上系统,只有立刻重启,连接恢复正常,一切功能正常
为下次假死做准备,与运维沟通,检测到下次假死后,取消一个节点的负载均衡,先把其他节点重启,保证服务可用,剩下一个节点dump内存数据,查看线程情况
heapdump类的情况如下:
sentinel被阻塞影响,导致数量相对多还算比较正常
jstack查看线程,发现大量blocked线程(忘了截图),定位到具体代码,发现只是一个简单的count语句,类似于select count(*) from user_relation where relationId = ? 这种简单的查询,表结构只有id,userId,relationId,且全是int,都有索引,size刚到百万,直接在数据库(远程)上执行sql,响应0.046s左右,select 1响应时间也是0.044s左右........迷惑.jpg
查看数据库监控的性能,高峰期4个从库的QPS最高也就800多,cpu高点60%,有点压力,但也不至于毫无响应,MySQL节点不止我这一个服务在使用,但是库是独立使用的
无奈,只有在数据库连接池上把connection-timeout设短了(之前是0),虽然阻塞问题解决了,但始终存在数据库无响应的情况,且原因未知。推测:网络问题;MySQL监控粒度不够,可能有瞬时高峰;jpa的问题;MySQL5.6版本问题;其他sql影响(只是我没有找到阻塞的线程,监控发现的时候已经过去了),只是最终体现在了count语句上(请求来了最先查询);
等后续找个时间压测。。。。