SpringMVC攔截器失效問題及解決方法
SpringMVC攔截器失效
項目場景:
項目(springmvc)中新寫了些攔截器沒生效,記錄一下原因
問題描述:
使用的xml的方式配置攔截器,具體如下
1.首先新建一個類實現(xiàn)HandlerInterceptor
public class LoginInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
String sre = ".....";
return false;
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
}
}2.接著在xml中注冊攔截器
<mvc:interceptors>
<mvc:interceptor>
<mvc:mapping path="/apiweb/**"/>
<bean class="com.xxx.interceptor.LoginInterceptor"/>
</mvc:interceptor>
</mvc:interceptors>好像沒什么大問題,實現(xiàn) HandlerInterceptor接口,再將對應(yīng)的類注冊到容器中
但是,細(xì)節(jié)上存在很多問題,導(dǎo)致目前的配置中攔截器不生效
原因分析:
debug時發(fā)現(xiàn)根本就沒有在容器中注冊新寫的攔截類,首先要做的是看看為什么沒有注冊成功后;之后再debug時返現(xiàn)url攔截路徑不對,又修改了攔截路徑??偣彩?strong>兩個問題,一個一個分析
在xml中配置<mvc:annotation-driven/>,從網(wǎng)上的信息看,這段代碼會注冊HandlerMapping和HandlerAdapter,在官方的解釋中,有著更明確的回答

簡單總結(jié)一下的話,添加了<mvc:annotation-driven/>后,就會自動注冊自定義的HandlerInterceptors ,不再需要手動添加
debug一下
當(dāng)不寫<mvc:annotation-driven/>時,進(jìn)行請求,在AbstractHandlerMapping類中

容器中mappedInterceptors的個數(shù)為0
當(dāng)使用<mvc:annotation-driven/>后

