亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

SpringMVC的處理器攔截器HandlerInterceptor詳解

 更新時(shí)間:2024年01月30日 10:20:51   作者:曹牛牛  
這篇文章主要介紹了SpringMVC的處理器攔截器HandlerInterceptor詳解,SpringWebMVC的處理器攔截器,類似于Servlet開(kāi)發(fā)中的過(guò)濾器Filter,用于處理器進(jìn)行預(yù)處理和后處理,需要的朋友可以參考下

簡(jiǎn)介

SpringWebMVC的處理器攔截器,類似于Servlet開(kāi)發(fā)中的過(guò)濾器Filter,用于處理器進(jìn)行預(yù)處理和后處理。

應(yīng)用場(chǎng)景

1、日志記錄,可以記錄請(qǐng)求信息的日志,以便進(jìn)行信息監(jiān)控、信息統(tǒng)計(jì)等。

2、權(quán)限檢查:如登陸檢測(cè),進(jìn)入處理器檢測(cè)是否登陸,如果沒(méi)有直接返回到登陸頁(yè)面。

3、性能監(jiān)控:典型的是慢日志。

HandlerInterceptor

public interface HandlerInterceptor {
   /**
     * 預(yù)處理回調(diào)方法,實(shí)現(xiàn)處理器的預(yù)處理(如檢查登陸),第三個(gè)參數(shù)為響應(yīng)的處理器,自定義Controller
     * 返回值:true表示繼續(xù)流程(如調(diào)用下一個(gè)攔截器或處理器);false表示流程中斷(如登錄檢查失?。?,不會(huì)繼續(xù)調(diào)用其他的攔截器或處理器,此時(shí)我們需要通過(guò)response來(lái)產(chǎn)生響應(yīng);
   */
    boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception;
   /**
     * 后處理回調(diào)方法,實(shí)現(xiàn)處理器的后處理(但在渲染視圖之前),此時(shí)我們可以通過(guò)modelAndView(模型和視圖對(duì)象)對(duì)模型數(shù)據(jù)進(jìn)行處理或?qū)σ晥D進(jìn)行處理,modelAndView也可能為null。
   */
    void postHandle(
            HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView)
            throws Exception;
   /**
    * 整個(gè)請(qǐng)求處理完畢回調(diào)方法,即在視圖渲染完畢時(shí)回調(diào),如性能監(jiān)控中我們可以在此記錄結(jié)束時(shí)間并輸出消耗時(shí)間,還可以進(jìn)行一些資源清理,類似于try-catch-finally中的finally,但僅調(diào)用處理器執(zhí)行鏈中
   */
    void afterCompletion(
            HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
            throws Exception;
}

攔截器適配器HandlerInterceptorAdapter

有時(shí)候我們可能只需要實(shí)現(xiàn)三個(gè)回調(diào)方法中的某一個(gè),如果實(shí)現(xiàn)HandlerInterceptor接口的話,三個(gè)方法必須實(shí)現(xiàn),不管你需不需要,此時(shí)spring提供了一個(gè)HandlerInterceptorAdapter適配器(種適配器設(shè)計(jì)模式的實(shí)現(xiàn)),允許我們只實(shí)現(xiàn)需要的回調(diào)方法。

public abstract class HandlerInterceptorAdapter implements AsyncHandlerInterceptor {
    /**
     * 默認(rèn)是true
     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception {
        return true;
    }
    /**
     * This implementation is empty.
     */
    @Override
    public void postHandle(
            HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView)
            throws Exception {
    }
    /**
     * This implementation is empty.
     */
    @Override
    public void afterCompletion(
            HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
            throws Exception {
    }
    /**
     * 不是HandlerInterceptor的接口實(shí)現(xiàn),是AsyncHandlerInterceptor的,AsyncHandlerInterceptor實(shí)現(xiàn)了HandlerInterceptor
     */
    @Override
    public void afterConcurrentHandlingStarted(
            HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception {
    }
}

這樣在我們業(yè)務(wù)中比如要記錄系統(tǒng)日志,日志肯定是在afterCompletion之后記錄的,否則中途失敗了,也記錄了,那就扯淡了。一定是程序正常跑完后,我們記錄下那些對(duì)數(shù)據(jù)庫(kù)做個(gè)增刪改的操作日志進(jìn)數(shù)據(jù)庫(kù)。所以我們只需要繼承HandlerInterceptorAdapter,并重寫afterCompletion一個(gè)方法即可,因?yàn)閜reHandle默認(rèn)是true。

運(yùn)行流程總結(jié)如下:

1、攔截器執(zhí)行順序是按照Spring配置文件中定義的順序而定的。

2、會(huì)先按照順序執(zhí)行所有攔截器的preHandle方法,一直遇到return false為止,比如第二個(gè)preHandle方法是return false,則第三個(gè)以及以后所有攔截器都不會(huì)執(zhí)行。若都是return true,則按順序加載完preHandle方法。

3、然后執(zhí)行主方法(自己的controller接口),若中間拋出異常,則跟return false效果一致,不會(huì)繼續(xù)執(zhí)行postHandle,只會(huì)倒序執(zhí)行afterCompletion方法。

4、在主方法執(zhí)行完業(yè)務(wù)邏輯(頁(yè)面還未渲染數(shù)據(jù))時(shí),按倒序執(zhí)行postHandle方法。若第三個(gè)攔截器的preHandle方法return false,則會(huì)執(zhí)行第二個(gè)和第一個(gè)的postHandle方法和afterCompletion(postHandle都執(zhí)行完才會(huì)執(zhí)行這個(gè),也就是頁(yè)面渲染完數(shù)據(jù)后,執(zhí)行after進(jìn)行清理工作)方法。(postHandle和afterCompletion都是倒序執(zhí)行)

正常流程Demo

package com.bshf.recipe.demo.syslog;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class SyslogInterceptor implements HandlerInterceptor {
    /**
     * 預(yù)處理回調(diào)方法,實(shí)現(xiàn)處理器的預(yù)處理(如檢查登陸),第三個(gè)參數(shù)為響應(yīng)的處理器,自定義Controller
     * 返回值:true表示繼續(xù)流程(如調(diào)用下一個(gè)攔截器或處理器);false表示流程中斷(如登錄檢查失敗),不會(huì)繼續(xù)調(diào)用其他的攔截器或處理器,此時(shí)我們需要通過(guò)response來(lái)產(chǎn)生響應(yīng);
     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception {
        System.out.println("==========================================1================================================");
        return true;
    }
    /**
     * 后處理回調(diào)方法,實(shí)現(xiàn)處理器的后處理(但在渲染視圖之前),此時(shí)我們可以通過(guò)modelAndView(模型和視圖對(duì)象)對(duì)模型數(shù)據(jù)進(jìn)行處理或?qū)σ晥D進(jìn)行處理,modelAndView也可能為null。
     */
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
            ModelAndView modelAndView) throws Exception {
        System.out.println("==========================================post1================================================");
    }
    /**
     * 整個(gè)請(qǐng)求處理完畢回調(diào)方法,即在視圖渲染完畢時(shí)回調(diào),如性能監(jiān)控中我們可以在此記錄結(jié)束時(shí)間并輸出消耗時(shí)間,還可以進(jìn)行一些資源清理,類似于try-catch-finally中的finally,但僅調(diào)用處理器執(zhí)行鏈中
     */
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
            throws Exception {
        System.out.println("==========================================after1================================================");
    }
}
package com.bshf.recipe.demo.syslog;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class SyslogInterceptor2 implements HandlerInterceptor {
    /**
     * 預(yù)處理回調(diào)方法,實(shí)現(xiàn)處理器的預(yù)處理(如檢查登陸),第三個(gè)參數(shù)為響應(yīng)的處理器,自定義Controller
     * 返回值:true表示繼續(xù)流程(如調(diào)用下一個(gè)攔截器或處理器);false表示流程中斷(如登錄檢查失?。?,不會(huì)繼續(xù)調(diào)用其他的攔截器或處理器,此時(shí)我們需要通過(guò)response來(lái)產(chǎn)生響應(yīng);
     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception {
        System.out.println("==========================================2================================================");
        return true;
    }
    /**
     * 后處理回調(diào)方法,實(shí)現(xiàn)處理器的后處理(但在渲染視圖之前),此時(shí)我們可以通過(guò)modelAndView(模型和視圖對(duì)象)對(duì)模型數(shù)據(jù)進(jìn)行處理或?qū)σ晥D進(jìn)行處理,modelAndView也可能為null。
     */
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
            ModelAndView modelAndView) throws Exception {
        System.out.println("==========================================post2================================================");
    }
    /**
     * 整個(gè)請(qǐng)求處理完畢回調(diào)方法,即在視圖渲染完畢時(shí)回調(diào),如性能監(jiān)控中我們可以在此記錄結(jié)束時(shí)間并輸出消耗時(shí)間,還可以進(jìn)行一些資源清理,類似于try-catch-finally中的finally,但僅調(diào)用處理器執(zhí)行鏈中
     */
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
            throws Exception {
        System.out.println("==========================================after2================================================");
    }
}
package com.bshf.recipe.demo.syslog;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class SyslogInterceptor3 implements HandlerInterceptor {
    /**
     * 預(yù)處理回調(diào)方法,實(shí)現(xiàn)處理器的預(yù)處理(如檢查登陸),第三個(gè)參數(shù)為響應(yīng)的處理器,自定義Controller
     * 返回值:true表示繼續(xù)流程(如調(diào)用下一個(gè)攔截器或處理器);false表示流程中斷(如登錄檢查失?。粫?huì)繼續(xù)調(diào)用其他的攔截器或處理器,此時(shí)我們需要通過(guò)response來(lái)產(chǎn)生響應(yīng);
     */
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
            throws Exception {
        System.out.println("==========================================3================================================");
        return true;
    }
    /**
     * 后處理回調(diào)方法,實(shí)現(xiàn)處理器的后處理(但在渲染視圖之前),此時(shí)我們可以通過(guò)modelAndView(模型和視圖對(duì)象)對(duì)模型數(shù)據(jù)進(jìn)行處理或?qū)σ晥D進(jìn)行處理,modelAndView也可能為null。
     */
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler,
            ModelAndView modelAndView) throws Exception {
        System.out.println("==========================================post3================================================");
    }
    /**
     * 整個(gè)請(qǐng)求處理完畢回調(diào)方法,即在視圖渲染完畢時(shí)回調(diào),如性能監(jiān)控中我們可以在此記錄結(jié)束時(shí)間并輸出消耗時(shí)間,還可以進(jìn)行一些資源清理,類似于try-catch-finally中的finally,但僅調(diào)用處理器執(zhí)行鏈中
     */
    @Override
    public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
            throws Exception {
        System.out.println("==========================================after3================================================");
    }
}
<mvc:interceptors>
        <mvc:interceptor>
            <mvc:mapping path="/**"/>
            <bean class="com.bshf.recipe.demo.syslog.SyslogInterceptor" />
        </mvc:interceptor>
        
        <mvc:interceptor>
            <mvc:mapping path="/**"/>
            <bean class="com.bshf.recipe.demo.syslog.SyslogInterceptor2" />
        </mvc:interceptor>
        
        <mvc:interceptor>
            <mvc:mapping path="/**"/>
            <bean class="com.bshf.recipe.demo.syslog.SyslogInterceptor3" />
        </mvc:interceptor>
