我们从访问正常时的调用顺序开始聊起:
在doService()方法中先把localeResolver、themeResolver以及上下文等放入request的属性中,方便后面有需要的人进行使用。根据flashMapManager获取重定向的原有的请求参数。最后调用doDispatch()方法
在doDispatch()方法中:
- 从HandlerMapping集合中获取HandlerExecutionChain。
- 从HandlerAdapter集合中找到支持HandlerExecutionChain的Handler的HandlerAdapter
- 把HandlerExecutionChain中HandlerInterceptor数组进行遍历,调用HandlerInterceptor的preHandle()方法判断是否继续执行这个请求。如果某个HandlerInterceptor的preHandle()方法返回false(即,不继续执行),则直接遍历已经遍历过的HandlerInterceptor的afterCompletion()方法,然后这个请求直接返回。
- HandlerAdapter调用handle()方法结合HandlerExecutionChain的Handler执行业务流程(例如:Controller的某个方法)得到ModelAndView对象。(注:这里面涉及太多内容,暂不展开描述。)
- 当ModelAndView对象不为空,且没有返回视图时,则会去使用RequestToViewNameTranslator对象找对应的视图名称。
- 遍历HandlerExecutionChain中HandlerInterceptor数组,调用HandlerInterceptor的postHandle()方法对Handler处理完后处理。
- 使用LocaleResolver对象进行国际化处理。
- 使用ViewResolver集合进行视图解析。
- 遍历HandlerExecutionChain中HandlerInterceptor数组,调用HandlerInterceptor的afterCompletion()方法对Handler处理完并被渲染完成后进行处理。
一些组件的说明:
- HandlerMapping
Handler的映射器,用于将普通的一个方法转换成一个Handler。例如:将@RequestMapping注解的方法转换成一个Handler。
- HandlerExecutionChain
处理调用链,包含一个Handler和一个HandlerInterceptor数组
- HandlerInterceptor
Handler拦截器。有三个方法,如下:
1、preHandle()可以拦截请求。
2、postHandle()在方法处理完后进行处理。
3、afterCompletion()整个请求完成后再次处理。
- HandlerAdapter
Handler适配器,用于支持多种处理器,例如:HttpRequestHandler、Controller的子类、Servlet的子类以及我们最常用的基于@RequestMapping注解的方法。
- LocaleResolver
国际化解析器
- ViewResolver
视图解析器
- ThemeResolver
主题解析器
- RequestToViewNameTranslator
用于在未显式提供视图名称时将传入的HttpServletRequest转换为逻辑视图名称。
- FlashMapManager
注:笔者暂时只知道用于管理重定向的数据。
- HandlerExceptionResolver
异常处理解析器