【问题标题】:OutOfMemoryError while deploying a war from Jenkins to Tomcat将战争从 Jenkins 部署到 Tomcat 时出现 OutOfMemoryError
【发布时间】:2015-04-16 15:42:57
【问题描述】:

我使用以下 shell 命令从 Jenkins 部署我的应用程序:

rm -rf E:/FooTomcat/apache-tomcat-7.0.55/webapps/foo-web;
rm -rf E:/FooTomcat/apache-tomcat-7.0.55/webapps/foo-web.war;
sleep 2;
cp foo-web/target/foo-web-0.0.1-SNAPSHOT.war E:/FooTomcat/apache-tomcat-7.0.55/webapps/foo-web.war

通常在启动定期构建时,Tomcat 会耗尽内存并给出以下错误。

Feb 13, 2015 3:59:58 PM org.apache.catalina.startup.HostConfig deployWAR
INFO: Deploying web application archive E:\FooTomcat\apache-tomcat-7.0.55\webapps\foo-web.war
Feb 13, 2015 4:00:06 PM org.apache.catalina.startup.HostConfig deployWARs
SEVERE: Error waiting for multi-thread deployment of WAR files to complete
java.util.concurrent.ExecutionException: java.lang.OutOfMemoryError: PermGen space
    at java.util.concurrent.FutureTask.report(FutureTask.java:122)
    at java.util.concurrent.FutureTask.get(FutureTask.java:188)
    at org.apache.catalina.startup.HostConfig.deployWARs(HostConfig.java:818)
    at org.apache.catalina.startup.HostConfig.deployApps(HostConfig.java:488)
    at org.apache.catalina.startup.HostConfig.check(HostConfig.java:1658)

我有windows环境,通过cygwin执行shell。

是shell命令出了点问题,还是因为内存泄漏?我引入了 sleep 是为了给应用程序一些时间来取消部署。我从未尝试过增加睡眠时间。

谢谢。

【问题讨论】:

  • 有机会在 Java 8 下运行您的 Tomcat 吗?在 Java 8 中,Permanent Generation (PermGen) 空间被可扩展的 Metaspace 取代。
  • 你为什么不用tomcat manager webapp来代替呢?此外,您似乎正在“实时”服务器上运行此脚本,对吗?
  • @Seelenvirtuose 不,不可能用 Java 8 运行 tomcat。
  • @fge 是的,tomcat 服务在脚本运行时正在运行,它会影响部署吗?我不确定什么是“tomcat manager webapp”,我会google一下。
  • 嗯,它可能会影响它,是的,特别是因为你运行 Windows

标签: java shell tomcat deployment jenkins


【解决方案1】:

由于异常表明您的问题来自填充 PermGen 空间。它是内存的一部分,Java 存储有关您的类的元数据(比如说您加载的类的代码)。当你部署一个新的 web 应用程序时,你会添加新的类并增加 PermGen 的负载。更糟糕的是,当您在 90% 的情况下重新部署相同的应用程序时,使用过的类的先前版本保留在内存中,因此您不会从 PermGen 释放“旧”内存,而只是添加到它(90 % 估计来自使用 DataBase 驱动程序、使用 ThreadLocal 的框架、Scheduler 线程……实际上它几乎一直都在发生)。

默认的 permgen 太小了(比如 64M 或者一些荒谬的东西)。以更高的值启动 tomcat,您可以通过将 JVM 选项传递给 tomcat 来完成,例如:

JAVA_OPTS = -XX:MaxPermSize=512m -Xmx4024m

(首先将 perm 大小设置为 512MB,然后将堆大小设置为 4G,这对于现代系统来说很好)。

您在启动 tomcat 之前设置此变量,或者(我更喜欢这样,您可以修改 /bin/catalina 脚本以始终将它们设置在那里,这样您在启动时不会“忘记”它们再次使用tomcat)。

从 tomact 7 开始,当您取消部署应用程序时,tomcat 日志会显示保留在内存中的应用程序的警告(并填满您的 PermGen),您可能需要检查它们并尝试修复一些问题(更新框架、正确关闭你的线程池...)

【讨论】:

  • 我试过增加空间,这是我目前的配置:-Xms512m -Xmx1024m -XX:PermSize=512m -XX:MaxPermSize=2048m。对我来说看起来就足够了。
  • 但是它解决了你的问题吗?最大烫发大小为 2G 可能已经过时了,尤其是您的堆现在只有 1G。
  • 我昨天使用了一个 enw 配置,“-Xms512m -Xmx2048m -XX:PermSize=512m -XX:MaxPermSize=4096m”,在夜间构建中我又遇到了同样的错误。我有一个查询,但我需要在“catalina.sh”或“catalina.bat”中设置参数吗?
  • 在 windows bat 上,在 linux sh 上。如果 tomcat 在 Windows 上作为服务启动,我不确定(我猜也在 catalina.sh 中,但你应该检查一下)。当然你需要重启服务器。
  • 如果你去tomcat欢迎页面,管理器,服务器状态,你会设置当前的内存消耗和最大设置。检查它们是否与您的配置匹配。如果他们这样做并且您仍然收到异常,则说明您的应用程序有问题。取消部署应用程序时检查 tomcats 日志中的警告。 PermSize 的 4G 也太多了。
猜你喜欢
  • 2016-09-19
  • 1970-01-01
  • 2011-04-12
  • 2021-01-24
  • 2016-07-11
  • 1970-01-01
  • 1970-01-01
  • 2014-04-23
  • 1970-01-01
相关资源
最近更新 更多