首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> Java 程式設計 >> Java 相關知識

Spring MVC 基礎筆記(五):DispatcherServlet 初始化、HandlerMapping 三種策略與視圖解析器載入機制

     編輯:Java 相關知識

《Spring in Action》筆記第五部分,聚焦 Spring MVC 核心啟動流程:DispatcherServlet 初始化順序、三大 HandlerMapping 策略對比、視圖解析器自動發現機制與多映射器責任鏈模式。

DispatcherServlet 與 Struts ActionServlet 對比

項目Spring MVCStruts 1.x
前端控制器DispatcherServletActionServlet
映射配置*.htm (慣例)*.do / *.action
暴露技術隱藏副檔名暴露 .do/.action
上下文載入自動載入 /WEB-INF/[servlet-name]-servlet.xmlstruts-config.xml
業務 Bean 注入支援完整依賴注入Struts 1.2+ 始支援簡單屬性注入

DispatcherServlet 初始化鏈

HttpServlet.init(config)
 └─ HttpServletBean.init()
     └─ FrameworkServlet.initServletBean()
         └─ DispatcherServlet.initFrameworkServlet()
             ├─ initMultipartResolver()
             ├─ initLocaleResolver()
             ├─ initThemeResolver()
             ├─ initHandlerMappings()      // 關鍵:載入 HandlerMapping
             ├─ initHandlerAdapters()
             ├─ initHandlerExceptionResolvers()
             └─ initViewResolvers()       // 關鍵:載入 ViewResolver

視圖解析器自動發現邏輯

// DispatcherServlet.initViewResolvers() 簡化邏輯
if (detectAllViewResolvers) { // 預設 true
    Map beans = BeanFactoryUtils.beansOfTypeIncludingAncestors(
        getApplicationContext(), ViewResolver.class, true, false);
    // 按 order 排序,註冊到 this.viewResolvers
} else {
    ViewResolver vr = getApplicationContext().getBean("viewResolver", ViewResolver.class);
    this.viewResolvers = Collections.singletonList(vr);
}

同樣邏輯應用於 HandlerMapping、HandlerAdapter、HandlerExceptionResolver 等組件。

三大 HandlerMapping 策略深度對比

映射器映射規則優點缺點推薦度
BeanNameUrlHandlerMappingBean name = URL 路徑(/home.html → bean name="/home.html")零配置,約定優於配置URL 與 Bean 名強綁定,重構困難⭐ 原型/測試
SimpleUrlHandlerMapping屬性檔 映射 URL → Bean name集中管理,關注點分離,支援 order需維護映射表⭐⭐⭐⭐⭐ 生產首選
CommonsPathMapHandlerMappingController 類註解 @PathMap("/url")程式碼即配置,重構友好侵入業務代碼,屬硬編碼風格⭐⭐ 特定場景

SimpleUrlHandlerMapping 完整配置範例

<bean id="urlMapping" class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
    <property name="mappings">
        <props>
            <prop key="/listCourses.html">listCoursesController</prop>
            <prop key="/register.htm">registerStudentController</prop>
        </props>
    </property>
    <property name="order" value="1"/> <!-- 優先級 -->
</bean>

多 HandlerMapping 責任鏈

同時註冊多個映射器時,DispatcherServlet 按 order 從小到大遍歷,第一個返回非 null HandlerExecutionChain 者生效。實現 Ordered 介面或設 order 屬性控制優先級。

<bean class="...BeanNameUrlHandlerMapping" p:order="2"/> <!-- fallback -->
<bean class="...SimpleUrlHandlerMapping" p:order="1"/>  <!-- 主力 -->

InternalResourceViewResolver 載入細節

<bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
    <property name="prefix" value="/WEB-INF/jsp/"/>
    <property name="suffix" value=".jsp"/>
</bean>

Controller 回傳 new ModelAndView("home") → 解析為 /WEB-INF/jsp/home.jsp → RequestDispatcher.forward()。

關鍵收穫

  • DispatcherServlet 初始化順序固定,組件自動發現機制統一(detectAll* 預設 true)。
  • 生產環境**強烈建議**使用 SimpleUrlHandlerMapping 集中管理 URL 映射,避免 Bean 名洩露為 URL。
  • 多映射器/解析器/攔截器均支援 order 優先級,構建靈活的責任鏈。
  • 理解啟動流程有助於排查「為什麼我的 Controller 沒被調用」或「視圖解析失敗」等常見問題。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved