詳談springboot過(guò)濾器和攔截器的實(shí)現(xiàn)及區(qū)別
前言
springmvc中有兩種很普遍的AOP實(shí)現(xiàn):
1.過(guò)濾器(Filter)
2.攔截器(Interceptor)
本篇面對(duì)的是一些剛接觸springboot的人群
所以主要講解filter和interceptor的簡(jiǎn)單實(shí)現(xiàn)和它們之間到底有什么區(qū)別
(一些復(fù)雜的功能我會(huì)之后發(fā)出文章,請(qǐng)記得關(guān)注)
Filter的簡(jiǎn)單實(shí)現(xiàn)
字面意思:過(guò)濾器就是過(guò)濾的作用,在web開發(fā)中過(guò)濾一些我們指定的url
那么它能幫我們過(guò)濾什么呢?
那功能可就多了:
比如過(guò)攔截掉我們不需要的接口請(qǐng)求
修改請(qǐng)求(request)和響應(yīng)(response)內(nèi)容
完成CORS跨域請(qǐng)求等等
現(xiàn)在我們來(lái)實(shí)現(xiàn)一個(gè)簡(jiǎn)單的過(guò)濾器:
可以新建一個(gè)filter包,隨著項(xiàng)目的擴(kuò)大過(guò)濾器會(huì)越來(lái)越多
在這里我新建了一個(gè)TestFilter類,實(shí)現(xiàn)Filter接口
@Component @WebFilter(urlPatterns = "/Blogs",filterName = "blosTest") public class TestFilter implements Filter{}
我們一步步來(lái)
1.@Component就是把這個(gè)類注入到IOC容器中
2.@WebFilter(urlPatterns = "/Blogs",filterName = "blosTest")說(shuō)明這是一個(gè)web過(guò)濾器,它攔截的url為/Blogs,過(guò)濾器名字為blogsTest
下面貼出實(shí)現(xiàn)接口之后的三個(gè)重構(gòu)方法:
@Override public void init(FilterConfig filterConfig) throws ServletException { } @Override public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException { HttpServletRequest request= (HttpServletRequest) servletRequest; HttpServletResponse response = (HttpServletResponse) servletResponse; System.out.printf("過(guò)濾器實(shí)現(xiàn)"); filterChain.doFilter(request,response); } @Override public void destroy() { }
初始化(init)和摧毀(destroy)方法一般不會(huì)用到,具體使用看下源碼便知
doFilter()是過(guò)濾器的核心
注意:在實(shí)現(xiàn)接口方法之后,我們要轉(zhuǎn)換request和response類型至HttpServlet,否則接下去的操作可能會(huì)報(bào)錯(cuò)。
如果過(guò)濾通過(guò),執(zhí)行filterChain.doFilter(request,response);
說(shuō)明這個(gè)url已經(jīng)經(jīng)過(guò)了我們的Filter
可以看到,只需要一個(gè)類我們就實(shí)現(xiàn)了一個(gè)簡(jiǎn)單的過(guò)濾器
當(dāng)然可以不用注解的方式,配置啟動(dòng)類
//過(guò)濾器 @Bean public FilterRegistrationBean filterRegistrationBean(){ FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean(); List<String> urlPatterns = new ArrayList<String>(); TestFilter testFilter = new TestFilter(); //new過(guò)濾器 urlPatterns.add("/Blogs"); //指定需要過(guò)濾的url filterRegistrationBean.setFilter(testFilter); //set filterRegistrationBean.setUrlPatterns(urlPatterns); //set return filterRegistrationBean; }
這也是可以的,本人其實(shí)還是比較推薦這種方式添加過(guò)濾器
Interceptor的簡(jiǎn)單實(shí)現(xiàn)
攔截器的實(shí)現(xiàn)比過(guò)濾器稍微復(fù)雜一點(diǎn)
我們同樣可以新建一個(gè)interceptor包
在里面新建一個(gè)名為MyInterceptor的類
public class MyInterceptor implements HandlerInterceptor {}
這個(gè)類實(shí)現(xiàn)了HandleInterceptor接口
直接貼類代碼,我會(huì)在代碼中注釋功能
public class MyInterceptor implements HandlerInterceptor { //在請(qǐng)求處理之前進(jìn)行調(diào)用(Controller方法調(diào)用之前 @Override public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception { System.out.printf("preHandle被調(diào)用"); return true; //如果false,停止流程,api被攔截 } //請(qǐng)求處理之后進(jìn)行調(diào)用,但是在視圖被渲染之前(Controller方法調(diào)用之后) @Override public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, ModelAndView modelAndView) throws Exception { System.out.println("postHandle被調(diào)用"); } //在整個(gè)請(qǐng)求結(jié)束之后被調(diào)用,也就是在DispatcherServlet 渲染了對(duì)應(yīng)的視圖之后執(zhí)行(主要是用于進(jìn)行資源清理工作) @Override public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception { System.out.println("afterCompletion被調(diào)用"); } }
它依次實(shí)現(xiàn)了三個(gè)方法
相比過(guò)濾器,攔截器還需要在springmvc中注入
所以我們打開啟動(dòng)類,寫入以下代碼
public class WarApplication { public static void main(String[] args) { SpringApplication.run(WarApplication.class, args); } //mvc控制器 //@Configuration static class WebMvcConfigurer extends WebMvcConfigurerAdapter{ //增加攔截器 public void addInterceptors(InterceptorRegistry registry){ registry.addInterceptor(new MyInterceptor()) //指定攔截器類 .addPathPatterns("/Handles"); //指定該類攔截的url } } }
這里我在/Handles這個(gè)url中進(jìn)行攔截
代碼寫完了,來(lái)看下結(jié)果
當(dāng)進(jìn)入指定url時(shí),我們執(zhí)行到了攔截器
接下來(lái)就可以根據(jù)需求去使用攔截器了
區(qū)別
過(guò)濾器和攔截器非常相似,但是它們有很大的區(qū)別
最簡(jiǎn)單明了的區(qū)別就是過(guò)濾器可以修改request,而攔截器不能
過(guò)濾器需要在servlet容器中實(shí)現(xiàn),攔截器可以適用于javaEE,javaSE等各種環(huán)境
攔截器可以調(diào)用IOC容器中的各種依賴,而過(guò)濾器不能
過(guò)濾器只能在請(qǐng)求的前后使用,而攔截器可以詳細(xì)到每個(gè)方法
區(qū)別很多,大家可以去查下
總的來(lái)說(shuō)
過(guò)濾器就是篩選出你要的東西,比如requeset中你要的那部分
攔截器在做安全方面用的比較多,比如終止一些流程
以上這篇詳談springboot過(guò)濾器和攔截器的實(shí)現(xiàn)及區(qū)別就是小編分享給大家的全部?jī)?nèi)容了,希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。
- springboot過(guò)濾器和攔截器的實(shí)例代碼
- SpringBoot 過(guò)濾器、攔截器、監(jiān)聽(tīng)器對(duì)比及使用場(chǎng)景分析
- SpringBoot實(shí)現(xiàn)攔截器、過(guò)濾器、監(jiān)聽(tīng)器過(guò)程解析
- SpringBoot實(shí)現(xiàn)過(guò)濾器、攔截器與切片的實(shí)現(xiàn)和區(qū)別
- SpringBoot全局異常處理機(jī)制和配置攔截器方式
- SpringBoot實(shí)現(xiàn)全局異常處理方法總結(jié)
- SpringBoot配置GlobalExceptionHandler全局異常處理器案例
- Springboot全局異常捕獲及try catch區(qū)別解析
- Springboot?過(guò)濾器、攔截器、全局異常處理的方案處理小結(jié)
相關(guān)文章
java中BigDecimal進(jìn)行加減乘除的基本用法
大家應(yīng)該對(duì)于不需要任何準(zhǔn)確計(jì)算精度的數(shù)字可以直接使用float或double運(yùn)算,但是如果需要精確計(jì)算的結(jié)果,則必須使用BigDecimal類,而且使用BigDecimal類也可以進(jìn)行大數(shù)的操作。下面這篇文章就給大家介紹介紹關(guān)于java中BigDecimal進(jìn)行加減乘除的基本用法。2016-12-12Java Socket編程實(shí)例(二)- UDP基本使用
這篇文章主要講解Java Socket編程中UDP的基本使用,希望能給大家做一個(gè)參考。2016-06-06java實(shí)現(xiàn)即時(shí)通信的完整步驟分享
這篇文章主要給大家介紹了關(guān)于java實(shí)現(xiàn)即時(shí)通信的完整步驟,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2020-09-09使用SpringMVC在redirect重定向的時(shí)候攜帶參數(shù)的問(wèn)題
這篇文章主要介紹了使用SpringMVC在redirect重定向的時(shí)候攜帶參數(shù)的問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-03-03