Springmvc中的HandlerAdaptor執行流程

今天講解一下在Springmvc中的HandlerAdaptor執行流程,明白這個過程,你就能畫出下面的圖:java

  

接下來咱們就來看看具體的實現過程吧。web

1.0在DispatcherServlet中找到getHandlerAdapter()方法spring

  

2.0進入getHandlerAdapter()具體的方法實現內apache

3.0獲取ModelAndView:api

4.0真正的執行者:瀏覽器

  

簡單地瞭解一下,仍是用具體的代碼來增強印象吧。架構

先把項目的架構搭建完成,依賴節點導入,進行下面的操做。mvc

MAVEN所需的依賴節點:app

    <dependencies>
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.3</version>
        </dependency>

        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-context</artifactId>
            <version>4.3.3.RELEASE</version>
        </dependency>

        <!--spring web jar 包-->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-web</artifactId>
            <version>4.3.3.RELEASE</version>
        </dependency>

        <!--springmvc jar 包-->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-webmvc</artifactId>
            <version>4.3.3.RELEASE</version>
        </dependency>

        <!--spring-ormjar 包-->
        <dependency>
            <groupId>org.springframework</groupId>
            <artifactId>spring-orm</artifactId>
            <version>4.3.3.RELEASE</version>
        </dependency>

        <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjweaver</artifactId>
            <version>1.8.7</version>
        </dependency>

        <!--servlet api包-->
        <dependency>
            <groupId>javax.servlet</groupId>
            <artifactId>servlet-api</artifactId>
            <version>2.5</version>
        </dependency>

        <dependency>
            <groupId>org.apache.taglibs</groupId>
            <artifactId>taglibs-standard-spec</artifactId>
            <version>1.2.1</version>
        </dependency>

        <dependency>
            <groupId>org.apache.taglibs</groupId>
            <artifactId>taglibs-standard-impl</artifactId>
            <version>1.2.1</version>
        </dependency>

    </dependencies>

    <build>
        <resources>
            <resource>
                <directory>src/main/java</directory>
                <includes>
                    <include>**/*.xml</include>
                    <include>**/*.properties</include>
                </includes>
            </resource>
        </resources>
    </build>

web.xml的配置:jsp

<?xml version="1.0" encoding="UTF-8"?>
<web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
         xmlns="http://java.sun.com/xml/ns/javaee"
         xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
         xsi:schemaLocation="
         http://java.sun.com/xml/ns/javaee
         http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd"
         version="2.5">
  <display-name>Archetype Created Web Application</display-name>

  <!--中央調度器-->
  <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:applicationContextfirst.xml</param-value>
    </init-param>
  </servlet>
  
  <servlet-mapping>
    <servlet-name>springmvc</servlet-name>
    <url-pattern>/</url-pattern>
  </servlet-mapping>

</web-app>

 

示例一:實現簡單的訪問

準備名稱爲FirstController的類

public class FirstController implements Controller{

    /*第一個示例實現Controller接口*/
    public ModelAndView handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception {
        ModelAndView av=new ModelAndView();
        av.setViewName("index");
        return av;
    }

} 

 編寫applicationfirst.xml:

 <!--第一種方式實現-->
    <!--處理器-->
    <bean id="firstController" class="cn.happy.controller.FirstController"></bean>

    <!--處理器映射器-->
    <bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
        <property name="mappings">
            <props>
                <prop key="/hello">firstController</prop>
            </props>
        </property>
    </bean>

    <!--視圖解析器-->
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <property name="prefix" value="/"></property>
        <property name="suffix" value=".jsp"></property>
    </bean>

效果圖:

    

實例二:(註解方式)

@org.springframework.stereotype.Controller
public class FirstController {

    /*第二個示例註解方式*/
    @RequestMapping("1")
    public String index(){
        return "index";
    }

    @RequestMapping("2")
    public String index2(){
        return "index2";
    }

}

applicationfirst.xml中的配置:

 <!--第二種方式實現-註解-->
     <!--配置包掃描器-->
        <context:component-scan base-package="cn.happy.controller"></context:component-scan>

        <!--視圖解析器-->
        <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
            <property name="prefix" value="/"></property>
            <property name="suffix" value=".jsp"></property>
        </bean>

如今項目中註解式開發仍是不錯的,簡單,簡潔。

效果圖:

 

示例三:(根據不用訪問名稱來實現訪問同一頁面)
public class FirstController extends AbstractController{
       /*不一樣的訪問名稱訪問同一個方法*/
    protected ModelAndView handleRequestInternal(HttpServletRequest request, HttpServletResponse response) throws Exception {
        ModelAndView av=new ModelAndView();
        av.setViewName("index");
        return av;
    }

}

applicationfirst.xml中的配置:

<!--第三種實現方式 不一樣的訪問名稱AbstractResolver-->
      <!--處理器-->
    <bean id="firstController" class="cn.happy.controller.FirstController">
    </bean>

    <!--視圖解析器-->
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <property name="prefix" value="/"></property>
        <property name="suffix" value=".jsp"></property>
    </bean>

    <!--處理器映射器-->
    <bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
        <property name="mappings">
            <props>
                <prop key="/h1">firstController</prop>
                <prop key="/h2">firstController</prop>
            </props>
        </property>
    </bean>

效果圖:

 

