java spring-mvc spring-boot nosuchmethoderror lifecycleexception

Obteniendo NoSuchMethodError: javax.servlet.ServletContext.addServlet en Spring Boot mientras ejecuta una aplicaciĆ³n Spring MVC



spring-mvc spring-boot (15)

Estoy por debajo de la excepción cuando intento ejecutar una aplicación Spring MVC usando Spring boot ...

ContainerBase: A child container failed during start java.util.concurrent.ExecutionException: org.apache.catalina.LifecycleException: Failed to start component [StandardEngine[Tomcat].StandardHost[localhost].StandardContext[]] at java.util.concurrent.FutureTask.report(FutureTask.java:122) at java.util.concurrent.FutureTask.get(FutureTask.java:188) at org.apache.catalina.core.ContainerBase.startInternal(ContainerBase.java:1123) at org.apache.catalina.core.StandardHost.startInternal(StandardHost.java:799) at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150) at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1559) at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1549) at java.util.concurrent.FutureTask.run(FutureTask.java:262) at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145) at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615) at java.lang.Thread.run(Thread.java:745) Caused by: org.apache.catalina.LifecycleException: Failed to start component [StandardEngine[Tomcat].StandardHost[localhost].StandardContext[]] at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:154) ... 6 more Caused by: java.lang.NoSuchMethodError: javax.servlet.ServletContext.addServlet(Ljava/lang/String;Ljavax/servlet/Servlet;)Ljavax/servlet/ServletRegistration$Dynamic; at org.springframework.boot.context.embedded.ServletRegistrationBean.onStartup(ServletRegistrationBean.java:166) at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext$1.onStartup(EmbeddedWebApplicationContext.java:214) at org.springframework.boot.context.embedded.tomcat.ServletContextInitializerLifecycleListener.lifecycleEvent(ServletContextInitializerLifecycleListener.java:54) at org.apache.catalina.util.LifecycleSupport.fireLifecycleEvent(LifecycleSupport.java:117) at org.apache.catalina.util.LifecycleBase.fireLifecycleEvent(LifecycleBase.java:90) at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5355) at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150) ... 6 more



Estaba usando Gradle y lo que funcionó para mí:

