搭建排查tomcat内存溢出问题的调试环境

news2024/11/20 2:33:09

上个月赶工上线的门户网站,由于种种原因导致部署到线上服务器后每隔一段时间后就会导致tomcat内存溢出,今天我就要来直面这个棘手的问题。

要解决的问题对我来说还是有点难度的,原因有二:

  1. 代码不是我写的;
  2. 我对java并不熟悉。

废话不多说,就由我这个小白依靠GG带领大家来启程吧!

凭借我多年的编程经验,我认为首先要找到趁手的工具,那么,问题就来了,挖掘机技术到底哪家强?……

好吧,GG一下,可以很容易查到很多用来监控jvm实时状态的工具,我们以jconsole为第一款尝试的工具吧。

jconsole

这里要说明的是,我们需要搭建的监控环境是在win桌面机上远程监控一台centos服务器。按照网上说的,搭建起这么一个环境没有多大难度,大家可以参考这里:传送门。

如果你像我一样碰到了timeout提示,那多半就是centos防火墙拦截导致的,可以暂时关闭防火墙再尝试一下:

/etc/init.d/iptables stop

好的,终于有了一个监控界面了,是不是感觉心里敞亮了不少呢?不过我感觉还是太笼统了,只能大概知道jvm的状况,而对于我们要排查代码导致的内存泄露问题似乎并没有帮到太大的忙~~

不过可以通过提供的一些信息来判断是否配置了比较合理的参数,比方说可以通过GC时间看出是否给tomcat分配了适当的内存大小,尽可能的设置一个合理的内存来减少gc的次数和耗时。

那我们接下来换哪个工具呢?

JProfiler

好吧,上大杀器!无需我多讲,我相信没有人会对我的选择有质疑吧?哇哈哈哈哈哈~~不过JProfiler是个商用产品,钱花到位才能享受生活,这一点儿错都没有。

大家可以参考下面这些链接,相信你们很快就能搭建成功:

传送门1,传送门2,传送门3

按照上面提供的信息,我相信你很顺利就能安装部署完毕jprofiler(毕竟是商用产品嘛,肯定做的足够简单),但如果你和我一样是第一次用这个玩意儿,肯定会被它的默认界面震出翔!

不要pia,先阅读一下这篇文章: 传送门。

这里要提到的一点是,可能是软件版本的原因,按照上面前辈说的方法我却死活查不到方法调用Tree,查了一下GG才发现是需要调整配置选项,如下图:

查看调用轨迹

我这属于暴力解决吧,毕竟我把能开启的选项都选中了,不过想得到的问题也就是速度慢点,对于远程连接方式来说带宽占用多一些而已吧~~

测试代码

找到了趁手的兵器,下一步就是要挖的坑了!哦,no,是一段会造成内存溢出的测试代码,我简单地修改了一下tomcat提供的例子中的HelloWorldExample.java

import java.io.IOException;
import java.io.PrintWriter;
import java.util.ResourceBundle;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import java.util.ArrayList;

public class HelloWorldExample extends HttpServlet {

    private static final long serialVersionUID = 1L;

    private static ArrayList list = new ArrayList();

    @Override
    public void doGet(HttpServletRequest request,
                      HttpServletResponse response)
        throws IOException, ServletException
    {
        ResourceBundle rb =
            ResourceBundle.getBundle("LocalStrings",request.getLocale());
        response.setContentType("text/html");
        PrintWriter out = response.getWriter();

        out.println("<html>");
        out.println("<head>");
        out.println("</head>");
        out.println("<body bgcolor=\"white\">");
        
	
	for(int i=0; i < 1000; i++){
		//Object o = new String("by kazaff, index is :" + i);
		HelloWorldExample.list.add(new kazaffBean());
		//o = null;	
	}	

	out.println("<div>kazaff in here!!!!!!!</div>");	

	out.println("</body>");
        out.println("</html>");

    }
}