容器中mappedInterceptors個數(shù)變成了2個,包含自定義的LoginInterceptor(圖片中沒顯示出來。。。). 攔截器注冊后,剩下攔截路徑的配置
最初的攔截路徑為
<mvc:mapping path="/apiweb/**"/>
這樣寫的原因是web.xml中的DispatcherServlet攔截的路徑為/apiweb/**,以為攔截器這么寫也沒問題,但實際上路徑錯誤導(dǎo)致攔截失敗,debug發(fā)現(xiàn),當(dāng)輸入的地址為http://localhost:8004/apiweb/test/a

lookupPath是/test/a,而攔截路徑卻是/apiweb/**,并不匹配,所以攔截路徑也要進(jìn)行修改,目前而言,改成/**即可
解決方案:
要修改的地方有兩處:
- 在xml配置文件中添加
<mvc:annotation-driven/> - 將攔截器的攔截路徑修改為/**
ps:如果使用注解配置的話,只需要添加一個類并繼承WebMvcConfigurationSupport類,然后重寫addInterceptors方法。如下
@Configuration
public class WebCon extends WebMvcConfigurationSupport {
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(new LoginInterceptor())
.addPathPatterns("/**");
}
}看上去比xml配置簡單很多,也不用操心<mvc:annotation-driven/>
補充:
SpringMVC 攔截器和異常處理器
一、攔截器
1、攔截器的配置
SpringMVC中的攔截器用于攔截控制器方法的執(zhí)行
SpringMVC中的攔截器需要實現(xiàn)HandlerInterceptor
SpringMVC的攔截器必須在SpringMVC的配置文件中進(jìn)行配置:
<bean class="com.gedeshidai.interceptor.FirstInterceptor"></bean>
<ref bean="firstInterceptor"></ref>
<!-- 以上兩種配置方式都是對DispatcherServlet所處理的所有的請求進(jìn)行攔截 -->
<mvc:interceptor>
<mvc:mapping path="/**"/>
<mvc:exclude-mapping path="/testRequestEntity"/>
<ref bean="firstInterceptor"></ref>
</mvc:interceptor>
<!--
以上配置方式可以通過ref或bean標(biāo)簽設(shè)置攔截器,通過mvc:mapping設(shè)置需要攔截的請求,通過mvc:exclude-mapping設(shè)置需要排除的請求,即不需要攔截的請求
-->2、攔截器的三個抽象方法
SpringMVC中的攔截器有三個抽象方法:
preHandle:控制器方法執(zhí)行之前執(zhí)行preHandle(),其boolean類型的返回值表示是否攔截或放行,返回true為放行,即調(diào)用控制器方法;返回false表示攔截,即不調(diào)用控制器方法
postHandle:控制器方法執(zhí)行之后執(zhí)行postHandle()
afterComplation:處理完視圖和模型數(shù)據(jù),渲染視圖完畢之后執(zhí)行afterComplation()
3、多個攔截器的執(zhí)行順序
a>若每個攔截器的preHandle()都返回true
此時多個攔截器的執(zhí)行順序和攔截器在SpringMVC的配置文件的配置順序有關(guān):
preHandle()會按照配置的順序執(zhí)行,而postHandle()和afterComplation()會按照配置的反序執(zhí)行
b>若某個攔截器的preHandle()返回了false
preHandle()返回false和它之前的攔截器的preHandle()都會執(zhí)行,postHandle()都不執(zhí)行,返回false的攔截器之前的攔截器的afterComplation()會執(zhí)行
二、異常處理器
1、基于配置的異常處理
SpringMVC提供了一個處理控制器方法執(zhí)行過程中所出現(xiàn)的異常的接口:HandlerExceptionResolver
HandlerExceptionResolver接口的實現(xiàn)類有:DefaultHandlerExceptionResolver和SimpleMappingExceptionResolver
SpringMVC提供了自定義的異常處理器SimpleMappingExceptionResolver,使用方式:
<bean class="org.springframework.web.servlet.handler.SimpleMappingExceptionResolver">
<property name="exceptionMappings">
<props>
<!--
properties的鍵表示處理器方法執(zhí)行過程中出現(xiàn)的異常
properties的值表示若出現(xiàn)指定異常時,設(shè)置一個新的視圖名稱,跳轉(zhuǎn)到指定頁面
-->
<prop key="java.lang.ArithmeticException">error</prop>
</props>
</property>
<!--
exceptionAttribute屬性設(shè)置一個屬性名,將出現(xiàn)的異常信息在請求域中進(jìn)行共享
-->
<property name="exceptionAttribute" value="ex"></property>
</bean>2、基于注解的異常處理
//@ControllerAdvice將當(dāng)前類標(biāo)識為異常處理的組件
@ControllerAdvice
public class ExceptionController {
//@ExceptionHandler用于設(shè)置所標(biāo)識方法處理的異常
@ExceptionHandler(ArithmeticException.class)
//ex表示當(dāng)前請求處理中出現(xiàn)的異常對象
public String handleArithmeticException(Exception ex, Model model){
model.addAttribute("ex", ex);
return "error";
}
}總結(jié)
以上就是SpringMVC之?dāng)r截器和異常處理器的相關(guān)知識點,希望對你有所幫助。
到此這篇關(guān)于SpringMVC 攔截器和異常處理器的文章就介紹到這了,更多相關(guān)SpringMVC 攔截器內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Java基于面向?qū)ο髮崿F(xiàn)一個戰(zhàn)士小游戲
這篇文章主要為大家詳細(xì)介紹了Java如何基于面向?qū)ο髮崿F(xiàn)一個戰(zhàn)士小游戲,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以動手嘗試一下2022-07-07
spring boot與redis 實現(xiàn)session共享教程
這篇文章主要介紹了spring boot與redis 實現(xiàn)session共享教程,非常不錯,具有參考借鑒價值,需要的朋友可以參考下2017-04-04
Spring ApplicationContext接口功能詳細(xì)介紹
ApplicationContext是Spring應(yīng)用程序中的中央接口,由于繼承了多個組件,使得ApplicationContext擁有了許多Spring的核心功能,如獲取bean組件,注冊監(jiān)聽事件,加載資源文件等2023-02-02
Java 單元測試之Mockito 模擬靜態(tài)方法與私有方法最佳實踐
本文將深入探討如何使用 Mockito 來模擬靜態(tài)方法和私有方法,結(jié)合大量實戰(zhàn)代碼示例,帶你突破傳統(tǒng)單元測試的邊界,寫出更徹底、更獨立、更具可讀性的測試用例,感興趣的朋友跟隨小編一起看看吧2025-09-09
Java字節(jié)流與基本數(shù)據(jù)類型的轉(zhuǎn)換實例
本篇文章主要介紹了Java字節(jié)流與基本數(shù)據(jù)類型的轉(zhuǎn)換實例,具有一定的參考價值,感興趣的小伙伴們可以參考一下2017-06-06
使用SpringBoot整合Sharding Sphere實現(xiàn)數(shù)據(jù)脫敏的示例
Apache ShardingSphere數(shù)據(jù)脫敏模塊,通過SQL攔截與改寫實現(xiàn)敏感信息加密存儲,解決手動處理繁瑣及系統(tǒng)改造難題,支持Spring和Spring Boot配置,本文通過實例代碼介紹如何使用SpringBoot整合Sharding Sphere實現(xiàn)數(shù)據(jù)脫敏,感興趣的朋友一起看看吧2025-06-06
SpringBoot打包前重新拉取maven依賴的方法實現(xiàn)
在使用 Maven 構(gòu)建 Spring Boot 項目時,如果希望在每次打包時都強(qiáng)制拉取依賴,可以通過以下方法實現(xiàn),本文給大家介紹了四種實現(xiàn)方法,并通過代碼講解的非常詳細(xì),需要的朋友可以參考下2024-12-12

