SpringMVC的全注解开发

2023-10-26

一、spring-mvc.xml 中组件转化为注解形式

跟之前全注解开发思路一致, xml配置文件使用核心配置类替代,xml中的标签使用对应的注解替代

<!-- 组件扫描web层 -->
<context:component-scan base-package="com.itheima.controller"/>

<!--注解驱动-->
<mvc:annotation-driven/>

<!--配置文件上传解析器-->
<bean id="multipartResolver" 
class="org.springframework.web.multipart.commons.CommonsMultipartResolver"/>

<!--配置拦截器-->
<mvc:interceptors>
	<mvc:interceptor>
		<mvc:mapping path="/*"/>
		<bean class="com.itheima.interceptor.MyInterceptor01"></bean>
	</mvc:interceptor>
</mvc:interceptors>

<!--配置DefaultServletHttpRequestHandler-->
<mvc:default-servlet-handler/>

⚫ 组件扫描,可以通过@ComponentScan注解完成;
⚫ 文件上传解析器multipartResolver可以通过非自定义Bean的注解配置方式,即@Bean注解完成

@Configuration
@ComponentScan("com.itheima.controller")
public class SpringMVCConfig {
	@Bean
	public CommonsMultipartResolver multipartResolver() {
		CommonsMultipartResolver multipartResolver = new CommonsMultipartResolver();
		multipartResolver.setDefaultEncoding("UTF-8");
		multipartResolver.setMaxUploadSize(3145728);
		multipartResolver.setMaxUploadSizePerFile(1048576);
		multipartResolver.setMaxInMemorySize(1048576);
		return multipartResolver;
	}
}

< mvc:annotation-driven>、< mvc:default-servlet-handler /> 和 < mvc:interceptor > 怎么办呢?SpringMVC 提供了一个注解@EnableWebMvc,我们看一下源码,内部通过@Import 导入了DelegatingWebMvcConfiguration类

@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE})
@Documented
@Import({DelegatingWebMvcConfiguration.class})
public @interface EnableWebMvc {}
@Configuration(proxyBeanMethods = false)
public class DelegatingWebMvcConfiguration extends WebMvcConfigurationSupport {
	private final WebMvcConfigurerComposite configurers = new WebMvcConfigurerComposite();
	// 从容器中注入WebMvcConfigurer类型的Bean
	@Autowired(required = false)
	public void setConfigurers(List<WebMvcConfigurer> configurers) {
		if (!CollectionUtils.isEmpty(configurers)) {
			this.configurers.addWebMvcConfigurers(configurers);
		}
	}
	//省略其他代码
}

WebMvcConfigurer类型的Bean会被注入进来,然后被自动调用,所以可以实现WebMvcConfigurer接口,完成一些解析器、默认Servlet等的指定,WebMvcConfigurer接口定义如下:

public interface WebMvcConfigurer {
	// 配置默认Servet处理器
	default void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) { }
	
	// 添加拦截器
	default void addInterceptors(InterceptorRegistry registry) { }
	
	// 添加资源处理器
	default void addResourceHandlers(ResourceHandlerRegistry registry) { }
	
	// 添加视图控制器
	default void addViewControllers(ViewControllerRegistry registry) { }
	
	// 配置视图解析器
	default void configureViewResolvers(ViewResolverRegistry registry) { }
	
	// 添加参数解析器
	default void addArgumentResolvers(List<HandlerMethodArgumentResolver> resolvers) { }
	
	// ... 省略其他代码 ...
}

创建MyWebMvcConfigurer实现WebMvcConfigurer接口,实现addInterceptors 和 configureDefaultServletHandling方法

@Component
public class MyWebMvcConfigurer implements WebMvcConfigurer {
	@Override
	public void configureDefaultServletHandling(DefaultServletHandlerConfigurer configurer) {
		// 开启DefaultServlet,可以处理静态资源了
		configurer.enable();
	}
	
	@Override
	public void addInterceptors(InterceptorRegistry registry) {
		// 创建拦截器对象,进行注册
		// Interceptor的执行顺序也取决于添加顺序
		registry.addInterceptor(new MyInterceptor01()).addPathPatterns("/*");
	}
}

最后,在SpringMVC核心配置类上添加@EnableWebMvc注解

@Configuration
@ComponentScan("com.itheima.controller")
@EnableWebMvc
public class SpringMVCConfig {
	@Bean
	public CommonsMultipartResolver multipartResolver(){
		CommonsMultipartResolver multipartResolver = new CommonsMultipartResolver();
		multipartResolver.setDefaultEncoding("UTF-8");
		multipartResolver.setMaxUploadSize(3145728);
		multipartResolver.setMaxUploadSizePerFile(1048576);
		multipartResolver.setMaxInMemorySize(1048576);
		return multipartResolver;
	}
}

二、DispatcherServlet加载核心配置类

DispatcherServlet在进行SpringMVC配置文件加载时,使用的是以下方式:

