解决IntelliJ IDEA报错:调用方法[manageApp]时发生异常java.lang.IllegalStateException: 启动子级时出错

问题描述:

  笔者将一个在 Tomcat 安装目录下的文件夹 webapps 部署成功且运行正常的 Web 应用,改成使用 IntelliJ IDEA 工程中的文件夹 webapp 来部署。这之中,笔者没有改动原 Web 应用文件夹内的任何文件,但却在 IntelliJ IDEA 中运行时直接 报错 1 ^1 1 。这之后,笔者改使用该工程来部署其它原来在此 IntelliJ IDEA 工程中部署成功的任何 Web 应用,此时均报与之前相同的 错误 2 ^2 2

笔者报错时的运行环境:

  • JDK 13.0.2

  • Maven 3.6.3

  • Tomcat 9.0.41(Servlet 4.0,JSP 2.3)

  • IntelliJ IDEA 2020.1.2 (Ultimate Edition)

  这个报错的信息如下:

XX-XXX-202X XX:XX:XX.XXX 严重 [RMI TCP Connection(3)-127.0.0.1] org.apache.tomcat.util.modeler.BaseModelMBean.invoke 调用方法[manageApp]时发生异常
	java.lang.IllegalStateException: 启动子级时出错
		at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:720)
		at org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:690)
		at org.apache.catalina.core.StandardHost.addChild(StandardHost.java:706)
		at org.apache.catalina.startup.HostConfig.manageApp(HostConfig.java:1727)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
		at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
		at java.base/java.lang.reflect.Method.invoke(Method.java:567)
		at org.apache.tomcat.util.modeler.BaseModelMBean.invoke(BaseModelMBean.java:288)
		at java.management/com.sun.jmx.interceptor.DefaultMBeanServerInterceptor.invoke(DefaultMBeanServerInterceptor.java:809)
		at java.management/com.sun.jmx.mbeanserver.JmxMBeanServer.invoke(JmxMBeanServer.java:801)
		at org.apache.catalina.mbeans.MBeanFactory.createStandardContext(MBeanFactory.java:459)
		at org.apache.catalina.mbeans.MBeanFactory.createStandardContext(MBeanFactory.java:408)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
		at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
		at java.base/java.lang.reflect.Method.invoke(Method.java:567)
		at org.apache.tomcat.util.modeler.BaseModelMBean.invoke(BaseModelMBean.java:288)
		at java.management/com.sun.jmx.interceptor.DefaultMBeanServerInterceptor.invoke(DefaultMBeanServerInterceptor.java:809)
		at java.management/com.sun.jmx.mbeanserver.JmxMBeanServer.invoke(JmxMBeanServer.java:801)
		at java.management/com.sun.jmx.remote.security.MBeanServerAccessController.invoke(MBeanServerAccessController.java:468)
		at java.management.rmi/javax.management.remote.rmi.RMIConnectionImpl.doOperation(RMIConnectionImpl.java:1466)
		at java.management.rmi/javax.management.remote.rmi.RMIConnectionImpl$PrivilegedOperation.run(RMIConnectionImpl.java:1307)
		at java.base/java.security.AccessController.doPrivileged(AccessController.java:691)
		at java.management.rmi/javax.management.remote.rmi.RMIConnectionImpl.doPrivilegedOperation(RMIConnectionImpl.java:1406)
		at java.management.rmi/javax.management.remote.rmi.RMIConnectionImpl.invoke(RMIConnectionImpl.java:827)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
		at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
		at java.base/java.lang.reflect.Method.invoke(Method.java:567)
		at java.rmi/sun.rmi.server.UnicastServerRef.dispatch(UnicastServerRef.java:359)
		at java.rmi/sun.rmi.transport.Transport$1.run(Transport.java:200)
		at java.rmi/sun.rmi.transport.Transport$1.run(Transport.java:197)
		at java.base/java.security.AccessController.doPrivileged(AccessController.java:691)
		at java.rmi/sun.rmi.transport.Transport.serviceCall(Transport.java:196)
		at java.rmi/sun.rmi.transport.tcp.TCPTransport.handleMessages(TCPTransport.java:562)
		at java.rmi/sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(TCPTransport.java:796)
		at java.rmi/sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.lambda$run$0(TCPTransport.java:677)
		at java.base/java.security.AccessController.doPrivileged(AccessController.java:391)
		at java.rmi/sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(TCPTransport.java:676)
		at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
		at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
		at java.base/java.lang.Thread.run(Thread.java:830)
	Caused by: org.apache.catalina.LifecycleException: 无法启动组件[StandardEngine[Catalina].StandardHost[localhost].StandardContext[/XXX_war_exploded]]
		at org.apache.catalina.util.LifecycleBase.handleSubClassException(LifecycleBase.java:440)
		at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:198)
		at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:717)
		... 42 more
	Caused by: java.lang.IllegalArgumentException: 找到多个名为XXX的片段。这是不合法的相对排序。有关详细信息,请参阅Servlet规范的第8.2.2 2c节。考虑使用绝对排序。
		at org.apache.tomcat.util.descriptor.web.WebXml.orderWebFragments(WebXml.java:2260)
		at org.apache.tomcat.util.descriptor.web.WebXml.orderWebFragments(WebXml.java:2218)
		at org.apache.catalina.startup.ContextConfig.webConfig(ContextConfig.java:1293)
		at org.apache.catalina.startup.ContextConfig.configureStart(ContextConfig.java:985)
		at org.apache.catalina.startup.ContextConfig.lifecycleEvent(ContextConfig.java:303)
		at org.apache.catalina.util.LifecycleBase.fireLifecycleEvent(LifecycleBase.java:123)
		at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5082)
		at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:183)
		... 43 more