class kazaffBean {
	String name= "";
}

然后我们还要手动编译修改后的java代码,进入到/usr/local/apache-tomcat-7.0.53/webapps/examples/WEB-INF/classes/HelloWorldExample.java所在的文件夹中,执行下面的命令:

 javac HelloWorldExample.java -cp /usr/local/apache-tomcat-7.0.53/lib/servlet-api.jar 

当然,你的tomcat路径和我的很可能不同,酌情修改即可~~

然后我们重启tomcat,对了,重启之前最好改一下分配给tomcat的内存上限,改小一些,有助于问题快速的暴露:

-Xms20m -Xmx20m -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/www/java-OOM/

后面的两个-XX参数是用来让jvm在出现OOM后自动保存内存堆栈快照信息用的,方便我们排查问题。

重启吧,然后为了加速内存溢出,我们可以使用apache自带的ab做压力测试:

ab -c 100 -n 10000 http://192.168.153.128:81/examples/jsp/

执行上面的这条命令后,基本上tomcat肯定就已经挂掉了,注意,我说的是tomcat挂掉了!也就是说你在终端中执行jps命令,不再会看到Bootstrap这个进程了!我之所以强调这一点,是因为我在测试中发现直接导致jconsole断开连接,并且再也无法建立连接。

而奇怪的是,jprofiler照常可以连接并获取到远程服务器上的jvm的监控数据,这种情况一度使我陷入深深的迷惘。因为我在tomcat的logs里死活找不到任何关于内存溢出或其他异常的记录,直到我的目光落在终端上:

Exception: java.lang.OutOfMemoryError thrown from the UncaughtExceptionHandler in thread "http-bio-81-exec-13"
……
java.lang.OutOfMemoryError: GC overhead limit exceeded
……
java.lang.OutOfMemoryError: Java heap space
……
Exception in thread "RMI TCP Connection(idle)" java.lang.OutOfMemoryError: Java heap space

这才是乖孩子嘛,就应该是这样的才对嘛~~不过还有几个点想不明白:

  • 虽然jps已经查不到tomcat的进程,但是从jprofiler的线程监控中还是可以看到相关的线程,如下图:

  • 既然tomcat都已经挂了,为什么jprofiler没有像jconsole那样连接断开呢?

我这种小白目前是搞不定这两个问题了,还是抛到社区给大牛们分析吧。我们继续往下走~

关于内存溢出

通过我上面列出的异常信息,已经是非常常见的了,对于一些java老鸟而言肯定是再熟悉不过的了!不过我还是找到了一篇排版不咋滴但是比较全面的文章: 传送门。

到此为止,就算做好了一切准备,可以去真正的项目上搞了!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1899680.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【操作与配置】VSCode配置Python及Jupyter

Python环境配置 可以参见&#xff1a;【操作与配置】Python&#xff1a;CondaPycharm_pycharmconda-CSDN博客 官网下载Python&#xff1a;http://www.python.org/download/官网下载Conda&#xff1a;Miniconda — Anaconda documentation VSCode插件安装 插件安装后需重启V…

14-28 剑和诗人2 - 高性能编程Bend和Mojo

介绍&#xff1a; 在不断发展的计算世界中&#xff0c;软件和硬件之间的界限变得越来越模糊。随着我们不断突破技术可能性的界限&#xff0c;对能够利用现代硬件功能的高效、可扩展的编程语言的需求从未如此迫切。 Bend和 Mojo是编程语言领域的两种新秀&#xff0c;它们有望弥…

HumbleBundle7月虚幻捆绑包30件军事题材美术模型沙漠自然环境大逃杀模块化建筑可定制武器包二战现代坦克飞机道具丧尸士兵角色模型20240705