</mvc:interceptors>

<mvc:mapping path="/**"/>需要攔截的路徑,這里匹配所有。這里的配置順序?qū)⑹菙r截器執(zhí)行順序。

輸出結(jié)果

==========================================1================================================
==========================================2================================================
==========================================3================================================
==========================================post3================================================
==========================================post2================================================
==========================================post1================================================
==========================================after3================================================
==========================================after2================================================
==========================================after1================================================

post和after是倒序的!?。?!

中斷流程Demo

將SyslogInterceptor3的preHandle方法返回false。其他不變,再看輸出結(jié)果

==========================================1================================================
==========================================2================================================
==========================================3================================================
==========================================after2================================================
==========================================after1================================================

發(fā)現(xiàn)沒(méi)有了post,post方法一個(gè)都沒(méi)有輸出。不僅如此,你的主程序代碼(xxx.controller的一個(gè)接口)都不會(huì)被執(zhí)行,所以只要遇到return false,則直接進(jìn)行after清理工作,post和自己主程序代碼都將被略過(guò)。

到此這篇關(guān)于SpringMVC的處理器攔截器HandlerInterceptor詳解的文章就介紹到這了,更多相關(guān)攔截器HandlerInterceptor內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • SpringBoot中@ConditionalOnProperty的使用及作用詳解

    SpringBoot中@ConditionalOnProperty的使用及作用詳解

    這篇文章主要介紹了SpringBoot中@ConditionalOnProperty的使用及作用詳解,@ConditionalOnProperty通過(guò)讀取本地配置文件中的值來(lái)判斷 某些 Bean 或者 配置類 是否加入spring 中,需要的朋友可以參考下
    2024-01-01
  • Java日常練習(xí)題,每天進(jìn)步一點(diǎn)點(diǎn)(9)

    Java日常練習(xí)題,每天進(jìn)步一點(diǎn)點(diǎn)(9)

    下面小編就為大家?guī)?lái)一篇Java基礎(chǔ)的幾道練習(xí)題(分享)。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧,希望可以幫到你
    2021-07-07
  • Spring Boot2.0實(shí)現(xiàn)靜態(tài)資源版本控制詳解

    Spring Boot2.0實(shí)現(xiàn)靜態(tài)資源版本控制詳解

    這篇文章主要給大家介紹了關(guān)于Spring Boot2.0實(shí)現(xiàn)靜態(tài)資源版本控制的相關(guān)資料,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2018-11-11
  • Java中的泛型和泛型通配符詳解

    Java中的泛型和泛型通配符詳解

    這篇文章主要介紹了Java中的泛型和泛型通配符詳解,泛型的作用就是在編譯的時(shí)候能夠檢查類型安全,并且所有的強(qiáng)制轉(zhuǎn)換都是自動(dòng)和隱式的在沒(méi)有泛型的情況的下,通過(guò)對(duì)類型Object的引用來(lái)實(shí)現(xiàn)參數(shù)的“任意化”,需要的朋友可以參考下
    2023-07-07
  • SpringBoot中實(shí)現(xiàn)多數(shù)據(jù)源連接和切換的方案

    SpringBoot中實(shí)現(xiàn)多數(shù)據(jù)源連接和切換的方案

    在Spring Boot中,通過(guò)AbstractRoutingDataSource實(shí)現(xiàn)多數(shù)據(jù)源連接是一種常見(jiàn)的做法,這種技術(shù)允許你在運(yùn)行時(shí)動(dòng)態(tài)地切換數(shù)據(jù)源,從而支持對(duì)多個(gè)數(shù)據(jù)庫(kù)的操作,本文給大家介紹了SpringBoot中實(shí)現(xiàn)多數(shù)據(jù)源連接和切換的方案,需要的朋友可以參考下
    2024-11-11
  • dockerfile-maven-plugin極簡(jiǎn)教程(推薦)

    dockerfile-maven-plugin極簡(jiǎn)教程(推薦)

    這篇文章主要介紹了dockerfile-maven-plugin極簡(jiǎn)教程,本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2020-10-10
  • Java面向?qū)ο蠡A(chǔ)知識(shí)之委托和lambda

    Java面向?qū)ο蠡A(chǔ)知識(shí)之委托和lambda

    這篇文章主要介紹了Java面向?qū)ο蟮闹泻?lambda,文中有非常詳細(xì)的代碼示例,對(duì)正在學(xué)習(xí)java基礎(chǔ)的小伙伴們有很好的幫助,需要的朋友可以參考下
    2021-11-11
  • Kubernetes k8s集群之包管理器Helm方式

    Kubernetes k8s集群之包管理器Helm方式

    這篇文章主要介紹了Kubernetes k8s集群之包管理器Helm方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2024-08-08
  • 關(guān)于通過(guò)java調(diào)用datax,返回任務(wù)執(zhí)行的方法

    關(guān)于通過(guò)java調(diào)用datax,返回任務(wù)執(zhí)行的方法

    今天小編就為大家分享一篇關(guān)于通過(guò)java調(diào)用datax,返回任務(wù)執(zhí)行的方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧
    2019-08-08
  • 一次因Java應(yīng)用造成CPU過(guò)高的排查實(shí)踐過(guò)程

    一次因Java應(yīng)用造成CPU過(guò)高的排查實(shí)踐過(guò)程

    一個(gè)應(yīng)用占用CPU很高,除了確實(shí)是計(jì)算密集型應(yīng)用之外,通常原因都是出現(xiàn)了死循環(huán)。下面這篇文章主要給大家介紹了一次因Java應(yīng)用造成CPU過(guò)高的排查實(shí)踐過(guò)程,文中通過(guò)示例代碼介紹的非常詳細(xì),需要的朋友可以參考下
    2018-11-11

最新評(píng)論