ElasticSearch服务Java内存异常分析和排查解决
ElasticSearch服务Java内存异常分析和排查解决
1.ElasticSearch业务微服务日志排查
java.lang.IllegalStateException: Request cannot be executed; I/O reactor status: STOPPED
现象:
部署到测试环境之后,用户量大了之后接口报错,报错信息为:Request cannot be executed; I/O reactor status: STOPPED
后端程序处于假死状态,访问其他接口一直转圈,无法响应内容,重启程序之后一切正常,用户量大了之后又有此问题。
测试方法:
使用JMETER设置50个线程并发访问可以稳定复现此问题。压力测试
2.业务系统搜索,关键字: OutOfMemoryError
cat myProject-2024-05-09-3.log | grep "OutOfMemoryError"
org.springframework.web.util.NestedServletException: Handler dispatch failed; nested exception is java.lang.OutOfMemoryError: GC overhead limit exceeded
Consumer thread error, thread abort.java.lang.OutOfMemoryError: GC overhead limit exceeded
这个报错出现时,往往是因为JVM中的GC(Garbage Collection,垃圾回收)过于频繁,以至于大部分的CPU时间都在做GC操作,而无法正常执行程序,这时,就会抛出这个错误。
具体来说,如果超过98%的CPU时间被用来做GC,并且GC后可用的堆内存不足2%,那么将会抛出"java.lang.OutOfMemoryError: GC overhead limit exceeded"错误。
以上日志分析排查的方向转为:
后来发现就是因为OOM导致程序宕机,进而引发连接终止。 排查日志也找到了oom报错日志。
推断:
程序接口中将一块很大的数据存进JAVA集合中引发了oom,oom异常导致程序宕机,处于假死状态,进而导致ES-CLIENT和ES-SERVER端的http连接异常终止,然后org.apache.http.impl.nio.client.CloseableHttpAsyncClientBase.ensureRunning方法报异常。
SpringDataElasticsearch和ES-SERVER是长链接,只要报了OOM,当前和ES-SERVER的连接线程都将报异常,也就是说,虽然OOM只报了一次,但是可能有多个线程都在Asserts.check方法中报异常。
3.查看进程等,确定gc,heapDump.bin文件目录路径,查看xmx配置大小
ps aux --sort -rss | head
链接:ps top命令查看内存空间
https://www.cnblogs.com/oktokeep/p/16361896.html
USER PID %CPU %MEM VSZ RSS TTY STAT START TIME COMMAND
root 21722 14.6 4.5 11410052 1502980 ? Sl 16:51 5:47 /usr/local/java/bin/java -Djava.util.logging.config.file=/usr/local/myProject/conf/logging.properties -Djava.util.logging.manager=org.apache.juli.ClassLoaderLogManager -Djava.awt.headless=true -Dfile.encoding=UTF-8 -Dfastjson.parser.safeMode=true -server -Xms512m -Xmx1g -XX:MetaspaceSize=256m -XX:MaxMetaspaceSize=512m -XX:+PrintGCDetails -XX:+PrintGCDateStamps -Xloggc:/usr/local/myProject/logs/gc-20240509_165141.log -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/usr/local/myProject/logs/heapdump.bin -XX:+CMSParallelRemarkEnabled -XX:+ScavengeBeforeFullGC -XX:CMSInitiatingOccupancyFraction=75 -Djdk.tls.ephemeralDHKeySize=2048 -Djava.protocol.handler.pkgs=org.apache.catalina.webresources -Dorg.apache.catalina.security.SecurityListener.UMASK=0027 -Dignore.endorsed.dirs= -classpath /usr/local/myProject/bin/bootstrap.jar:/usr/local/myProject/bin/tomcat-juli.jar -Dcatalina.base=/usr/local/myProject -Dcatalina.home=/usr/local/myProject -Djava.io.tmpdir=/usr/local/myProject/temp org.apache.catalina.startup.Bootstrap start
4.找到tomcat服务里面的gc日志,确定问题,oom报错日志
Java HotSpot(TM) 64-Bit Server VM (25.171-b11) for linux-amd64 JRE (1.8.0_171-b11), built on Mar 28 2018 17:07:08 by "java_re" with gcc 4.3.0 20080428 (Red Hat 4.3.0-8)
Memory: 4k page, physical 32778396k(694320k free), swap 0k(0k free)
CommandLine flags: -XX:CMSInitiatingOccupancyFraction=75 -XX:+CMSParallelRemarkEnabled -XX:CompressedClassSpaceSize=528482304 -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/usr/local/myProject/logs/heapdump.bin -XX:InitialHeapSize=536870912 -XX:MaxHeapSize=1073741824 -XX:MaxMetaspaceSize=536870912 -XX:MetaspaceSize=268435456 -XX:+PrintGC -XX:+PrintGCDateStamps -XX:+PrintGCDetails -XX:+PrintGCTimeStamps -XX:+ScavengeBeforeFullGC -XX:+UseCompressedClassPointers -XX:+UseCompressedOops -XX:+UseParallelGC
Heap
PSYoungGen total 153088K, used 21054K [0x00000000eab00000, 0x00000000f5580000, 0x0000000100000000)
eden space 131584K, 16% used [0x00000000eab00000,0x00000000ebf8f870,0x00000000f2b80000)
from space 21504K, 0% used [0x00000000f4080000,0x00000000f4080000,0x00000000f5580000)
to space 21504K, 0% used [0x00000000f2b80000,0x00000000f2b80000,0x00000000f4080000)
ParOldGen total 349696K, used 0K [0x00000000c0000000, 0x00000000d5580000, 0x00000000eab00000)
object space 349696K, 0% used [0x00000000c0000000,0x00000000c0000000,0x00000000d5580000)
Metaspace used 5422K, capacity 5552K, committed 5888K, reserved 1056768K
class space used 608K, capacity 664K, committed 768K, reserved 1048576K
5.解决思路:
1.增大堆空间:Java的堆空间是用来存储对象实例的,如果堆空间不足,那么GC就需要更频繁的运行以回收内存空间,进而造成上述的错误。因此,增大堆空间可以有效减轻GC的压力,从而避免这个错误。
-Xms512m -Xmx1g >> 扩大内存空间 -Xmx2g
2.优化代码:另一个可能的解决思路是优化你的代码,减少对象实例的创建,或者及时地释放不再使用的对象实例,减少GC的工作量。
推荐使用MemoryAnalyzer工具分析溢出代码,于是官网下载,下载地址为:https://www.eclipse.org/downloads/download.php?file=/mat/1.11.0/rcp/MemoryAnalyzer-1.11.0.20201202-win32.win32.x86_64.zip
解决内存溢出,确定gc,heapDump.bin文件目录路径
-XX:+PrintGCDateStamps -Xloggc:/usr/local/myProject/logs/gc-20240509_165141.log -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/usr/local/myProject/logs/heapdump.bin
6.Java优化代码片段示例:
SearchResponse searchResponse = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);
//数据转换方法
OrderVO<?> result = transform(reqVO, result(searchResponse.getHits().getHits()), searchResponse);
//设置为null 关键 java 大对象快速回收
searchResponse = null; protected List<OrderInfoVO> result(SearchHit[] searchHits) {
List<OrderInfoVO> orderInfoContent = new ArrayList<>();
Gson gson = new GsonBuilder().registerTypeAdapter(LocalDateTime.class, (JsonDeserializer<LocalDateTime>) (json, type, jsonDeserializationContext) ->
LocalDateTime.parse(json.getAsJsonPrimitive().getAsString(), DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss")))
.registerTypeAdapter(LocalDate.class, (JsonDeserializer<LocalDate>) (json, type, jsonDeserializationContext) ->
LocalDate.parse(json.getAsJsonPrimitive().getAsString(), DateTimeFormatter.ofPattern("yyyy-MM-dd"))).create();
for (SearchHit hit : searchHits) {
String sourceAsString = hit.getSourceAsString();
OrderInfoVO vo = gson.fromJson(sourceAsString, OrderInfoVO.class);
orderInfoContent.add(vo);
//设置为null 关键 java 大对象快速回收
hit = null;
}
return orderInfoContent;
}
ElasticSearch服务Java内存异常分析和排查解决的更多相关文章
- Java内存泄漏分析系列之二:jstack生成的Thread Dump日志结构解析
原文地址:http://www.javatang.com 一个典型的thread dump文件主要由一下几个部分组成: 上图将JVM上的线程堆栈信息和线程信息做了详细的拆解. 第一部分:Full th ...
- java内存溢出分析工具
http://www.cnblogs.com/preftest/archive/2011/12/08/2281322.html java内存溢出分析工具:jmap使用实战 在一次解决系统tomcat老 ...
- C#连接solr时提示 java内存异常 (jetty和tomcat哪个更High) java.lang.OutOfMemoryError
C#连接solr时提示 java内存异常 java.lang.OutOfMemoryError 时间:20180130 09:51:13.329,消息:异常消息<?xml version=& ...
- Java 内存溢出分析
原文地址:Java 内存溢出分析 博客地址:http://www.moonxy.com 一.前言 Java 的 JVM 的内存一般可分为 3 个区:堆(heap).栈(stack)和方法区(metho ...
- 华为云数据库GaussDB(for Cassandra)揭秘第二期:内存异常增长的排查经历
摘要:华为云数据库GaussDB(for Cassandra) 是一款基于计算存储分离架构,兼容Cassandra生态的云原生NoSQL数据库:它依靠共享存储池实现了强一致,保证数据的安全可靠. 本文 ...
- java内存溢出分析(二)
我们继续java内存溢出分析(一)的分析,点击Details>按钮,显示如下图,我们发现有一个对象数量达到280370216个,再点击其中的List objects 点击后,显示下图 至此,我们 ...
- Java内存泄漏分析系列之五:常见的Thread Dump日志案例分析
原文地址:http://www.javatang.com 症状及解决方案 下面列出几种常见的症状即对应的解决方案: CPU占用率很高,响应很慢 按照<Java内存泄漏分析系列之一:使用jstac ...
- Java内存原型分析:基本知识
转载: Java内存原型分析:基本知识 java虚拟机内存原型 寄存器:我们在程序中无法控制 栈:存放基本类型的数据和对象的引用,但对象本身不存放在栈中,而是存放在堆中 堆:存放用new产生的数据 静 ...
- Java ConcurrentModificationException 异常分析与解决方案
Java ConcurrentModificationException 异常分析与解决方案http://www.2cto.com/kf/201403/286536.html java.util.Co ...
- (转)java内存分配分析/栈内存、堆内存
转自(http://blog.csdn.net/qh_java/article/details/9084091) java内存分配分析/栈内存.堆内存 java内存分配分析 本文将由浅入深详细介绍Ja ...
随机推荐
- Serverless 应用优化四则秘诀
简介:Serverless 架构下,虽然我们更多精力是关注我们的业务代码,但是实际上对于一些配置和成本也是需要进行关注的,并且在必要的时候,还需要根据配置与成本进行对我们的 Serverless 应 ...
- Joint Consensus两阶段成员变更的单步实现
简介: Raft提出的两阶段成员变更Joint Consensus是业界主流的成员变更方法,极大的推动了成员变更的工程应用.但Joint Consensus成员变更采用两阶段,一次变更需要提议两条日 ...
- OLAP系列之分析型数据库clickhouse集群部署(二)
一.环境准备 IP 配置 clickhouse版本 zookeeper版本 myid 192.168.12.88 Centos 7.9 4核8G 22.8.20.11 3.7.1 3 192.168. ...
- R2_ES中数据的存储测试
基本概念:ES(一): 架构及原理 关系数据库 ⇒ 数据库 ⇒ 表 ⇒ 行 ⇒ 列(Columns) Elasticsearch ⇒ 索引(Index) ⇒ 类型(Type) ⇒ 文档(Documen ...
- Go语言连接Redis之go-redis使用指南
参考下面的连接: https://mp.weixin.qq.com/s?__biz=MzU5MjAxMDc1Ng==&mid=2247483899&idx=1&sn=b103c ...
- Pr 的导出视频
导出视频 https://www.bilibili.com/video/BV1Vt411n7Bb?p=7
- Android Framework学习之系统启动流程
最近抽空看了framework一些内存,总结一下,留作后续回顾复习
- 西门子PLC设备如何接入AIRIOT物联网低代码平台 ?
西门子PLC设备广泛应用于工业控制领域,高性能和稳定是它最大的优势.下面我们要把西门子300 1200 1500 PLC设备连接到AIRIOT物联网低代码平台,具体操作如下所示: 西门子驱动配置(配套 ...
- 给大家分享一套非常棒的python机器学习课程
给大家分享一套非常棒的python机器学习课程--<AI小天才:让小学生轻松掌握机器学习>,2024年5月完结新课,提供配套的代码+笔记+软件包下载!学完本课程,可以轻松掌握机器学习的全面 ...
- web开发遇到的坑之360浏览器缓存问题
再使用360浏览器,浏览我自己开发的一个配置的web管理后台时,发现,使用ctrl+F5都不能刷新表格的数据,还有,我添加字段时,明明是添加成功的,用sql再数据库查都能查出来.但表格里就是不显示.我 ...