HumbleBundle7月虚幻捆绑包30件军事题材美术模型沙漠自然环境大逃杀模块化建筑可定制武器包二战现代坦克飞机道具丧尸士兵角色模型202407051607 这次HumbleBundle捆绑包是UE虚幻军事题材的&#xff0c;内容非常多。 有军事基地、赛博朋克街区、灌木丛景观环境等 HB捆绑包虚幻…

【Python】基于KMeans的航空公司客户数据聚类分析

&#x1f490;大家好&#xff01;我是码银~&#xff0c;欢迎关注&#x1f490;&#xff1a; CSDN&#xff1a;码银 公众号&#xff1a;码银学编程 实验目的和要求 会用Python创建Kmeans聚类分析模型使用KMeans模型对航空公司客户价值进行聚类分析会对聚类结果进行分析评价 实…

springboot 社区垃圾回收处理小程序-计算机毕业设计源码71905

摘要 在数字化高速发展的今天&#xff0c;随着Spring Boot等轻量级框架的广泛应用&#xff0c;各种小程序、微服务如雨后春笋般涌现&#xff0c;极大地丰富了我们的软件生态系统。然而&#xff0c;伴随着这些应用的迅速增加&#xff0c;垃圾回收处理成为了一个不可忽视的问题。…

Mybatis原生使用

一、MyBatis初次使用 2.1 环境搭建步骤 MyBatis 的 API &#xff1a; https://mybatis.org/mybatis-3/zh/getting-started.html 1.引入依赖包 2.准备核心配置件 db.properties drivercom.mysql.cj.jdbc.Driver urljdbc:mysql://123.57.206.19:3306/demo?useUnicodetrue&am…

步进电机改伺服电机

步进电机&#xff1a; 42&#xff1a;轴径5mm 57&#xff1a;轴径8mm 86&#xff1a;轴径14mm 【86CME120闭环】// 12牛米 伺服电机&#xff1a; 40&#xff1a; 60&#xff1a; 80&#xff1a; 86&#xff1a; ECMA——C 1 0910 R S 4.25A 轴径…

26.5 Django模板层

1. 模版介绍 在Django中, 模板(Templates)主要用于动态地生成HTML页面. 当需要基于某些数据(如用户信息, 数据库查询结果等)来动态地渲染HTML页面时, 就会使用到模板.以下是模板在Django中使用的几个关键场景: * 1. 动态内容生成: 当需要根据数据库中的数据或其他动态数据来生…

Hook 实现 Windows 系统热键屏蔽(二)

目录 前言 一、介绍用户账户控制&#xff08;UAC&#xff09; 1.1 什么是 UAC &#xff1f; 2.2 UAC 运行机制的概述 2.3 分析 UAC 提权参数 二、 NdrAsyncServerCall 函数的分析 2.1 函数声明的解析 2.2 对 Winlogon 的逆向 2.3 对 rpcrt4 的静态分析 2.4 对 rpcrt4…

240705_昇思学习打卡-Day17-基于 MindSpore 实现 BERT 对话情绪识别

240705_昇思学习打卡-Day17-基于 MindSpore 实现 BERT对话情绪识别 近期确实太忙&#xff0c;此处仅作简单记录&#xff1a; 模型简介 BERT全称是来自变换器的双向编码器表征量&#xff08;Bidirectional Encoder Representations from Transformers&#xff09;&#xff0c…

14-32 剑和诗人6 - GenAI 重塑 SRE 和云工程实践

在不断发展的软件开发和运营领域&#xff0c;各种学科的融合催生了新的范式和实践&#xff0c;旨在简化流程、加强协作和推动创新。DevSecOps、站点可靠性工程 (SRE)、平台工程和云工程已成为支持现代软件系统的重要支柱&#xff0c;每个支柱都解决了独特的挑战和要求。 然而&…

Fastapi 项目第二天首次访问时数据库连接报错问题Can‘t connect to MySQL server