XX-XXX-202X XX:XX:XX.XXX 严重 [RMI TCP Connection(3)-127.0.0.1] org.apache.tomcat.util.modeler.BaseModelMBean.invoke 调用方法[createStandardContext]时发生异常
	javax.management.RuntimeOperationsException: 调用方法[manageApp]时发生异常
		at org.apache.tomcat.util.modeler.BaseModelMBean.invoke(BaseModelMBean.java:297)
		at java.management/com.sun.jmx.interceptor.DefaultMBeanServerInterceptor.invoke(DefaultMBeanServerInterceptor.java:809)
		at java.management/com.sun.jmx.mbeanserver.JmxMBeanServer.invoke(JmxMBeanServer.java:801)
		at org.apache.catalina.mbeans.MBeanFactory.createStandardContext(MBeanFactory.java:459)
		at org.apache.catalina.mbeans.MBeanFactory.createStandardContext(MBeanFactory.java:408)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
		at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
		at java.base/java.lang.reflect.Method.invoke(Method.java:567)
		at org.apache.tomcat.util.modeler.BaseModelMBean.invoke(BaseModelMBean.java:288)
		at java.management/com.sun.jmx.interceptor.DefaultMBeanServerInterceptor.invoke(DefaultMBeanServerInterceptor.java:809)
		at java.management/com.sun.jmx.mbeanserver.JmxMBeanServer.invoke(JmxMBeanServer.java:801)
		at java.management/com.sun.jmx.remote.security.MBeanServerAccessController.invoke(MBeanServerAccessController.java:468)
		at java.management.rmi/javax.management.remote.rmi.RMIConnectionImpl.doOperation(RMIConnectionImpl.java:1466)
		at java.management.rmi/javax.management.remote.rmi.RMIConnectionImpl$PrivilegedOperation.run(RMIConnectionImpl.java:1307)
		at java.base/java.security.AccessController.doPrivileged(AccessController.java:691)
		at java.management.rmi/javax.management.remote.rmi.RMIConnectionImpl.doPrivilegedOperation(RMIConnectionImpl.java:1406)
		at java.management.rmi/javax.management.remote.rmi.RMIConnectionImpl.invoke(RMIConnectionImpl.java:827)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
		at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
		at java.base/java.lang.reflect.Method.invoke(Method.java:567)
		at java.rmi/sun.rmi.server.UnicastServerRef.dispatch(UnicastServerRef.java:359)
		at java.rmi/sun.rmi.transport.Transport$1.run(Transport.java:200)
		at java.rmi/sun.rmi.transport.Transport$1.run(Transport.java:197)
		at java.base/java.security.AccessController.doPrivileged(AccessController.java:691)
		at java.rmi/sun.rmi.transport.Transport.serviceCall(Transport.java:196)
		at java.rmi/sun.rmi.transport.tcp.TCPTransport.handleMessages(TCPTransport.java:562)
		at java.rmi/sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run0(TCPTransport.java:796)
		at java.rmi/sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.lambda$run$0(TCPTransport.java:677)
		at java.base/java.security.AccessController.doPrivileged(AccessController.java:391)
		at java.rmi/sun.rmi.transport.tcp.TCPTransport$ConnectionHandler.run(TCPTransport.java:676)
		at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
		at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