<!--配置springMVC前端控制器-->
<servlet>
	<servlet-name>DispatcherServlet</servlet-name>
	<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
	<!--指定springMVC配置文件位置-->
	<init-param>
		<param-name>contextConfigLocation</param-name>
		<param-value>classpath:spring-mvc.xml</param-value>
	</init-param>
	<!--服务器启动就创建-->
	<load-on-startup>2</load-on-startup>
</servlet>

<servlet-mapping>
	<servlet-name>DispatcherServlet</servlet-name>
	<url-pattern>/</url-pattern>
</servlet-mapping>

现在是使用SpringMVCConfig核心配置类替代的spring-mvc.xml,怎么加载呢?参照Spring的ContextLoaderListener加载核心配置类的做法,定义了一个AnnotationConfigWebApplicationContext,通过代码注册核心配置类

public class MyAnnotationConfigWebApplicationContext extends AnnotationConfigWebApplicationContext {
	public MyAnnotationConfigWebApplicationContext() {
	// 注册核心配置类
	super.register(SpringMVCConfig.class);
	}
}
<!--指定springMVC的applicationContext全限定名 -->
<init-param>
	<param-name>contextClass</param-name>
	<param-value>com.itheima.config.MyAnnotationConfigWebApplicationContext</param-value>
</init-param>

三、消除web.xml

目前,几乎消除了配置文件,但是web工程的入口还是使用的web.xml进行配置的,如下:

<!--配置springMVC前端控制器-->
<servlet>
	<servlet-name>DispatcherServlet</servlet-name>
	<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
	<!--指定springMVC的applicationContext全限定名 -->
	<init-param>
		<param-name>contextClass</param-name>
		<param-value>com.itheima.config.MyAnnotationConfigWebApplicationContext</param-value>
	</init-param>
	<!--服务器启动就创建-->
	<load-on-startup>2</load-on-startup>
</servlet>

<servlet-mapping>
	<servlet-name>DispatcherServlet</servlet-name>
	<url-pattern>/</url-pattern>
</servlet-mapping>

⚫ Servlet3.0环境中,web容器提供了javax.servlet.ServletContainerInitializer接口,实现了该接口后,在对应的类加载路径的META-INF/services 目录创建一个名为javax.servlet.ServletContainerInitializer的文件,文件内容指定具体的ServletContainerInitializer实现类,那么,当web容器启动时就会运行这个初始化器做一些组件内的初始化工作;
⚫ 基于这个特性,Spring就定义了一个SpringServletContainerInitializer实现了ServletContainerInitializer接口;
⚫ 而SpringServletContainerInitializer会查找实现了WebApplicationInitializer的类,Spring又提供了一个WebApplicationInitializer的基础实现类AbstractAnnotationConfigDispatcherServletInitializer,当我们编写类继承AbstractAnnotationConfigDispatcherServletInitializer时,容器就会自动发现我们自己的类,在该类中我们就可以配置Spring和SpringMVC的入口了。

按照下面的配置就可以完全省略web.xml

public class MyAnnotationConfigDispatcherServletInitializer extends AbstractAnnotationConfigDispatcherServletInitializer {

	// 返回的带有@Configuration注解的类用来配置ContextLoaderListener
	protected Class<?>[] getRootConfigClasses() {
		System.out.println("加载核心配置类创建ContextLoaderListener");
		return new Class[]{ApplicationContextConfig.class};
	}
	
	// 返回的带有@Configuration注解的类用来配置DispatcherServlet
	protected Class<?>[] getServletConfigClasses() {
		System.out.println("加载核心配置类创建DispatcherServlet");
		return new Class[]{SpringMVCConfig.class};
	}
	
	// 将一个或多个路径映射到DispatcherServlet上
	protected String[] getServletMappings() {
		return new String[]{"/"};
	}
}
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

SpringMVC的全注解开发 的相关文章

