Java进程故障排查思路及步骤

吃可爱长大的小学妹 提交于 2020-05-02 14:27:49

Java进程故障排查

目录

故障现象

Java进程出现问题,通常表现出如下现象:

1.CPU使用率持续极高/低 2.内存占用持续极高,甚至出现OOM(例如:进程正常运行一段时间之后突然不再响应请求,但是进程依然存在) 3.Web应用响应时间很长/超时,甚至不响应直接出现502(使用nginx作为反向代理)

响应时间长、超时,甚至不响应,这是最直观的表现;而CPU使用率极高或极低,频繁出现Full GC甚至OOM,需要借助系统日志或者监控辅助发现。

原因分析

响应时间长、超时,甚至不响应,这是一个综合性的故障结果,可能并不单纯是应用程序本身的问题。 首先,需要排查网络连通性是否正常; 其次,如果后端还接了数据存储系统,除了排查应用程序本身的问题之外,还需要排查应用所依赖的第三方组件是否出现了性能瓶颈,这通常可以从应用程序日志中看到错误信息。

在直观的故障表象背后是对应的系统指标异常,排查思路如下。

CPU使用率极低

通常是线程Hang住了,或者是出现了死锁,通过线程堆栈日志可以进行定位。

CPU使用率持续极高

先使用jstack命令查看堆栈信息,结合线程堆栈信息分析可能的原因:

  1. 业务代码很忙,甚至出现了死循环,这个从线程堆栈日志中可以 定位到具体的代码块
  2. 频繁出现GC,特别是Full GC,从gc日志中可以得知
  3. TCP连接数很高,这通常是高并发导致的
  4. 系统日志输出很频繁也会导致CPU占用很高

内存占用很高

使用jmap命令将堆内存快照保存下来,使用工具“Memory Analyzer”分析定位可能的原因:

  1. 业务代码在频繁创建对象,并且没有及时销毁,甚至因为BUG原因根本就没有释放内存空间
  2. 如果不能定位到业务代码问题,有可能是Serlvet容器等服务组件出现了内存泄漏,从堆内存快照分析中可以确定
  3. 不恰当的垃圾回收器也会引起堆空间回收不及时,这可以从GC日志中找到一些蛛丝马迹

如果频繁出现Full GC,首先需要排查是否分配的堆内存空间太小,或者GC是否需要调优。

解决思路及处理方式

  1. 应用程序日志是首先排查的入口,可以直接排查日志文件,或者从日志中心进行检索,因此要求在系统开发的时候必须设计合理的日志输出规范。
  2. 如果是线上问题,先保存“线程堆栈”和“内存快照”,重启进程,及时恢复服务,进一步排查并复现问题。
  3. 如果是测试环境,需要增加监控,充分进行压测,排查问题并解决后上线。

常用工具

查看网络连接

连接数很多意味着并发很高。

$ netstat -anpt|grep <port>

线程堆栈日志分析

  1. jstack命令:线程dump,导出线程堆栈日志
  2. 可视化分析工具

堆内存快照分析

  1. jmap命令:保存堆内存快照
  2. 可视化分析工具

线上问题诊断

  1. Arthas

https://alibaba.github.io/arthas/index.html

阿里开源的线上问题排查工具,可以不用重启进程进行问题定位。

【参考】 https://mp.weixin.qq.com/s/g8KJhOtiBHWb6wNFrCcLVg 面试官:如果你们的系统 CPU 突然飙升且 GC 频繁,如何排查?

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!