springboot自定義過濾器的方法
過濾器是Servlet的規(guī)范,是基于函數(shù)回調(diào)的,需要實(shí)現(xiàn)javax.servlet.Filter接口,依賴于Tomcat等容器,一般用于過濾請求的URL。
1自定義過濾器
自定義filter的實(shí)現(xiàn),本質(zhì)上只有一種方式,就是實(shí)現(xiàn)Filter接口。但是在spring中我們有時候也會通過繼承框架提供的XXXFilter,例如OncePerRequestFilter、 AbstractAuthenticationProcessingFilter(Spring Security使用的認(rèn)證過濾器),當(dāng)然,這些過濾器所實(shí)現(xiàn)的頂層接口還是Filter,只不過框架提供的過濾器都是有其特殊職能的,我們自己實(shí)現(xiàn)過濾器基本通過下面兩種方法。
1.1實(shí)現(xiàn)Filter接口
public class MyFilterOne implements Filter { ? ? ? @Override ? ? public void destroy() { ? ? ? ? //服務(wù)停止時銷毀; ? ? } ? ? ? @Override ? ? public void doFilter(ServletRequest srequest, ServletResponse sresponse, FilterChain filterChain) ? ? ? ? ? ? throws IOException, ServletException { ? ? ? ?? ? ? ? ? System.out.println("this is MyFilter,url :" + request.getRequestURI()); ? ? ? ? //1、進(jìn)入過濾器,通常在這里根據(jù)requet做一些事情 ? ? ? ? HttpServletRequest request = (HttpServletRequest) srequest; ? ? ? ? //2、放行,進(jìn)入下一個過濾器,如果是最后一個過濾器,就執(zhí)行Controller代碼 ? ? ? ? filterChain.doFilter(srequest, sresponse); ? ? ? ? //3、回到過濾器,通常在這里對response做一些處理 ? ? ? ? HttpServletResponse response = (HttpServletResponse) srequest; ? ? } ? ? ? @Override ? ? public void init(FilterConfig arg0) throws ServletException { ? ? ? ? //服務(wù)啟動時創(chuàng)建; ? ? } ? }
1.2繼承OncePerRequestFilter
下面的實(shí)現(xiàn),并沒有配置過濾路徑,所有的請求都會進(jìn)入到這個過濾器,但是它通過@Value獲取配置的url列表,然后用這個列表去和進(jìn)入過濾器的請求進(jìn)行對比,如果匹配就做一些操作,如果不匹配直接放行。個人覺得還是配置過濾路徑好。
@Component @Order(-1) public class MyFilterThree extends OncePerRequestFilter { ? ? ? private final List<Pattern> uriPatterns = new ArrayList<Pattern>(); ? ? ? @Value("#{'${filtered.uris:^$}'.split(',')}") ? ? private List<String> filteredUris; ? ? ? @PostConstruct ? ? public void initialize() { ? ? ? ? for (String uri : this.filteredUris) { ? ? ? ? ? ? try { ? ? ? ? ? ? ? ? this.uriPatterns.add(Pattern.compile(uri)); ? ? ? ? ? ? ? ? System.out.println(String.format("符合 '%s' 格式的URI,將進(jìn)行過濾處理,否則放行.", uri)); ? ? ? ? ? ? ? } catch (PatternSyntaxException patternSyntaxException) { ? ? ? ? ? ? ? ? System.out.println("Invalid regular expression pattern in filtered.uris: " + uri); ? ? ? ? ? ? } ? ? ? ? } ? ? } ? ? ? @Override ? ? protected void doFilterInternal(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, FilterChain filterChain) throws ServletException, IOException { ? ? ? ? System.out.println(httpServletRequest.getRequestURI()); ? ? ? ? System.out.println("需要過濾的路徑"+ Arrays.toString(uriPatterns.toArray())); ? ? ? ? System.out.println("進(jìn)入過濾器了"); ? ? ? ? filterChain.doFilter(httpServletRequest, httpServletResponse);//放行 ? ? ? ? System.out.println("又回到過濾器了"); ? ? } ? ? ? private boolean isMatchedUri(String uri) { ? ? ? ? if (StringUtils.isEmpty(uri)) { ? ? ? ? ? ? return false; ? ? ? ? } else { ? ? ? ? ? ? Iterator var2 = this.uriPatterns.iterator(); ? ? ? ? ? ? ? Pattern pattern; ? ? ? ? ? ? do { ? ? ? ? ? ? ? ? if (!var2.hasNext()) { ? ? ? ? ? ? ? ? ? ? return false; ? ? ? ? ? ? ? ? } ? ? ? ? ? ? ? ? ? pattern = (Pattern)var2.next(); ? ? ? ? ? ? } while(!pattern.matcher(uri).find()); ? ? ? ? ? ? ? return true; ? ? ? ? } ? ? } }
1.3使過濾器生效配置
使用配置類
@Configuration public class MyFilterConfiguration { ? ? ? @Bean ? ? public FilterRegistrationBean registerFilter() { ? ? ? ? System.out.println("MyFilterConfiguration"); ? ? ? ? FilterRegistrationBean registration = new FilterRegistrationBean(); ? ? ? ? registration.setFilter(new MyFilterOne()); ? ? ? ? registration.addUrlPatterns("/public/*");//過濾的路徑 ? ? ? ? registration.addInitParameter("paramName", "paramValue"); ? ? ? ? registration.setName("MyFilter"); ? ? ? ? registration.setOrder(1);//在過濾鏈中的執(zhí)行順序 ? ? ? ? return registration; ? ? } }
@WebFilter和@ServletComponentScan(basePackages = "")
個人比較喜歡這個方式,代碼量最小
第一步:在啟動類上添加注解@ServletComponentScan(basePackages = "")
第二步:Filter類添加@WebFilter注解,配置FilterRegistrationBean的屬性@WebFilter基本都有
@WebFilter(urlPatterns = "/selfAnnotation/*") @Order(-2) public class MyFilterFive extends OncePerRequestFilter { ? ? ? @Override ? ? protected void doFilterInternal(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, FilterChain filterChain) throws ServletException, IOException { ? ? ? ? ? System.out.println("進(jìn)入5號過濾器了"); ? ? } }
2 Filter生命周期
init():在構(gòu)造器被調(diào)用后,緊接著被調(diào)用。作用:用來初始化Filter。
doFilter():每一次攔截請求時都會調(diào)用。
destroy():方法在項(xiàng)目停止時調(diào)用,用來在對象被銷毀前做一些收尾工作。
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
通過Java 程序獲取Word中指定圖片的坐標(biāo)位置
本文介紹通過Java程序獲取Word文檔中指定圖片的坐標(biāo)位置,程序運(yùn)行環(huán)境是jdk1.8開發(fā)環(huán)境idea,通過java程序代碼給大家介紹的非常詳細(xì),需要的朋友參考下吧2021-05-05Java中String.split()的最詳細(xì)源碼解讀及注意事項(xiàng)
以前經(jīng)常使用String.split()方法,但是從來沒有注意,下面這篇文章主要給大家介紹了關(guān)于Java中String.split()最詳細(xì)源碼解讀及注意事項(xiàng)的相關(guān)資料,文中通過圖文介紹的非常詳細(xì),需要的朋友可以參考下2022-07-07JMeter連接Mysql數(shù)據(jù)庫的實(shí)現(xiàn)步驟
本文主要介紹了JMeter操作Mysql數(shù)據(jù)庫,文中通過示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下2021-12-12SpringBoot中實(shí)現(xiàn)@Scheduled動態(tài)定時任務(wù)
SpringBoot中的@Scheduled注解為定時任務(wù)提供了一種很簡單的實(shí)現(xiàn),本文主要介紹了SpringBoot中實(shí)現(xiàn)@Scheduled動態(tài)定時任務(wù),具有一定的參考價值,感興趣的可以了解一下2024-01-01當(dāng)面試官問我ArrayList和LinkedList哪個更占空間時,我是這么答的(面試官必問)
今天介紹一下Java的兩個集合類,ArrayList和LinkedList,這兩個集合的知識點(diǎn)幾乎可以說面試必問的。感興趣的朋友跟隨小編一起看看吧2020-08-08Java Thread之Sleep()使用方法總結(jié)
這篇文章主要介紹了Java Thread之Sleep()使用方法總結(jié),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2020-05-05MyBatis Plus 將查詢結(jié)果封裝到指定實(shí)體的方法步驟
這篇文章主要介紹了MyBatis Plus 將查詢結(jié)果封裝到指定實(shí)體的方法步驟,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2020-09-09