随机推荐

  • MySQL-binlog2sql:非主从关系实现数据的【数据同步+数据恢复+数据追踪】

    文章目录 MySQL binlog2sql 非主从实时同步 恢复误删数据 1 引 1 介绍 2 功能 3 针对3种场景 4 脚本汇总说明 2 先决条件 1 安装 MySQL 2 修改 MySQL 配置 3 安装 binlog2sql 1 解
  • yii2 mysql设置时区

    第一步 修改配置文件 common config db php 注 8 00为北京时间 Asia Shanghai common config main php 第二步 修改vendor yiisoft yii2 db Connection
  • 抓取网站中的视频

    最近想从别人家的网站宣传片上提取一些素材 借鉴一下 之前也没有弄过 但是我的思路就是从网页的缓存中查找播放完后缓存的视频 然后失败了 然后又想到了网页打开源代码 然后查找到网页源代码饮用的视频的路径 然后找到视频 然后 再次失败 网上找了好
  • css基础———清除浮动的一些方法及区别

    为什么要清楚浮动 地址 http blog csdn net qwe502763576 article details 78811658 清除浮动方法概览 这里例举四种常见的清除浮动方式 方式一 使用overflow属性来清除浮动 ovh
  • 论文阅读

    简介 paper https arxiv org abs 1911 11907 github https github com huawei noah ghostnet Ghostnet CVPR2020 是华为提出的一种轻量级网络 结构类
  • WSL安装

    WSL安装教程 WSL简介 Windows Subsystem for Linux 简称WSL 是一个在Windows10上能够运行原生Linux二进制可执行文件 ELF格式 的兼容层 它是有微软与Canonical公司合作开发 其目标正是
  • 模糊查询与带参数跳转

    一 模糊查询 使用
  • 方法重写(override)原则

    方法的重写 override 两同两小一大原则 1 方法名相同 参数类型相同 2 子类返回类型小于等于父类方法返回类型 3 子类抛出异常小于等于父类方法抛出异常 4 子类访问权限大于等于父类方法访问权限
  • oracle RAC ORA-03113 错误解决

    好久 没有更新博客 太懒了 这咋换工作呢 1 错误现象 数据库 客户端连接不正常 频繁报 ORA 03113 错误 oracle 文档中对这个错误这样解释 ORA 03113 错误就是说连接到数据库的网络中断了 有些错误由于频繁出现 原因复
  • res_company_white_url.py 详解

    res company white url py 主要作用是 在数据库中建立一个表 存放白名单的URL 当我们读取文件时 先判断Referer是否在白名单中 如果不在则自动转到一个图片文件 防止盗链 接下来我们看一下主要代码 class C
  • unexpected keyword argument 'renderer'-DjangoUeditor

    今天在集成DjangoUeditor按照官方的Github集成之后 本以为就可以看到后台了没想到直接报错 render got an unexpected keyword argument renderer 报错93行 boundfield
  • 【QT】——06_带参数的信号(笔记)

    信号重载 说明 信号是可以重载的 相同的名字不同的参数 在发射信号的时候给值 emit musicSignal 100 音乐菜单 主窗口 h 创建一个带参的槽来处理信号 注意槽的参数要与信号一致 void dealMusic2 int QS
  • 《Hadoop学习笔记系列》二.Hadoop分布式文件系统 HDFS

    0 Hadoop分布式文件系统 HDFS HDFS以流式数据访问模式来存储超大文件 运行与商用硬件集群上 1 流式数据访问 HDFS的构建思路 一次写入 多次读取是最高效的访问模式 2 Block数据块 HDFS基本读写单位 类似于磁盘的页
  • STM32的ADC采样与多通道ADC采样

    一 单通道采样 参考资料 STM32库开发实战指南 刘火良 杨森著 原理性质的东西还是少讲 因为上面那本书里面讲解的很详细了 直接来看硬件电路图 这里使用的是3362电位器 10K 即用STM32来测量PB0和GND两端的电压 这样的电路设
  • 一篇明白SQL的执行顺序

    这是一条标准的查询语句 这是我们实际上SQL执行顺序 我们先执行from join来确定表之间的连接关系 得到初步的数据 where对数据进行普通的初步的筛选 group by 分组 各组分别执行having中的普通筛选或者聚合函数筛选 然
  • 小谈HashMap与ConcurrentHashMap

    HashMap JDK7 在JDK7中 HashMap通过数组加链表的形式存储 当元素个数达到阈值 并且数组下标已经存在元素 则会进行扩容 如果数组下标不存在元素 则直接添加 不会扩容 JDK7中添加元素使用的是头插法 在高并发的环境下可能
  • [算法通关村] 1.3 链表的删除

    上一节我们谈到了链表的头插 尾插 中间插入的方法 忘记的小伙伴可以复习一下 算法通关村 1 2 链表的插入 接下来 完成链表的删除工作 我们在上一节的学习中 分别在链表的开头 中间和结尾插入了节点 现在我们想使链表恢复原来的样子 即 1 g
  • 更多的服务商从业者都开始关注刷脸支付

    刷脸支付就是通过人脸进行支付 简单来说消费者在接入蜻蜓的商家结账付款时 只需将脸面对蜻蜓上的摄像头即可完成支付 在这一过程中用户甚至不需要用手机 支付效率相比扫码支付更加的高效 此外由于支付宝刷脸支付是基于3D人脸识别技术 在安全也要比扫码
  • 【机器学习】编码、创造和筛选特征

    在机器学习和数据科学领域中 特征工程是提取 转换和选择原始数据以创建更具信息价值的特征的过程 假设拿到一份数据集之后 如何逐步完成特征工程呢 文章目录 一 特性类型分析 1 1 数值型特征 1 2 类别型特征 1 3 时间型特征 1 4 文
  • SpringMVC的全注解开发

    文章目录 一 spring mvc xml 中组件转化为注解形式 二 DispatcherServlet加载核心配置类 三 消除web xml 一 spring mvc xml 中组件转化为注解形式 跟之前全注解开发思路一致 xml配置文件