Spring MVC 实现原理 ① 初始化阶段

前言

Spring mvc 的实现我们主要分两个阶段来了解,一个是初始化阶段,一个是调用阶段,在了解mvc之前,可以先了解一下servlet的生命周期
servlet生命周期包括init一次,service多次,destroy一次
而我们下面要了解的mvc初始化阶段,核心就是DispatcherServlet

mvc初始化阶段

在这里插入图片描述
来看DispatcherServlet

DispatcherServlet

在这里插入图片描述
我们需要找到的是servlet的init方法真正的实现位置,即HttpServletBean的init方法

HttpServletBean

在这里插入图片描述
该方法首先将配置参数映射到此servlet的bean属性上,紧接着调用子类初始化。
我们来看子类初始化做了啥事情

FrameworkServlet

DispatcherServlet继承了FrameworkServlet,而FrameworkServlet继承了HttpServletBean并重写了initServletBean

	/**
	 * Overridden method of {@link HttpServletBean}, invoked after any bean properties
	 * have been set. Creates this servlet's WebApplicationContext.
	 */
	@Override
	protected final void initServletBean() throws ServletException {
		getServletContext().log("Initializing Spring " + getClass().getSimpleName() + " '" + getServletName() + "'");
		if (logger.isInfoEnabled()) {
			logger.info("Initializing Servlet '" + getServletName() + "'");
		}
		long startTime = System.currentTimeMillis();

		try {
			this.webApplicationContext = initWebApplicationContext();
			initFrameworkServlet();
		}
		catch (ServletException | RuntimeException ex) {
			logger.error("Context initialization failed", ex);
			throw ex;
		}

		if (logger.isDebugEnabled()) {
			String value = this.enableLoggingRequestDetails ?
					"shown which may lead to unsafe logging of potentially sensitive data" :
					"masked to prevent unsafe logging of potentially sensitive data";
			logger.debug("enableLoggingRequestDetails='" + this.enableLoggingRequestDetails +
					"': request parameters and headers will be " + value);
		}

		if (logger.isInfoEnabled()) {
			logger.info("Completed initialization in " + (System.currentTimeMillis() - startTime) + " ms");
		}
	}

该方法首先是初始化了spring web容器,webApplicationContext,关于容器,请看spring容器,初始化后,会触发ContextRefreshedEvent事件,调用onRefresh初始化三大件,关于ContextRefreshedEvent,可以参考ContextRefreshedEvent

onRefresh

该方法便是初始化mvc九大件的实际入口

	/**
	 * Initialize the strategy objects that this servlet uses.
	 * <p>May be overridden in subclasses in order to initialize further strategy objects.
	 */
	protected void initStrategies(ApplicationContext context) {
		initMultipartResolver(context); //用于处理文件上传
		initLocaleResolver(context); // 主要作用在于根据不同的用户区域展示不同的视图
		initThemeResolver(context); // 主题就是系统的整体样式或风格,可通过Spring MVC框架提供的主题(theme)设置应用的整体样式风格,提高用户体验。Spring MVC的主题就是一些静态资源的集合,即包括样式及图片,用来控制应用的视觉风格。
		/**
		*用来查找Handler的。在SpringMVC中会有很多请求,每个请求都需要一个Handler处理,具体接收到一个请求之后使用哪个Handler进行处理呢?这就是HandlerMapping需要做的事。
		*作用是根据当前请求的找到对应的 Handler,并将 Handler(执行程序)与一堆 HandlerInterceptor(拦截器,也是它来处理的)封装到 HandlerExecutionChain 对象中,返回给中央调度器。
		**/
		initHandlerMappings(context); 
		/**
		*因为SpringMVC中的Handler可以是任意的形式,只要能处理请求就ok,但是Servlet需要的处理方法的结构却是固定的,都是以request和response为参数的方法。如何让固定的Servlet处理方法调用灵活的Handler来进行处理呢?这就是HandlerAdapter要做的事情。
		**/
		initHandlerAdapters(context);
		// 对异常情况进行处理
		initHandlerExceptionResolvers(context);
		// Spring MVC是通过ViewName来找到对应的视图的,而此接口的作用就是从request中获取viewName。
		initRequestToViewNameTranslator(context);
		/**
		*ViewResolver用来将String类型的视图名和Locale解析为View类型的视图。View是用来渲染页面的,也就是将程序返回的参数填入模板里,生成html(也可能是其它类型)文件。这里就有两个关键问题:使用哪个模板?用什么技术(规则)填入参数?这其实是ViewResolver主要要做的工作。
		*ViewResolver需要找到渲染所用的模板和所用的技术(也就是视图的类型)进行渲染,具体的渲染过程则交由不同的视图自己完成。
		**/
		initViewResolvers(context);
		// 用来管理FlashMap的,FlashMap主要用在redirect中传递参数。
		initFlashMapManager(context);
	}

关于九大件可以,参考一下mvc九大件
Handler是用来干活的工具;HandlerMapping用于根据需要干的活找到相应的工具;HandlerAdapter是使用工具干活的人

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值