configurations { all*.exclude group: '''', module: ''servlet-api'' }

Recortó el árbol de dependencia de la manera deseada.


Estoy usando Jetty en mi proyecto y recibí el mismo error. Mi solución rápida fue excluir Tomcat integrado de la dependencia Maven:

<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-ws</artifactId> <version>1.2.0.RELEASE</version> <exclusions> <exclusion> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-tomcat</artifactId> </exclusion> </exclusions> </dependency>


Lo resolví excluyendo una dependencia transitiva servlet-api.

En mi caso, fue com.github.isrsal: spring-mvc-logger

<dependency> <groupId>com.github.isrsal</groupId> <artifactId>spring-mvc-logger</artifactId> <version>0.2</version> <exclusions> <exclusion> <groupId>javax.servlet</groupId> <artifactId>servlet-api</artifactId> </exclusion> </exclusions> </dependency>



Me estaba ejecutando con Hadoop 2.7.2 usando Spring-boot, las siguientes dependencias de Hadoop usan javax.servlet, lo que impidió que la versión de tomcat incorporada se inicie. Debajo de las exclusiones en mi POM solucionó el problema .

<dependency> <groupId>org.apache.hadoop</groupId> <artifactId>hadoop-hdfs</artifactId> <version>2.7.2</version> <exclusions> <exclusion> <artifactId>servlet-api</artifactId> <groupId>javax.servlet</groupId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.springframework.data</groupId> <artifactId>spring-data-hadoop-boot</artifactId> <version>2.3.0.RELEASE-hadoop26</version> <exclusions> <exclusion> <artifactId>servlet-api</artifactId> <groupId>javax.servlet</groupId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.apache.hadoop</groupId> <artifactId>hadoop-common</artifactId> <version>2.7.2</version> <exclusions> <exclusion> <artifactId>slf4j-log4j12</artifactId> <groupId>org.slf4j</groupId> </exclusion> <exclusion> <artifactId>servlet-api</artifactId> <groupId>javax.servlet</groupId> </exclusion> </exclusions> </dependency>


No pude rastrear la referencia problemática a excepción de saber que de alguna manera está entrando en mi camino de clase, así que aquí están mis 2 centavos para desarrolladores perezosos que usan eclipse:

Desplácese por la lista de dependencias maven bajo su árbol de proyecto (generalmente en Recursos Java -> Bibliotecas -> Dependencias Maven), rastree el jar problemático agregado que desea excluir de su JAR empaquetado, haga clic derecho sobre él -> seleccione Maven -> Excluir ¡Artefacto Maven! Voila: automáticamente se agregará una exclusión a su pom justo debajo de la dependencia que lo refiere.

El mío por cierto fue jcifs ...

<dependency> <groupId>org.codelibs</groupId> <artifactId>jcifs</artifactId> <version>1.3.18.2</version> <exclusions> <exclusion> <artifactId>servlet-api</artifactId> <groupId>javax.servlet</groupId> </exclusion> </exclusions> </dependency>

¡Buena suerte!


Para cualquier otra persona que no pueda resolverlo excluyendo servlet-api , aquí hay una alternativa:

Resulta que Spring Boot se configura por defecto en Tomcat 8. Si está ejecutando una versión diferente de Tomcat y desea corregir este error, simplemente agregue su versión de tomcat a las propiedades de pom:

<properties> <tomcat.version>7.0.63</tomcat.version> </properties>


Para una solución rápida, he eliminado el servlet-api.jar manualmente de la lib y luego compilo la aplicación y funciona. Aunque, idealmente como sugiere Kumetix, uno debería necesitar analizar hasta la dependencia que hace que se cargue en classpath.


Si está utilizando STS y ha agregado la biblioteca Groovy a su proyecto (Propiedades del proyecto -> Ruta de compilación de Java -> Bibliotecas), asegúrese de seleccionar la opción "No, solo incluir groovy-all". La otra opción de "Sí, incluir groovy-all y bsf.jar ..., servlet-2.4.jar" agrega servlet-2.4.jar que entra en conflicto con las clases incrustadas de tomcat8 que dan como resultado este problema.


Si quieres saber de dónde se está cargando la clase, prueba

java -verbose:class -jar foo.jar | grep javax.servlet.ServletContext

donde foo.jar es el JAR gordo producido por Gradle o Maven. Por ejemplo, la clase ServletContext podría obtenerse de un JAR servlet-api en un directorio de extensiones JDK en lugar de las dependencias de Maven o Gradle.

La salida del comando se ve más o menos así ...

$ java -verbose:class -jar build/libs/foo-0.2.3.jar | grep javax.servlet.ServletContext [Loaded javax.servlet.ServletContext from jar:file:.../build/libs/foo-0.2.3.jar!/lib/javax.servlet-api-3.1.0.jar!/] [Loaded javax.servlet.ServletContextListener from jar:file:.../build/libs/foo-0.2.3.jar!/lib/javax.servlet-api-3.1.0.jar!/] [Loaded javax.servlet.ServletContextAttributeListener from jar:file:.../build/libs/foo-0.2.3.jar!/lib/javax.servlet-api-3.1.0.jar!/]


También enfrenté este error. Tengo un proyecto Maven / Spring MVC / Spring Boot. Estoy usando IntelliJ como el IDE y cada vez que agrego nuevas dependencias al archivo POM.xml, el IDE altera el archivo .iml (como se esperaba), pero lo que es extraño es que mueve la siguiente línea a la parte superior del archivo:

<orderEntry type="library" name="Java EE 6-Java EE 6" level="project" />

una vez que eso suceda, mi proyecto no se compilará y obtendré el mismo error:

java.lang.NoSuchMethodError: javax.servlet.ServletContext.getVirtualServerName () Ljava / lang / String;

simplemente moviendo el orderEntry para Java EE al final, el error desaparece y puedo compilar una vez más.


Tuve este problema al intentar iniciar mi servidor de arranque de muelles durante las pruebas (usando gradle + spock). Seguí el problema hasta la biblioteca de wiremock.

Esto lo solucionó:

testCompile(''com.github.tomakehurst:wiremock:1.58'') { exclude module: ''servlet-api'' // this exclude fixed it }

FYI

gradle dependencies

muestra (abreviado):

/--- com.github.tomakehurst:wiremock:1.58 +--- org.mortbay.jetty:jetty:6.1.26 +--- org.mortbay.jetty:jetty-util:6.1.26 /--- org.mortbay.jetty:servlet-api:2.5-20081211

El antiguo (2008) org.mortbay.jetty:servlet-api jar contiene una versión de ServletContext que no es compatible con la versión 1.3.2 del arranque de primavera (funcionó bien al menos hasta 1.2.6).


solución gradle.

Tuve un problema similar en mi jar de lib que por alguna razón traía consigo una versión anterior de javax.servlet.ServletContext que luego fue cargada por mi módulo de arranque de resorte en lugar de su propia clase suministrada, causando un NoSuchMethodError

Lo arreglé editando el módulo build.gradle of my lib:

configurations { provided.all*.exclude group: ''javax.servlet'' }


mvn dependency:tree no reveló el servlet-api.jar en mi classpath, pero haciendo clic derecho en el proyecto (en Eclipse) y yendo a Build Path / Configure Build Path mostró que mi espacio de trabajo predeterminado JRE, JDK 1.7.0_51, tenía ese jar en su directorio jre/lib/ext (al menos en mi instalación). Intenté y no pude eliminarlo de mi classpath. La solución de @ Pedro de forzar la versión de tomcat a 7 funcionó. Lo mismo hizo la instalación de la última versión de Java 7: JDK 1.7.0_79.