上圖是接口Controller的實現類,咱們能夠很清晰的看到Controller-------->AbstractController------->MultiActionController,還有一些其餘的子類,在這裏咱們就不一一介紹了,就拿MultiActionController爲例。

 

上面的圈起來的兩個類,就是方法名稱解析所用到的。

先來第一種方式:PropertiesMethodNameResolver

public class FirstController extends MultiActionController{
       /*繼承MultiActionController   propertiesMethodNameResolver*/
    public ModelAndView doFirst(HttpServletRequest request, HttpServletResponse response)  {
        ModelAndView av=new ModelAndView();
        av.setViewName("index");
        return av;
    }

    public ModelAndView doSecond(HttpServletRequest request, HttpServletResponse response){
        ModelAndView av=new ModelAndView();
        av.setViewName("index2");
        return av;
    }

}

applicationfirst.xml中的配置:

<!--第四種方式實現 第一種 MultiActionSesolver-->
    <!--處理器-->
    <bean id="firstController" class="cn.happy.controller.FirstController">
        <!--關聯方法名稱解析器-->
        <property name="methodNameResolver" ref="propertiesMethodNameResolver"></property>
    </bean>

    <!--視圖解析器-->
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <property name="prefix" value="/"></property>
        <property name="suffix" value=".jsp"></property>
    </bean>

    <!--處理器映射器-->
    <bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
        <property name="mappings">
            <props>
                <prop key="/*">firstController</prop>
            </props>
        </property>
    </bean>

    <!--方法名稱解析器  PropertiesMethodNameResolver-->
    <bean  id="propertiesMethodNameResolver" class="org.springframework.web.servlet.mvc.multiaction.PropertiesMethodNameResolver">
        <property name="mappings">
            <props>
                <prop key="/h1">doFirst</prop>
                <prop key="/h2">doSecond</prop>
            </props>
        </property>
    </bean>

    

效果圖:

    

另外一種方式:ParameterMethodNameResolver,先來一張圖看一下

   

當你不指定paramName的時候默認爲action

public class FirstController extends MultiActionController{
    /*繼承MultiActionController   parameterMethodNameResolver*/
    public ModelAndView doFirst(HttpServletRequest request, HttpServletResponse response)  {
        ModelAndView av=new ModelAndView();
        av.setViewName("index");
        return av;
    }

    public ModelAndView doSecond(HttpServletRequest request, HttpServletResponse response){
        ModelAndView av=new ModelAndView();
        av.setViewName("index2");
        return av;
    }

}

applicationContextfirst.xml的配置:

  <!--第四種方式實現  第二種 MultiActionSesolver-->
    <!--處理器-->
    <bean id="firstController" class="cn.happy.controller.FirstController">
        <!--關聯方法名稱解析器-->
        <property name="methodNameResolver" ref="parameterMethodNameResolver"></property>
    </bean>

    <!--視圖解析器-->
    <bean class="org.springframework.web.servlet.view.InternalResourceViewResolver">
        <property name="prefix" value="/"></property>
        <property name="suffix" value=".jsp"></property>
    </bean>

    <!--處理器映射器-->
    <bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
        <property name="mappings">
            <props>
                <prop key="/*">firstController</prop>
            </props>
        </property>
    </bean>

    <!--方法名稱解析器  PropertiesMethodNameResolver-->
    <bean  id="parameterMethodNameResolver" class="org.springframework.web.servlet.mvc.multiaction.ParameterMethodNameResolver">
        <property name="paramName" value="actionName"></property>
    </bean>

指定了方法名稱解析器的參數,效果圖以下:

   
當註釋掉以後,默認爲action,效果圖:

 <!--方法名稱解析器  PropertiesMethodNameResolver-->
    <bean  id="parameterMethodNameResolver" class="org.springframework.web.servlet.mvc.multiaction.ParameterMethodNameResolver">
        <!--<property name="paramName" value="actionName"></property>-->
    </bean>

   

最後再來一組,訪問外部資源和訪問內部資源

public class FirstController extends MultiActionController{
  public ModelAndView doFirst(HttpServletRequest request, HttpServletResponse response)  {
        ModelAndView av=new ModelAndView();
        av.setViewName("jd");
        return av;
    }

}

applicationContextfirst.xml的配置:

    <!--外部資源方式-->
     <!--處理器-->
    <bean id="firstController" class="cn.happy.controller.FirstController">
        <property name="methodNameResolver" ref="parameterMethodNameResolver"></property>
    </bean>
    <!--方法名稱解析器-->
    <bean id="parameterMethodNameResolver" class="org.springframework.web.servlet.mvc.multiaction.ParameterMethodNameResolver">
    </bean>

    <!--處理器映射器-->
    <bean class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
        <property name="mappings">
            <props>
                <prop key="/*">firstController</prop>
            </props>
        </property>
    </bean>

    <!--外部資源-->
   <bean id="jd" class="org.springframework.web.servlet.view.RedirectView">
       <property name="url" value="http://www.jd.com"></property>
   </bean>

    <bean class="org.springframework.web.servlet.view.BeanNameViewResolver"></bean>

在瀏覽器地址欄中填寫如圖所示地址:

    

內部資源訪問:

只須要更改一處便可:

 <!--外部資源-->
    <bean id="jd" class="org.springframework.web.servlet.view.JstlView">
       <property name="url" value="index2.jsp"></property>
   </bean>

效果圖:

   

相關文章
相關標籤/搜索