Spring web MVC和其他的web MVC框架一样,由请求驱动,围绕一个中心Servlet来进行设计,中心Servlet负责把请求派发给控制器(Controller),还提供其他的功能方便web应用的开发。Spirng的中心Servlet就是DispatcherServlet,它完全和Spring的Ioc容器集成,可以使用Spring的许多其他功能。
DispatcherServlet处理请求的流程是:
熟悉设计模式的人马上就能知道DispatcherServlet使用的是前端控制器模式(其他主流的web框架也是采用这种模式)。
1、DispatcherServlet本身的配置(基于web.xml的配置、基于代码的配置)
DispatcherServlet其实就是一个Servlet,从HttpServlet基类继承。所以需要在web.xml中进行配置,也是在同一个web.xml里通过URL Mapping来配置你希望由DispatcherServlet来处理的所有请求。如:
<web-app> <servlet> <servlet-name>example</servlet-name> <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>example</servlet-name> <url-pattern>/example/*</url-pattern> </servlet-mapping> </web-app>
在Servlet3.0+的环境下,也可以在代码里配置DispatcherServlet,如:
public class MyWebApplicationInitializer implements WebApplicationInitializer { @Override public void onStartup(ServletContext container) { ServletRegistration.Dynamic registration = container.addServlet("dispatcher", new DispatcherServlet()); registration.setLoadOnStartup(1); registration.addMapping("/example/*"); } }
WebApplicationInitializer是Spring MVC提供的一个接口,可以保证基于代码的配置在Servlet 3容器初始化的时候被识别并且使用。这个接口的一个抽象实现类是AbstractDispatcherServletInitializer,使用这个类可以更简单的对DispatcherServlet进行配置。
以上只是设置spring mvc的第一步。现在需要配置供spring mvc框架使用的bean(除了DispatcherServlet本身之外的bean)。
2、配置DispatcherServlet使用的bean(如:controller,view resolver,locale resolver,other web-related bean)。
在DispatcherServlet初始化的时候,SpringMVC会到你的web应用的web-inf文件夹下寻找一个命名为[servlet-name]-servlet.xml的文件,创建在该文件中定义的bean。这些bean保存在DispatcherServlet自己的应用上下文中(WebApplicationContext)。在SpringMVC中,每个DispatcherServlet都有自己的应用上下文,称为子应用上下文。如果存在一个根应用上下文的话(也叫父应用上下文),子应用上下文中的bean可以访问根应用上下文中的bean,而父应用上下文不能访问子应用上下文中的bean。如果子上下文中存在和父上下文中相同定义的bean,那么子上下文中的bean会覆盖父上下文中的bean。
DispatcherServlet使用一些特殊的bean来处理请求和渲染视图。这些特殊的bean是SpringMVC的一部分,你可以通过简单地在WebApplicationContext中配置来选择你要使用的bean。不过配置并不是必须的,因为你如果不配置的话,SpringMVC也会提供一系列默认的bean来使用。这些特殊的bean有:
HandlerMapping --
HandlerAdapter --
HandlerExceptionResolver--
ViewResolver--
LocaleResolver & LocaleContextResolver--
ThemeResolver--
MultipartResolver--
FlashMapManager--
对应每一个特殊的bean,SpringMVC提供了一组默认的实现,具体使用的是哪个默认的实现,这些信息保存在文件DispatcherServlet.properties中,这个文件在包org.springframework.web.servlet下。
肯定迟早会有些时候,你希望对这些默认的bean的某些属性进行自定义,如设置InternalResourceViewResolver的prefix属性为你的视图文件的文件夹路径。
这里要记住的是,你一旦配置了某个特殊的bean,那么这个bean的所有默认实现就失效了。比如你配置了InternalResourceViewResolver,那么ViewResolver的默认实现列表就被忽略了。
3、DispatcherServlet处理请求的顺序
当配置好一个DispatcherServlet时,一个请求(request)进来了,需要DispatcherServlet来处理,DispatcherServlet将按以下顺序来处理:
(1)DispatcherServlet寻找它自身的上下文WebApplicationContext,把找到的上下文作为一个属性绑定了request上,这样控制器或者在这个过程中的其他元素就可以使用这个上下文信息。绑定到request上时使用的默认的键是:DispatcherServlet.WEB_APPLICATION_CONTEXT_ATTRIBUTE.
(2)一个本地化解析器(LocaleResolver)被绑定到request上,这样其他的元素就可以使用这个解析器来解析本地化信息并使用(如渲染视图等),如果不需要本地化,就不需要这个解析器。
(3)一个主题解析器(ThemeResolver)被绑定到request上,这样其他的元素(比如:视图)就可以使用这个解析器来决定使用哪个主题,如果没有主题,可以忽略。
(4)如果指定了一个多部件解析器,那么就会对请求检查多部件,如果找到,该请求就会被封装到一个MultipartHttpServletRequest中,然后把它交给后续的过程进行处理。
(5)寻找合适的处理器Handler,如果处理器找到了,那么处理器相关的执行链(包括预处理器preprocessor,后处理器postprocessor,控制器controller)就会被执行,从而准备一个模型或者表现。
(6)如果模型被返回,那么对视图进行渲染。如果没有模型返回(由于预处理器或者后处理器的拦截,或者安全原因),就没有视图被渲染。因为请求已经全部处理完了。
HandlerExceptionResolver用来捕获和解析在处理请求过程中的异常。
4、DispatcherServlet的初始化配置参数
DispatcherServlet提供了以下几个初始化的配置参数。
contextClass --实现了WebApplicationContext的类,默认为XmlWebApplicationContext
contextConfigLocation --上下文配置路径,可以是多个路径用逗号分隔,如果存在相同的bean,那么后面文件中定义的优先于前面的。
namespace --WebApplication的命名空间,默认为:[servlet-name]-servlet
Spring framework---web MVC framework(1)---DispatcherServlet,布布扣,bubuko.com