问题描述 Fastapi 项目使用 sqlalchemy 连接的mysql 数据库&#xff0c;每次第二天首次访问数据库相关操作&#xff0c;都会报错&#xff1a;sqlalchemy.exc.OperationalError: (pymysql.err.OperationalError) (2003, “Can’t connect to MySQL server on ‘x.x.x.x’ ([Err…

【Unity数据交互】Unity中使用二进制进行数据持久化

&#x1f468;‍&#x1f4bb;个人主页&#xff1a;元宇宙-秩沅 &#x1f468;‍&#x1f4bb; hallo 欢迎 点赞&#x1f44d; 收藏⭐ 留言&#x1f4dd; 加关注✅! &#x1f468;‍&#x1f4bb; 本文由 秩沅 原创 &#x1f468;‍&#x1f4bb; 专栏交流&#x1f9e7;&…

2.4G无线收发芯片 XL2401D,SOP16封装,集成单片机,高性价比

XL2401D 芯片是工作在2.400~2.483GHz世界通用ISM频段&#xff0c;片内集成了九齐 NY8A054E单片机的SOC无线收发芯片。芯片集成射频收发机、频率收生器、晶体振荡器、调制解调器等功能模块&#xff0c;并且支持一对多组网和带ACK的通信模式。发射输出功率、工作频道以及通信数据…

vue3自定义全局指令和局部指令

1.全局指令 el&#xff1a;指令绑定到的DOM元素&#xff0c;可以用于直接操作当前元素&#xff0c;默认传入钩子的就是el参数&#xff0c;例如我们开始实现的focus指令&#xff0c;就是直接操作的元素DOM binding&#xff1a;这是一个对象&#xff0c;包含以下属性&#xff1a;…

Zynq系列FPGA实现SDI视频编解码,基于GTX高速接口,提供5套工程源码和技术支持

目录 1、前言工程概述免责声明 2、相关方案推荐本博已有的 SDI 编解码方案本方案在Xilinx--Kintex系列FPGA上的应用 3、详细设计方案设计原理框图SDI 输入设备Gv8601a 均衡器GTX 解串与串化SMPTE SD/HD/3G SDI IP核BT1120转RGB图像缓存视频读取控制HDMI输出RGB转BT1120Gv8500 驱…

玩转云服务:Oracle Cloud甲骨文永久免费云服务器注册及配置指南

上一篇&#xff0c;带大家分享了&#xff1a;如何薅一台腾讯云服务器。 不过&#xff0c;只有一个月免费额度&#xff0c;到期后需要付费使用。 相对而言&#xff0c;海外云厂商更加慷慨一些&#xff0c;比如微软Azure、甲骨文、亚马逊AWS等。 甲骨文2019年9月就推出了永久免…

信用卡没逾期就万事大吉了吗?

6月28日&#xff0c;中国人民银行揭晓了《2024年第一季度支付体系概览》&#xff0c;数据显示&#xff0c;截至本季度末&#xff0c;信用卡及借贷合一卡的总量为7.6亿张&#xff0c;与上一季度相比&#xff0c;这一数字微降了0.85个百分点。同时&#xff0c;报告还指出&#xf…

华为OD机试 - 跳马 - 广度优先搜索BFS(Java 2024 D卷 200分)

华为OD机试 2024D卷题库疯狂收录中&#xff0c;刷题点这里 专栏导读 本专栏收录于《华为OD机试&#xff08;JAVA&#xff09;真题&#xff08;D卷C卷A卷B卷&#xff09;》。 刷的越多&#xff0c;抽中的概率越大&#xff0c;每一题都有详细的答题思路、详细的代码注释、样例测…

JMeter:循环控制器While Controller的用法小结

前言 在之前的博文“JMeter案例优化&#xff1a;测试执行结束后&#xff0c;实现tearDown的几种方式”中&#xff0c;尝试了JMeter的循环控制器While Controller&#xff0c;发现还有点小复杂&#xff0c;将学习过程记录下来&#xff0c;免得遗忘。 注&#xff1a;我使用的是…