Java线上问题之日志打好与JVM参数配好
- 这里想说的是打印日志的重要性,它在你定位问题时起到至关重要的作用
以下是这次故障的分析过程:
- 服务无法访问,发现CPU被打满,同时进程僵死,jstack无法打印数据(后来了解到 jstack -F 可以暴力获取,可惜没得尝试)
- 重启一台机器(另外一台机器保留现场),更改nginx配置去掉另一台的映射
- 进程僵死,打印了java.hprof文件(7.3G)
- 很快又被打满,无法访问;怀疑是新代码问题,版本回滚,重启
- 继续定位问题原因;分析日志时发现有一行日志太大 (128M)
- 幸好日志打得好,入参和操作人记录了下来,直接找到对方询问
- 分析java.hprof文件,很可能是Json反序列化问题(下图)
- 复现问题;如愿的再次打满CPU
我们的服务是企业内部系统,所以操作起来简单很多,有了日志追溯,进程僵死打印的java.hprof文件,极有助于本次故障的定位
本次问题的根源是依赖的上游服务返回的测试数据,大Json(128M),在我们反序列化时候,直接致使进程僵死
所以必须做好以下准备,对应线上问题
1、依赖其他服务都必须保有不可信的心,像这样的不正常大Json,不予处理,配好告警
2、方法的出入参尽可能打印日志(如果是极高并发的系统,另当考虑)
3、JVM启动参数必须有以下配置
-XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/var/www/logs