使用WebMvcConfigurationSupport无法访问html页面原因分析

近日在使用Spring 3.0 + 无web.xml搭建 Spring MVC原型项目时,当使用spring 5.0版本以上时,会发现WebMvcConfigurerAdapter已经过时,此时将继承WebMvcConfigurerAdapter修改为继承WebMvcConfigurationSupport后,启动项目将无法访问html页面。配置代码如下:

package com.demo3.springmvc.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.*;
import org.springframework.web.servlet.view.InternalResourceViewResolver;

@Configuration
@EnableWebMvc
@ComponentScan("com.demo3.springmvc")
public class MvcConfig extends WebMvcConfigurationSupport {

    @Bean
    public InternalResourceViewResolver viewResolver() {
        InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
        viewResolver.setPrefix("/WEB-INF/classes/views/");
        viewResolver.setSuffix(".html");
        return viewResolver;
    }

	/**
	* 访问静态文件
	*/
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/assets/**").addResourceLocations("classpath:/assets/");
    }

	/**
	* 建立url与视图映射
	*/
    @Override
    public void addViewControllers(ViewControllerRegistry registry) {
        registry.addViewController("/").setViewName("/index");
    }
    
    @Override
    public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
        configurer.enable();
    }
}

通过以上代码是无法访问html的,然后又将WebMvcConfigurationSupport改为WebMvcConfigurer(因为WebMvcConfigurerAdapter是实现WebMvcConfigurer接口),此时程序可以访问html页面。
后来通过观察spring api文档后发现:

This is the main class providing the configuration behind the MVC Java config. It is typically imported by adding @EnableWebMvc to an application @Configuration class. An alternative more advanced option is to extend directly from this class and override methods as necessary, remembering to add @Configuration to the subclass and @Bean to overridden @Bean methods. For more details see the javadoc of @EnableWebMvc.

使用谷歌翻译(没办法,都怪当初英语没好好学,现在只能使用翻译软件了/哭 )后的大致意思如下:

这是提供MVC Java配置背后配置的主要类。 通常是通过将@EnableWebMvc添加到应用程序@Configuration类中来导入的。 另一种更高级的选择是直接从此类扩展并根据需要重写方法,记住将@Configuration添加到子类中,并记住将@Bean添加到重写的@Bean方法中。 有关更多详细信息,请参见@EnableWebMvc的javadoc。

也就是说,在进行 MVC 配置时,可以使用两种方法:

  1. 直接在配置类上添加@EnableWebMvc并实现WebMvcConfigurer接口,如:
    package com.demo3.springmvc.config;
    
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.ComponentScan;
    import org.springframework.web.servlet.config.annotation.*;
    import org.springframework.web.servlet.view.InternalResourceViewResolver;
    
    @EnableWebMvc
    @ComponentScan("com.demo3.springmvc")
    public class MvcConfig implements WebMvcConfigurer {
    
        @Bean
        public InternalResourceViewResolver viewResolver() {
            InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
            viewResolver.setPrefix("/WEB-INF/classes/views/");
            viewResolver.setSuffix(".html");
            return viewResolver;
        }
    
        @Override
        public void addResourceHandlers(ResourceHandlerRegistry registry) {
            registry.addResourceHandler("/assets/**").addResourceLocations("classpath:/assets/");
        }
    
        @Override
        public void addViewControllers(ViewControllerRegistry registry) {
            registry.addViewController("/").setViewName("/index");
        }
    
        @Override
        public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
            configurer.enable();
        }
    }
    
    
  2. 直接继承WebMvcConfigurationSupport并添加@Configuration注解
    package com.demo3.springmvc.config;
    
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.ComponentScan;
    import org.springframework.web.servlet.config.annotation.*;
    import org.springframework.web.servlet.view.InternalResourceViewResolver;
    
    @ComponentScan("com.demo3.springmvc")
    public class MvcConfig extends WebMvcConfigurationSupport {
    
        @Bean
        public InternalResourceViewResolver viewResolver() {
            InternalResourceViewResolver viewResolver = new InternalResourceViewResolver();
            viewResolver.setPrefix("/WEB-INF/classes/views/");
            viewResolver.setSuffix(".html");
            return viewResolver;
        }
    
        @Override
        public void addResourceHandlers(ResourceHandlerRegistry registry) {
            registry.addResourceHandler("/assets/**").addResourceLocations("classpath:/assets/");
        }
    
        @Override
        public void addViewControllers(ViewControllerRegistry registry) {
            registry.addViewController("/").setViewName("index");
        }
    
        @Override
        public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
            configurer.enable();
        }
    }
    
    

    注意: 由于上例使用到了@ComponentScan,所以就没再使用@Configuration注解

参考资料:

  1. 《Java EE 开发的颠覆者:Spring Boot实战》 – 汪云飞 编著
  2. WebMvcConfigurationSupport class api 文档: https://docs.spring.io/spring-framework/docs/5.1.5.RELEASE/javadoc-api/org/springframework/web/servlet/config/annotation/WebMvcConfigurationSupport.html
  3. The type WebMvcConfigurerAdapter is deprecated: https://stackoverflow.com/questions/47552835/the-type-webmvcconfigureradapter-is-deprecated
  4. Spring mvc请求处理流程详解(一)之视图解析: https://blog.csdn.net/lchpersonal521/article/details/53112728

你可能感兴趣的:(java,#,spring)