SpringMVC攔截器創建配置及執行順序

SpringMVC攔截器介紹

springMVC 中的攔截器用於攔截控制器方法的執行。

先創建出前置需要的一些條件:

<a th:href="@{/testInterceptor}" rel="external nofollow" >測試攔截器</a>

後端:

@Controller
public class TestController {
    @RequestMapping("/testInterceptor")
    public String testInterceptor() {
        return "success";
    }
}

一、創建攔截器

新建一個包 interceptors,在下面創建一個攔截器 FirstInterceptor ,並且要實現 HandlerInterceptor 接口。

快捷鍵Ctrl + O,快速重寫方法,圖示裡的 3 個。

public class FirstInterceptor implements HandlerInterceptor {
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("FirstInterceptor --> preHandle");
        return false;
    }
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("FirstInterceptor --> postHandle");
    }
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("FirstInterceptor --> afterCompletion");
    }
}

preHandle: 在當前控制器方法執行之前執行。

postHandle: 在當前控制器方法執行之後執行。

afterCompletion:處理完視圖和模型數據,渲染視圖完畢之後執行。

二、配置攔截器

在 springMVC 配置文件裡配置攔截器,對象就是FirstInterceptor 類:

<!-- 配置攔截器 -->
  <mvc:interceptors>
      <bean class="com.pingguo.mvc.interceptors.FirstInterceptor"></bean>
  </mvc:interceptors>

重新部署,訪問http://localhost:8080/springmvc/,發現頁面空白,查看控制器日志看到有打印:

說明攔截成功。

看下上面重新的三個方法中,隻有preHandle有返回值,是個佈爾類型:false 表示攔截,true 表示放行。

修改上面preHandle的返回為 true,重新部署後再次訪問首頁,可以訪問成功。

查看控制臺打印輸出,看到在渲染之前,前面2個方法執行瞭:preHandle、postHandle 。

在非常多的 Thymeleaf 渲染之後,最後一個 afterCompletion 也執行瞭。

現在繼續點擊首頁裡的新加的超鏈接,發現也會被攔截放行。

說明這種配置方式,會攔截所有的請求。

設置不需要攔截的請求

可以通過 ref 或 bean 標簽設置攔截器:

  • 通過mvc:mapping設置需要攔截的請求通過
  • mvc:exclude-mapping設置需要排除的請求
<bean name="firstInterceptor" class="com.pingguo.mvc.interceptors.FirstInterceptor"></bean>
    <!-- 配置攔截器 -->
    <mvc:interceptors>
        <mvc:interceptor>
            <mvc:mapping path="/**"/>
            <mvc:exclude-mapping path="/"></mvc:exclude-mapping>
            <ref bean="firstInterceptor"></ref>
        </mvc:interceptor>
    </mvc:interceptors>

註意這裡我在外部註冊瞭一個 bean 叫 firstInterceptor,以便 ref 引用。

  • <mvc:mapping path="/**"/>,表示攔截所有請求。
  • <mvc:exclude-mapping path="/">,表示除瞭首頁不攔截。

也就是說,現在我訪問http://localhost:8080/springmvc/的時候,應該不攔截。

訪問http://localhost:8080/springmvc/testInterceptor就會攔截瞭。

試一下,先訪問 http://localhost:8080/springmvc/:

可以正常打開首頁,並且控制臺也沒有輸出攔截器裡的內容:

現在繼續訪問 http://localhost:8080/springmvc/testInterceptor,

攔截瞭。

三、多個攔截器的執行順序

繼續新建一個攔截器SecondInterceptor,註意這次我加瞭 @Component,方便在配置文件中直接ref引用使用。

@Component
public class SecondInterceptor implements HandlerInterceptor {
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
        System.out.println("SecondInterceptor --> preHandle");
        return true;
    }
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
        System.out.println("SecondInterceptor --> postHandle");
    }
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
        System.out.println("SecondInterceptor --> afterCompletion");
    }
}

修改攔截器配置:

<!-- 配置攔截器 -->
    <mvc:interceptors>
        <ref bean="firstInterceptor"></ref>
        <ref bean="secondInterceptor"></ref>
    </mvc:interceptors>

重新部署,訪問下首頁http://localhost:8080/springmvc/,查看控制臺打印輸出。

可以發現,preHandle 方法執行的順序是 FirstInterceptor->SecondInterceptor。其他 2 個方法則是順序倒過來。

若每個攔截器的 preHandle()都返回 true:

  • 執行順序跟配置裡的順序有關,在上面攔截器裡 firstInterceptor 就是在 secondInterceptor前面。
  • preHandle()會按照配置的順序執行,而postHandle()和afterComplation()`會按照配置的反序執行。

若某個攔截器的preHandle()返回瞭false:

  • preHandle()返回false和它之前的攔截器的preHandle()都會執行。
  • postHandle()都不執行。
  • 返回false的攔截器之前的攔截器的afterComplation()會執行。

試一下,把 SecondInterceptor 中的preHandle()修改返回 false,再次請求下首頁:

符合預期。

這些過程可以打斷點看下源碼的執行過程。

以上就是SpringMVC攔截器創建配置及執行順序的詳細內容,更多關於SpringMVC攔截器配置的資料請關註WalkonNet其它相關文章!

推薦閱讀: