spring boot springMVC扩展配置实现解析
作者:JonRain0625 发布时间:2023-11-25 10:32:53
摘要:
在spring boot中 MVC这部分也有默认自动配置,也就是说我们不用做任何配置,那么也是OK的,这个配置类就是 WebMvcAutoConfiguration,但是也时候我们想设置自己的springMvc配置怎么办呢 。
我们也可以写个自己的配置类,继承 WebMvcConfigurer 重写需要的配置方法 。在spring boot 早期是继承WebMvcConfigurerAdapter ,但是高版已标上注解@Deprecated,注意:在配置类中不要标注:@EnableWebMvc,否则,spring boot的配置全部失效,只留自己扩展配置。
示例:
这里已高版为主 继承WebMvcConfigurer,WebMvcConfigurer 接口中的方法都是默认的方法,可以覆盖,也可以不实现 ,加一个视图解析配置 ,解析success请求路劲,返回success页面。如下代码:
@Configuration
public class MyMvcConfig Implements WebMvcConfigurer {
@Override
public void addViewControllers(ViewControllerRegistry registry) {
// super.addViewControllers(registry);
//浏览器发送 /success请求来到 success
registry.addViewController("/success").setViewName("success");
}
}
代码浅析:
1.首先我们来看看WebMvcAutoConfiguration这个配置类,这个配置了有首页的默认路劲,还有一些静态资源路劲,而这些方法在它的一个内部类中,如下代码(删除了部分代码):
@Configuration
@ConditionalOnWebApplication(
type = Type.SERVLET
)
@ConditionalOnClass({Servlet.class, DispatcherServlet.class, WebMvcConfigurer.class})
@ConditionalOnMissingBean({WebMvcConfigurationSupport.class})
@AutoConfigureOrder(-2147483638)
@AutoConfigureAfter({DispatcherServletAutoConfiguration.class, TaskExecutionAutoConfiguration.class, ValidationAutoConfiguration.class})
public class WebMvcAutoConfiguration {
....//省略部分代码
@Configuration
@Import({WebMvcAutoConfiguration.EnableWebMvcConfiguration.class}) // 导入了EnableWebMvcConfiguration这个类 addResourceHandlers方法
@EnableConfigurationProperties({WebMvcProperties.class, ResourceProperties.class})
@Order(0)
public static class WebMvcAutoConfigurationAdapter implements WebMvcConfigurer, ResourceLoaderAware {
...//省略部分代码
public void addResourceHandlers(ResourceHandlerRegistry registry) {//实现WebMvcConfigurer 这个类的
if(!this.resourceProperties.isAddMappings()) {
logger.debug("Default resource handling disabled");
} else {
Duration cachePeriod = this.resourceProperties.getCache().getPeriod();
CacheControl cacheControl = this.resourceProperties.getCache().getCachecontrol().toHttpCacheControl();
if(!registry.hasMappingForPattern("/webjars/**")) {
this.customizeResourceHandlerRegistration(registry.addResourceHandler(new String[]{"/webjars/**"}).addResourceLocations(new String[]{"classpath:/META-INF/resources/webjars/"}).setCachePeriod(this.getSeconds(cachePeriod)).setCacheControl(cacheControl));
}
String staticPathPattern = this.mvcProperties.getStaticPathPattern();
if(!registry.hasMappingForPattern(staticPathPattern)) {
this.customizeResourceHandlerRegistration(registry.addResourceHandler(new String[]{staticPathPattern}).addResourceLocations(getResourceLocations(this.resourceProperties.getStaticLocations())).setCachePeriod(this.getSeconds(cachePeriod)).setCacheControl(cacheControl));
}
}
}
}
可以看到,内部类 WebMvcAutoConfigurationAdapter 标记 @Configuration,并导入另一个内部类 @Import({WebMvcAutoConfiguration.EnableWebMvcConfiguration.class}),我们看下这个类,如下代码:
@Configuration
public static class EnableWebMvcConfiguration extends DelegatingWebMvcConfiguration {
private final WebMvcProperties mvcProperties;
private final ListableBeanFactory beanFactory;
private final WebMvcRegistrations mvcRegistrations;
...// 省略
}
重点在它的父类, DelegatingWebMvcConfiguration 代码如下 (写了几个案列方法,其他代码省略。)。
@Configuration
public class DelegatingWebMvcConfiguration extends WebMvcConfigurationSupport {
private final WebMvcConfigurerComposite configurers = new WebMvcConfigurerComposite();
...//省略
/**
* 从容器中拿到所有 WebMvcConfigurer 的实现类。遍历添加到 configurers
* [required description]
* @type {[type]}
*/
@Autowired( required = false ) // 自动装配
public void setConfigurers(List<WebMvcConfigurer> configurers) {
if(!CollectionUtils.isEmpty(configurers)) {
this.configurers.addWebMvcConfigurers(configurers);
}
}
...//省略
/**
* 当调用addResourceHandlers 时 ,调用的 成员configurers的 addResourceHandlers
* [addResourceHandlers description]
* @param {[type]} ResourceHandlerRegistry registry [description]
*/
protected void addResourceHandlers(ResourceHandlerRegistry registry) {
this.configurers.addResourceHandlers(registry);
}
...//省略
}
来看看 WebMvcConfigurerComposite 的 addResourceHandlers的方法做了什么 :
class WebMvcConfigurerComposite implements WebMvcConfigurer {
private final List<WebMvcConfigurer> delegates = new ArrayList<WebMvcConfigurer>();
@Override
public void addViewControllers(ViewControllerRegistry registry) { // 遍历 把 所有WebMvcConfigurer的 addViewControllers方法调用一遍
for (WebMvcConfigurer delegate : this.delegates) {
delegate.addViewControllers(registry);
}
}
}
看到这里我们知道,不管是spring boot中实现的 WebMvcConfigurer 类,还是我们自己实现 WebMvcConfigurer ,只要我们把实现类注入到容器中,就会被 注入 WebMvcConfigurerComposite 这个类成员变量 delegates中。
而 WebMvcConfigurerComposite 有是实现了 WebMvcConfigurer 。当调用 WebMvcConfigurer中 xxx方法的,就会遍历 delegates 中所有 WebMvcConfigurer 的方法xxx 。那我们的扩展配置MyMvcConfig 也就被调用了。
来源:https://www.cnblogs.com/jonrain0625/p/11299810.html


猜你喜欢
- 在C++、Java等众多OOP语言里都可以看到virtual的身影,而C#作为一个完全面向对象的语言当然也不例外。虚拟函数从C#的程序编译的
- 由于最近想要阅读下JDK1.8 中HashMap的具体实现,但是由于HashMap的实现中用到了红黑树,所以我觉得有必要先复习下红黑树的相关
- 前言本文主要给大家介绍的是java虚拟机的故障处理工具,文中提到这些工具包括:名称主要作用jpsJVM process Status Too
- 编写一个 Java 应用程序,实现图形界面多人聊天室(多线程实现),要求聊天室窗口标题是 “欢迎使用 XXX 聊天室应用
- 本文实例讲述了C#使用foreach循环遍历数组的方法。分享给大家供大家参考,具体如下:using System;using System.
- 本文实例为大家分享了Unity3D实现打砖块的具体代码,供大家参考,具体内容如下基于unity20171、 使用Plane创建初始地图(层级
- 一本书的页码从自然数1开始顺序编码直到自然数n。书的页码按照通常的习惯编排,每个页码都不含多余的前导数字0。例如第6页用6表示而不是06或0
- Android 实现单线程轮循机制批量下载图片listview 在为item 添加从网上下载下来的图片时, 如果每次都整合一个item时都需
- 一、项目概述本次项目主要实现了天气预报功能。通过调用天气预报接口来获得天气数据,用LIstView和GridView来搭建每个界面,将查询的
- 本文实例讲述了Java数组传递及可变参数操作。分享给大家供大家参考,具体如下:方法可以操作传递和返回基本数据类型,但是方法中也可用来传递和返
- 前言:回顾之前的微信公众号配置和消息处理的内容,我们已经掌握了如何配置服务器与微信公众号建立连接,也掌握了通过消息管理的方式,对用户的信息进
- Interfaces 接口在软件工程中,由一份“契约”规定来自不同的开发小组的软件之间如何相互作用是非常常见的。每个小组都可以在不知道别的组
- 1、使用AsyncTask异步任务实现,调用publishProgress()方法刷新进度来实现(已优化)public class MyAs
- 前言多数据源的事务处理是个老生常谈的话题,跨两个数据源的事务管理也算是分布式事务的范畴,在同一个JVM里处理多数据源的事务,比较经典的处理方
- Nacos是什么和Eureka,zookeeper,consul相同,Nacos也是一个注册中心组件咯,当然是,不过它不仅仅是注册中心。Na
- 一、基本概念JavaWeb里面的listener是通过观察者设计模式进行实现的。对于观察者模式,这里不做过多介绍,大概讲一下什么意思。观察者
- 最近正式入坑Flutter,首先从环境搭建开始,看了网上好多关于Windows环境搭建的资料,基本都是按官方文档写的,看完的感受是,还不如直
- 现在Java的大部分项目都是基于Maven, 在Maven项目中使用Selenium2. 非常简单。 首先你需要配置好
- 前言如今发短信功能已经成为互联网公司的标配,本篇文章将一步步实现java发送短信考察了许多提供短信服务的三方,几乎所有都需要企业认证才可以使
- 本文实例为大家分享了java与微信小程序实现websocket长连接的具体代码,供大家参考,具体内容如下背景:需要在小程序实现地图固定坐标下