Spring 4.0 StandaloneMockMvcBuilder java.lang.NoClassDefFoundError: javax/servlet/SessionCookieConfi...

standaloneSetup(clrr).
        build();

执行第二行 build() 时,出现下面的错误提示。

java.lang.NoClassDefFoundError: javax/servlet/SessionCookieConfig
    at org.springframework.test.web.servlet.setup.StandaloneMockMvcBuilder.initWebAppContext(StandaloneMockMvcBuilder.java:329)
    at org.springframework.test.web.servlet.setup.AbstractMockMvcBuilder.build(AbstractMockMvcBuilder.java:127)
    at com.tony.springTest.HomeControllerTest.testHomeP(HomeControllerTest.java:34)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:44)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:41)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:76)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:193)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:52)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:191)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:42)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:184)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:236)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:86)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:459)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:675)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:382)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:192)
Caused by: java.lang.ClassNotFoundException: javax.servlet.SessionCookieConfig
    at java.net.URLClassLoader$1.run(URLClassLoader.java:202)
    at java.security.AccessController.doPrivileged(Native Method)
    at java.net.URLClassLoader.findClass(URLClassLoader.java:190)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:306)
    at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:301)
    at java.lang.ClassLoader.loadClass(ClassLoader.java:247)
    ... 25 more

 

在 debug 模式下,可以知道 standaloneSetup(clrr) 得到的是 StandaloneMockMvcBuilder 对象和 exception 中报异常的类名一致。

在 Cannot create MockHttpSession with servlet 2.x, spring 得到下面有用提示:Spring 4.0 需要得到 servlet 3.0 或以上版本的支持。

The Servlet API mocks in Spring Framework 4.0 support Servlet 3.0 and higher, as can be seen inGitHub commit deba32cad9.

追踪上面的 github 链接,可以发现 SessionCookieConfig 是在升级 servlet API 到 3.0 变动中新增的。

在查询 SessionCookieConfig 文档,可以知道 SessionCookieConfig 是在 servlet 3.0 才引入的。

 

反观自己项目 pom.xml ,用的是 servlet 2.5 ,可以判断得到,是自己项目引用的 servlet 版本过低导致的,需要升级到 3.0 或以上。

        <!-- Servlet -->
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>servlet-api</artifactId>
            <version>2.5</version>
            <scope>provided</scope>
        </dependency>

 

变动 1 如下。 

        <!-- Servlet -->
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>servlet-api</artifactId>
            <version>3.0.1</version>
            <scope>provided</scope>
        </dependency>

改动后,出现了新的两个错误 : 

Missing artifact javax.servlet:servlet-api:jar: 3.0.1
Description    Resource    Path    Location    Type
The superclass "javax.servlet.http.HttpServlet" was not found on the Java Build Path    home.jsp    /SpringTest/src/main/webapp/WEB-INF/views    line 1    JSP Problem
The superclass "javax.servlet.http.HttpServlet" was not found on the Java Build Path    reg.jsp    /SpringTest/src/main/webapp/WEB-INF/views    line 1    JSP Problem
The superclass "javax.servlet.http.HttpServlet" was not found on the Java Build Path    regSucess.jsp    /SpringTest/src/main/webapp/WEB-INF/views    line 1    JSP Problem
The superclass "javax.servlet.http.HttpServlet" was not found on the Java Build Path    spittles.jsp    /SpringTest/src/main/webapp/WEB-INF/views    line 1    JSP Problem
HttpServlet 找不到是很不合理的,第一个错误表示无法找到 3.0.1 版本的 servlet 。

项目依赖是用 maven 管理的,通过 mvn clean,尝试解决无法找到 3.0.1 servlet artifact 问题。命令如下:
$ cd {project folder}
$ mvn clean compile

 但是出现了新的错误: 

[INFO] ------------------------------------------------------------------------
[ERROR] Failed to execute goal on project springTest: Could not resolve dependencies for project com.tony:springTest:war:1.0.0-BUILD-SNAPSHOT: Failure to find javax.servlet:servlet-api:jar:3.0.1 in https://repo.maven.apache.org/maven2/ was cached in the local repository, resolution will not be reattempted until the update interval of maven.dev.snaponglobal.com has elapsed or updates are forced -> [Help 1]