[202X-XX-XX XX:XX:XX.XX,XXX] Artifact XXX:war exploded: Error during artifact deployment. See server log for details.
		at java.base/java.lang.Thread.run(Thread.java:830)
	Caused by: java.lang.IllegalStateException: 启动子级时出错
		at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:720)
		at org.apache.catalina.core.ContainerBase.addChild(ContainerBase.java:690)
		at org.apache.catalina.core.StandardHost.addChild(StandardHost.java:706)
		at org.apache.catalina.startup.HostConfig.manageApp(HostConfig.java:1727)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
		at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
		at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
		at java.base/java.lang.reflect.Method.invoke(Method.java:567)
		at org.apache.tomcat.util.modeler.BaseModelMBean.invoke(BaseModelMBean.java:288)
		... 34 more
	Caused by: org.apache.catalina.LifecycleException: 无法启动组件[StandardEngine[Catalina].StandardHost[localhost].StandardContext[/XXX_war_exploded]]
		at org.apache.catalina.util.LifecycleBase.handleSubClassException(LifecycleBase.java:440)
		at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:198)
		at org.apache.catalina.core.ContainerBase.addChildInternal(ContainerBase.java:717)
		... 42 more
	Caused by: java.lang.IllegalArgumentException: 找到多个名为XXX的片段。这是不合法的相对排序。有关详细信息,请参阅Servlet规范的第8.2.2 2c节。考虑使用绝对排序。
		at org.apache.tomcat.util.descriptor.web.WebXml.orderWebFragments(WebXml.java:2260)
		at org.apache.tomcat.util.descriptor.web.WebXml.orderWebFragments(WebXml.java:2218)
		at org.apache.catalina.startup.ContextConfig.webConfig(ContextConfig.java:1293)
		at org.apache.catalina.startup.ContextConfig.configureStart(ContextConfig.java:985)
		at org.apache.catalina.startup.ContextConfig.lifecycleEvent(ContextConfig.java:303)
		at org.apache.catalina.util.LifecycleBase.fireLifecycleEvent(LifecycleBase.java:123)
		at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5082)
		at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:183)
		... 43 more

  笔者在经过反复试验排错后,终于找到了根因。原来笔者在此 IntelliJ IDEA 工程中使用的是 Maven 来构建项目的,而 Maven 中已经有了设置依赖的方法——通过文件 pom.xml 来设置,但在 Web 应用中是通过在 Web 应用下的目录 WEB-INF\lib 来设置的。如果同时设置了这两者,这就导致冲突,从而引发上面的 报错 1 ^1 1 。同理,如果在 IntelliJ IDEA 中设置了 Sources Root(源代码根目录),然后又在文件夹 WEB-INF 下投入了目录 classes,这同样会导致冲突。因此,解决 报错 1 ^1 1 的方法就是:

  • 方法 1:只使用本方法构成项目的 Java 源文件、依赖(如果同时掺杂了其它方法,删除之):

    • 源文件:选择 Web 应用下的目录 WEB-INF\classes 作为 Web 应用所需要的已编译 Java 源文件目录。

    • 依赖:选择 Web 应用下的目录 WEB-INF\lib 作为依赖的配置。

  • 方法 2:只使用本方法构成项目的 Java 源文件、依赖(如果同时掺杂了其它方法,删除之):

    • 源文件:在 IntelliJ IDEA 中标记某一个文件夹作为 Java 源文件目录。

    • 依赖:在下面的内容只选其一。

      • 选择且只选择一种项目构建工具管理依赖:(推荐)

        • Maven:在文件 pom.xml 中设置依赖

        • Gradle:在文件 build.gradle 中设置依赖

      • 使用 IntelliJ IDEA 原生的方法导入依赖(这种方法引入依赖弊端很多,不建议使用)。用这种方式导入依赖的方法,可见笔者的另一篇博客:

        Java 库文件的添加教程:
        https://blog.csdn.net/wangpaiblog/article/details/111772193

      • 选择 Web 应用下的目录 WEB-INF\lib 作为依赖的配置。

  另外,在产生了 报错 1 ^1 1 之后,可能会破坏此 IntelliJ IDEA 工程的环境,导致以后即使运行配置正确的 Web 应用,也将一直发生相同的报错,即上面的 错误 2 ^2 2 。此时,可以在解决 报错 1 ^1 1 的问题之后,删除此 IntelliJ IDEA 工程下,上一次编译生成的文件夹(如 Maven 编译产生的文件夹 target),然后重新编译即可。

Logo

更多推荐