掉坑里的背景
最近公司的项目部署,一个不小心的就踩到了这个坑。为了收敛对外暴露的端口数量,所以将许多工程都部署在里一个tomcat下,早期只有2个,并没有任何问题,后来工程增加至7个时,发现tomcat启动之后不久会自杀。通过一些手段解决该问题,后期需要添加访问path后,需要配置很高的内存才可以启动tomcat。
具体现象
- tomcat启动后不久进程会自杀,且无法查询到相关启动的端口。
- 在catalina.out中可找到'java.lang.OutOfMemoryError: PermGen space'字样,显示内存溢出。
- 需要不断的增加tomcat内存才可能启动工程。
原因分析
tomcat在加载工程的时候会去读取conf/server.xml文件。
<Host name="localhost" appBase="webapps" unpackWARs="true" autoDeploy="true">
这行内容表示工程默认路径是webapps(相对路径),tomcat启动后会将webapps路径内的工程均加载一遍。为了有具体的url访问path,我们在host标签内还添加了<Context docBase="XXXX" path="/xxxx" reloadable="true"/>
,以便客户端使用path/xxxx时,访问到具体的工程路径为XXXX(相对路径)。但是这样配置会导致tomcat先加载以便 appBase下的工程,再加载一遍docBase的工程,需要分配大量的内存,很容易溢出。
解决办法
新建webroot 目录作为appBase。具体配置为appBase="webroot"
修改docBase的内容。在原路径前加"../webapps/"具体配置为docBase="../webapps/原内容"
重启tomcat即可。
备注
如需要添加tomcat启动内存参数,详细解释如下
-server:一定要作为第一个参数,在多个CPU时性能佳
-Xms:java Heap初始大小。 默认是物理内存的1/64。
-Xmx:java heap最大值。建议均设为物理内存的一半。不可超过物理内存。
-XX:PermSize:设定内存的永久保存区初始大小,缺省值为64M。
-XX:MaxPermSize:设定内存的永久保存区最大 大小,缺省值为64M
e.g.
修改TOMCAT_HOME/bin/catalina.sh位置cygwin=false前。
JAVA_OPTS="-server -Xms256m -Xmx512m -XX:PermSize=64M -XX:MaxPermSize=128m"