错误提示 maven repository 无法找到需要的 3.0.1 servlet 。在 repository URL : https://repo.maven.apache.org/ 下面一级一级找,确实没有 servlet 3.0.1 版本的 artifiact 。那么就需要给 maven 换一个有 3.0.1 servlet 的 repository 或者 mirror 。

在网上找到一个有效的 servlet 3.0.1 : http://repo1.maven.org/maven2/javax/servlet/javax.servlet-api/。

于是在 ~/.m2/setting.xml 中将 maven 的 mirror 改为 repo1 的 。如下:

    <mirrors>
       <mirror>
          <id>maven.dev.snaponglobal.com</id>
          <name>Internal Artifactory Maven repository</name>
          <url>http://repo1.maven.org/maven2/</url>
          <mirrorOf>*</mirrorOf>
       </mirror>
    </mirrors>

修改好 mirror 后,还是提示无法解决依赖的 3.0.1 servlet : 

Downloading: http://repo1.maven.org/maven2/javax/servlet/servlet-api/3.0.1/servlet-api-3.0.1.jar
[INFO] ------------------------------------------------------------------------
[INFO] BUILD FAILURE
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 4.511 s
[INFO] Finished at: 2016-02-09T00:40:47+08:00
[INFO] Final Memory: 11M/245M
[INFO] ------------------------------------------------------------------------
[ERROR] Failed to execute goal on project springTest: Could not resolve dependencies for project com.tony:springTest:war:1.0.0-BUILD-SNAPSHOT: Could not find artifact javax.servlet:servlet-api:jar:3.0.1 in maven.dev.snaponglobal.com (http://repo1.maven.org/maven2/) -> [Help 1]

通过仔细对比错误提示的 URL 和 浏览器的 URL ,发现路径有点不一样。

错误提示的是 /servlet/servlet-api/ ,而浏览器的实际路径为 /servlet/javax.servlet-api/ ,将 pom.xml 中的 artifactId 纠正过来就好了。纠正后配置如下 : 

        <!-- Servlet -->
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>javax.servlet-api</artifactId>
            <version>3.0.1</version>
            <scope>provided</scope>
        </dependency>

重新运行 mvn clean 后,可以成功下载 3.0.1 servlet 。然后运行 Spring 的 unit test 也没也报错。

问题解决完毕。

 

转载于:https://www.cnblogs.com/TonyYPZhang/p/5185386.html

`java.lang.NoClassDefFoundError: javax/servlet/Filter`通常表示Java虚拟机(JVM)在运行时找不到指定的类,这个错误通常发生在试图加载一个已经被删除或者缺失的依赖类时。对于Spring Boot应用中遇到这个问题,可能是Shiro(安全框架)依赖的Servlet API版本与当前项目的环境不匹配,或者Shiro库本身没有正确地添加到构建路径。 解决此问题的方法包括: 1. **确认依赖**:检查你的pom.xml或build.gradle文件中,确保已经包含了正确的Servlet API依赖,例如在Maven中可能需要添加: ```xml <dependency> <groupId>javax.servlet</groupId> <artifactId>javax.servlet-api</artifactId> <version>4.0.1</version> <!-- 如果你的Spring Boot版本低于2.5,可能会需要更早的版本 --> </dependency> ``` 2. **排除冲突**:如果项目中有多个web相关的依赖,可能存在版本冲突,试着排除其他不需要Servlet的依赖,只保留必要的部分。 3. **重新打包和部署**:尝试清理并重新构建你的项目,有时候构建过程中的缓存问题可能导致类找不到。 类似地,如果是在使用Apache POI处理文件上传时遇到该问题,可能是缺少了`commons-compress`库,需要添加并配置正确的依赖,如: ```xml <dependency> <groupId>org.apache.commons</groupId> <artifactId>commons-compress</artifactId> <version>1.21</version> </dependency> ``` 确保版本兼容,并正确引入到你的应用程序中。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值