javascript
理解SpringMVC-------DispatchServlet
在web.xml中,可以找到這么一段配置文件,它的作用是將DispatchServlet作為一個servlet加載到servlet容器中 其中,是將某一類請求轉交給這個servlet進行處理
<servlet><servlet-name>SpringMVC</servlet-name><servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class><init-param><param-name>contextConfigLocation</param-name><param-value>classpath:spring-mvc.xml</param-value></init-param><load-on-startup>1</load-on-startup>//是否開啟異步支持<!--<async-supported>true</async-supported>--> </servlet> <servlet-mapping><servlet-name>SpringMVC</servlet-name><url-pattern>/</url-pattern> </servlet-mapping> 復制代碼然后我們開始解析一下DispatchServlet具體做了些什么事情
1)加載DispatcherServlet.properties中的屬性
private static final String DEFAULT_STRATEGIES_PATH = "DispatcherServlet.properties";...static {// Load default strategy implementations from properties file.// This is currently strictly internal and not meant to be customized// by application developers.try {ClassPathResource resource = new ClassPathResource(DEFAULT_STRATEGIES_PATH, DispatcherServlet.class);defaultStrategies = PropertiesLoaderUtils.loadProperties(resource);}catch (IOException ex) {throw new IllegalStateException("Could not load 'DispatcherServlet.properties': " + ex.getMessage());} } 復制代碼找到DispatcherServlet.properties,其中內容如下
# Default implementation classes for DispatcherServlet's strategy interfaces. # Used as fallback when no matching beans are found in the DispatcherServlet context. # Not meant to be customized by application developers.org.springframework.web.servlet.LocaleResolver=org.springframework.web.servlet.i18n.AcceptHeaderLocaleResolverorg.springframework.web.servlet.ThemeResolver=org.springframework.web.servlet.theme.FixedThemeResolverorg.springframework.web.servlet.HandlerMapping=org.springframework.web.servlet.handler.BeanNameUrlHandlerMapping,\org.springframework.web.servlet.mvc.annotation.DefaultAnnotationHandlerMappingorg.springframework.web.servlet.HandlerAdapter=org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter,\org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter,\org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerAdapterorg.springframework.web.servlet.HandlerExceptionResolver=org.springframework.web.servlet.mvc.annotation.AnnotationMethodHandlerExceptionResolver,\org.springframework.web.servlet.mvc.annotation.ResponseStatusExceptionResolver,\org.springframework.web.servlet.mvc.support.DefaultHandlerExceptionResolverorg.springframework.web.servlet.RequestToViewNameTranslator=org.springframework.web.servlet.view.DefaultRequestToViewNameTranslatororg.springframework.web.servlet.ViewResolver=org.springframework.web.servlet.view.InternalResourceViewResolverorg.springframework.web.servlet.FlashMapManager=org.springframework.web.servlet.support.SessionFlashMapManager 復制代碼所以我們可以知道,這個DispatcherServlet.properties的作用是將默認實現類的路徑以鍵值對的形式加載進來 LocaleResolver(本地化解析器,AcceptHeaderLocaleResolver) ThemeResolver(主題解析器,FixedThemeResolver) HandlerMapping(映射處理器,BeanNameUrlHandlerMapping) HandlerAdapter(處理適配器,多個) ViewResolver(視圖解析器,InternalResourceViewResolver) RequestToViewNameTranslator(將請求名稱轉化為視圖名稱,DefaultRequestToViewNameTranslator)
2)初始化加載SpringMVC框架下需要配置的基本的bean
protected void initStrategies(ApplicationContext context) {initMultipartResolver(context);initLocaleResolver(context);initThemeResolver(context);initHandlerMappings(context);initHandlerAdapters(context);initHandlerExceptionResolvers(context);initRequestToViewNameTranslator(context);initViewResolvers(context);initFlashMapManager(context); } 復制代碼這里的作用是將SpringMVC框架所需的各個基本的bean初始化,并加載到容器中
3)重寫doService()方法
DispatchServlet實際上繼承于FrameworkServlet,并且在其具體實現中重寫了doService()方法。 doService()主要是將一些全局屬性set到request中,具體的請求處理則調用并在doDispatch()中處理
4)doDipatch()將請求處理后轉發到Controller
/** * Process the actual dispatching to the handler. * <p>The handler will be obtained by applying the servlet's HandlerMappings in order. * The HandlerAdapter will be obtained by querying the servlet's installed HandlerAdapters * to find the first that supports the handler class. * <p>All HTTP methods are handled by this method. It's up to HandlerAdapters or handlers * themselves to decide which methods are acceptable. * @param request current HTTP request * @param response current HTTP response * @throws Exception in case of any kind of processing failure */ protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {//獲取當前要處理的requestHttpServletRequest processedRequest = request;HandlerExecutionChain mappedHandler = null;boolean multipartRequestParsed = false;WebAsyncManager asyncManager = WebAsyncUtils.getAsyncManager(request);try {ModelAndView mv = null;Exception dispatchException = null;try {//判斷是否有文件上傳processedRequest = checkMultipart(request);multipartRequestParsed = (processedRequest != request);// Determine handler for the current request.//獲取HandlerExecutionChain,其中包含了private HandlerInterceptor[] interceptors,即攔截器的一個數組mappedHandler = getHandler(processedRequest);if (mappedHandler == null || mappedHandler.getHandler() == null) {noHandlerFound(processedRequest, response);return;}// Determine handler adapter for the current request.//獲取HandlerAdapterHandlerAdapter ha = getHandlerAdapter(mappedHandler.getHandler());// Process last-modified header, if supported by the handler.//從request中獲取HTTP請求方法String method = request.getMethod();boolean isGet = "GET".equals(method);if (isGet || "HEAD".equals(method)) {long lastModified = ha.getLastModified(request, mappedHandler.getHandler());if (logger.isDebugEnabled()) {logger.debug("Last-Modified value for [" + getRequestUri(request) + "] is: " + lastModified);}if (new ServletWebRequest(request, response).checkNotModified(lastModified) && isGet) {return;}}//如果有攔截器,則處理其前置方法preHandleif (!mappedHandler.applyPreHandle(processedRequest, response)) {return;}// Actually invoke the handler.//返回處理后的modelViewmv = ha.handle(processedRequest, response, mappedHandler.getHandler());//判斷是否是異步請求if (asyncManager.isConcurrentHandlingStarted()) {return;}//如果view為空,返回一個默認的viewapplyDefaultViewName(processedRequest, mv);//處理攔截器的后置方法postHandlemappedHandler.applyPostHandle(processedRequest, response, mv);}catch (Exception ex) {dispatchException = ex;}processDispatchResult(processedRequest, response, mappedHandler, mv, dispatchException);}catch (Exception ex) {triggerAfterCompletion(processedRequest, response, mappedHandler, ex);}catch (Error err) {triggerAfterCompletionWithError(processedRequest, response, mappedHandler, err);}finally {//判斷是否是異步請求if (asyncManager.isConcurrentHandlingStarted()) {// Instead of postHandle and afterCompletionif (mappedHandler != null) {mappedHandler.applyAfterConcurrentHandlingStarted(processedRequest, response);}}else {// Clean up any resources used by a multipart request.//刪除上傳資源if (multipartRequestParsed) {cleanupMultipart(processedRequest);}}} } 復制代碼總結
以上是生活随笔為你收集整理的理解SpringMVC-------DispatchServlet的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Valve 公布 2023 年全年 St
- 下一篇: 酷狗音乐怎么设置循环播放