Spring 6项目HTTP 500错误:ServletContextTemplateResolver无法解析
问题:Spring MVC + Thymeleaf项目启动报HTTP 500错误
环境与配置
pom.xml配置
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>org.example</groupId> <artifactId>Travel</artifactId> <version>0.0.1-SNAPSHOT</version> <packaging>war</packaging> <name>Travel</name> <build> <plugins> <plugin> <artifactId>maven-compiler-plugin</artifactId> <version>3.8.1</version> <configuration> <release>17</release> </configuration> </plugin> <plugin> <artifactId>maven-war-plugin</artifactId> <version>3.2.3</version> </plugin> </plugins> </build> <dependencies> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-webmvc</artifactId> <version>6.0.3</version> </dependency> <dependency> <groupId>javax.servlet</groupId> <artifactId>javax.servlet-api</artifactId> <version>4.0.1</version> </dependency> <dependency> <groupId>org.thymeleaf</groupId> <artifactId>thymeleaf</artifactId> <version>3.0.11.RELEASE</version> </dependency> <dependency> <groupId>org.thymeleaf</groupId> <artifactId>thymeleaf-spring5</artifactId> <version>3.1.1.RELEASE</version> </dependency> </dependencies> </project>
WebConfig配置类
package main.config; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.ComponentScan; import org.springframework.context.annotation.Configuration; import org.springframework.web.context.WebApplicationContext; import org.springframework.web.servlet.config.annotation.DefaultServletHandlerConfigurer; import org.springframework.web.servlet.config.annotation.EnableWebMvc; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; import org.thymeleaf.spring5.SpringTemplateEngine; import org.thymeleaf.spring5.view.ThymeleafViewResolver; import org.thymeleaf.templateresolver.ServletContextTemplateResolver; @Configuration @EnableWebMvc @ComponentScan("main") public class WebConfig implements WebMvcConfigurer { @Autowired private WebApplicationContext context; @Bean public ServletContextTemplateResolver templateResolver() { ServletContextTemplateResolver resolver = new ServletContextTemplateResolver(context.getServletContext()); resolver.setPrefix("/WEB-INF/view/"); resolver.setSuffix(".html"); return resolver; } @Bean public SpringTemplateEngine templateEngine() { SpringTemplateEngine templateEngine = new SpringTemplateEngine(); templateEngine.setTemplateResolver(templateResolver()); return templateEngine; } @Bean public ThymeleafViewResolver viewResolver() { ThymeleafViewResolver viewResolver = new ThymeleafViewResolver(); viewResolver.setTemplateEngine(templateEngine()); return viewResolver; } @Override public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) { configurer.enable(); } }
报错信息
启动后浏览器返回HTTP 500,IDE日志如下:
sty 07, 2023 7:36:20 PM org.apache.catalina.core.StandardWrapperValve invoke SEVERE: Allocate exception for servlet [dispatcher] java.lang.Error: Unresolved compilation problems: ServletContextTemplateResolver cannot be resolved to a type ServletContextTemplateResolver cannot be resolved to a type ServletContextTemplateResolver cannot be resolved to a type The method getServletContext() from the type WebApplicationContext refers to the missing type ServletContext at main.config.WebConfig.templateResolver(WebConfig.java:31) at main.config.WebConfig$$SpringCGLIB$$0.CGLIB$templateResolver$1(<generated>) at main.config.WebConfig$$SpringCGLIB$$2.invoke(<generated>) at org.springframework.cglib.proxy.MethodProxy.invokeSuper(MethodProxy.java:258) at org.springframework.context.annotation.ConfigurationClassEnhancer$BeanMethodInterceptor.intercept(ConfigurationClassEnhancer.java:331) at main.config.WebConfig$$SpringCGLIB$$0.templateResolver(<generated>) at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:77) at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.base/java.lang.reflect.Method.invoke(Method.java:568) at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:139) at org.springframework.beans.factory.support.ConstructorResolver.instantiate(ConstructorResolver.java:653) at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:491) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1324) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1161) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:561) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:521) at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:326) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:324) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:200) at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:961) at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:915) at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:584) at org.springframework.web.servlet.FrameworkServlet.configureAndRefreshWebApplicationContext(FrameworkServlet.java:706) at org.springframework.web.servlet.FrameworkServlet.initWebApplicationContext(FrameworkServlet.java:583) at org.springframework.web.servlet.FrameworkServlet.initServletBean(FrameworkServlet.java:537) at org.springframework.web.servlet.HttpServletBean.init(HttpServletBean.java:169) at jakarta.servlet.GenericServlet.init(GenericServlet.java:158) at jakarta.servlet.http.HttpServlet.init(HttpServlet.java:140) at org.apache.catalina.core.StandardWrapper.initServlet(StandardWrapper.java:995) at org.apache.catalina.core.StandardWrapper.allocate(StandardWrapper.java:696) at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:128) at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:97) at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:542) at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:119) at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:92) at org.apache.catalina.valves.AbstractAccessLogValve.invoke(AbstractAccessLogValve.java:690) at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:78) at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:357) at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:400) at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:65) at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:861) at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1739) at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:52) at org.apache.tomcat.util.threads.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1191) at org.apache.tomcat.util.threads.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:659) at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61) at java.base/java.lang.Thread.run(Thread.java:833)
尝试过的修改
曾尝试强制类型转换,但问题未解决:
@Bean public ServletContextTemplateResolver templateResolver() { ServletContextTemplateResolver resolver = new ServletContextTemplateResolver((ServletContext) context.getServletContext()); resolver.setPrefix("/WEB-INF/view/"); resolver.setSuffix(".html"); return resolver; }
解决方案
问题核心是版本不兼容:
- Spring 6.x基于Jakarta EE 9+,依赖
jakarta.servlet包,但当前用了旧的javax.servlet-api;同时Thymeleaf用了适配Spring5的thymeleaf-spring5,与Spring6不兼容。 ServletContextTemplateResolver在Thymeleaf适配Spring6的版本中,已适配Jakarta Servlet,且推荐改用SpringResourceTemplateResolver更符合Spring MVC的资源加载方式。
步骤1:修改pom.xml依赖
替换为兼容Spring6的依赖:
<dependencies> <!-- Spring MVC 6.x --> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-webmvc</artifactId> <version>6.0.3</version> </dependency> <!-- Jakarta Servlet API 6.x,适配Spring6 --> <dependency> <groupId>jakarta.servlet</groupId> <artifactId>jakarta.servlet-api</artifactId> <version>6.0.0</version> <scope>provided</scope> </dependency> <!-- Thymeleaf 核心包,升级到兼容版本 --> <dependency> <groupId>org.thymeleaf</groupId> <artifactId>thymeleaf</artifactId> <version>3.1.1.RELEASE</version> </dependency> <!-- Thymeleaf 适配Spring6的包 --> <dependency> <groupId>org.thymeleaf</groupId> <artifactId>thymeleaf-spring6</artifactId> <version>3.1.1.RELEASE</version> </dependency> </dependencies>
步骤2:修改WebConfig配置类
替换ServletContextTemplateResolver为SpringResourceTemplateResolver,无需手动依赖WebApplicationContext:
package main.config; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.ComponentScan; import org.springframework.context.annotation.Configuration; import org.springframework.core.io.ResourceLoader; import org.springframework.web.servlet.config.annotation.DefaultServletHandlerConfigurer; import org.springframework.web.servlet.config.annotation.EnableWebMvc; import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; import org.thymeleaf.spring6.SpringTemplateEngine; import org.thymeleaf.spring6.view.ThymeleafViewResolver; import org.thymeleaf.templateresolver.SpringResourceTemplateResolver; @Configuration @EnableWebMvc @ComponentScan("main") public class WebConfig implements WebMvcConfigurer { private final ResourceLoader resourceLoader; // 注入ResourceLoader替代WebApplicationContext public WebConfig(ResourceLoader resourceLoader) { this.resourceLoader = resourceLoader; } @Bean public SpringResourceTemplateResolver templateResolver() { SpringResourceTemplateResolver resolver = new SpringResourceTemplateResolver(); resolver.setResourceLoader(resourceLoader); resolver.setPrefix("/WEB-INF/view/"); resolver.setSuffix(".html"); resolver.setTemplateMode("HTML"); return resolver; } @Bean public SpringTemplateEngine templateEngine() { SpringTemplateEngine templateEngine = new SpringTemplateEngine(); templateEngine.setTemplateResolver(templateResolver()); return templateEngine; } @Bean public ThymeleafViewResolver viewResolver() { ThymeleafViewResolver viewResolver = new ThymeleafViewResolver(); viewResolver.setTemplateEngine(templateEngine()); return viewResolver; } @Override public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) { configurer.enable(); } }
步骤3:清理并重新构建项目
- 执行
mvn clean install清理旧依赖并重新构建 - 重启IDE或刷新Maven依赖,确保所有包正确加载
内容的提问来源于stack exchange,提问作者Cineczeq
相关产品推荐
相关产品推荐

