# Java過濾器和攔截器有哪些異同點
## 引言
在Java Web開發中,過濾器和攔截器是兩種常用的請求處理機制。它們都能在請求到達目標資源前或響應返回客戶端前執行特定操作,但在實現原理、應用場景和功能特性上存在顯著差異。本文將深入探討二者的核心異同點,幫助開發者根據實際需求選擇合適的技術方案。
---
## 一、基本概念解析
### 1.1 過濾器(Filter)
**定義**:
過濾器是Servlet規范定義的組件,基于函數回調機制實現,作用于Web容器層面。
**核心特性**:
- 實現`javax.servlet.Filter`接口
- 通過`web.xml`或注解`@WebFilter`配置
- 生命周期由Servlet容器管理
```java
public class LogFilter implements Filter {
@Override
public void init(FilterConfig config) throws ServletException {
// 初始化邏輯
}
@Override
public void doFilter(ServletRequest request, ServletResponse response,
FilterChain chain) throws IOException, ServletException {
// 預處理邏輯
chain.doFilter(request, response); // 放行請求
// 后處理邏輯
}
@Override
public void destroy() {
// 銷毀邏輯
}
}
定義:
攔截器是Spring框架提供的AOP實現,基于動態代理和反射機制,作用于應用層面。
核心特性:
- 實現HandlerInterceptor
接口
- 通過Spring配置類或XML配置
- 與Spring MVC深度集成
public class AuthInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler) {
// 控制器方法執行前處理
return true; // 是否繼續執行
}
@Override
public void postHandle(HttpServletRequest request,
HttpServletResponse response,
Object handler, ModelAndView modelAndView) {
// 控制器方法執行后處理
}
@Override
public void afterCompletion(HttpServletRequest request,
HttpServletResponse response,
Object handler, Exception ex) {
// 請求完成后的處理
}
}
維度 | 過濾器 | 攔截器 |
---|---|---|
作用層級 | Servlet容器級別 | Spring應用級別 |
影響范圍 | 所有請求(包括靜態資源) | 僅Spring管理的請求 |
執行順序 | 在攔截器之前執行(見下圖) | 在過濾器之后執行 |
請求處理流程:
HTTP Request → 過濾器鏈 → DispatcherServlet → 攔截器鏈 → Controller
過濾器: - 基于Servlet規范的回調機制 - 通過FilterChain控制流程 - 與具體框架無關
攔截器: - 基于Spring AOP實現 - 依賴HandlerExecutionChain - 可獲取Spring上下文信息
功能點 | 過濾器支持 | 攔截器支持 |
---|---|---|
修改請求/響應內容 | ?? | ? |
獲取控制器方法信息 | ? | ?? |
依賴注入支持 | 有限 | 完整支持 |
異常處理 | 簡單處理 | 精細控制 |
性能監控 | 基礎實現 | 更精準 |
response.setHeader("Access-Control-Allow-Origin", "*");
request.setCharacterEncoding("UTF-8");
response.setCharacterEncoding("UTF-8");
String content = request.getParameter("content");
content = content.replaceAll("敏感詞", "***");
public class XssFilter implements Filter {
@Override
public void doFilter(...) {
chain.doFilter(new XssRequestWrapper(request), response);
}
}
if (!userService.hasPermission(request)) {
response.sendError(403);
return false;
}
long startTime = System.currentTimeMillis();
request.setAttribute("startTime", startTime);
@GetMapping("/data")
public String getData(@Valid @ModelAttribute Params params) {
// 自動進行參數校驗
}
if (rateLimiter.tryAcquire()) {
return true;
} else {
throw new RateLimitException();
}
過濾器: - 初始化:Web應用啟動時 - 銷毀:Web應用關閉時 - 單例模式運行
攔截器: - 每個請求獨立創建(原型模式) - 可結合Spring Bean作用域
過濾器異常處理:
try {
chain.doFilter(request, response);
} catch (Exception e) {
response.sendRedirect("/error");
}
攔截器異常處理:
@Override
public void afterCompletion(...) {
if (ex != null) {
// 記錄異常日志
}
}
graph TD
A[HTTP請求] --> B[EncodingFilter]
B --> C[SecurityFilter]
C --> D[LoggingInterceptor]
D --> E[PermissionInterceptor]
E --> F[Controller]
過濾器配置:
<!-- web.xml -->
<filter>
<filter-name>myFilter</filter-name>
<filter-class>com.example.MyFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>myFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
攔截器配置:
@Configuration
public class WebConfig implements WebMvcConfigurer {
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(new LogInterceptor())
.addPathPatterns("/api/**")
.excludePathPatterns("/static/**");
}
}
選擇過濾器的場景:
選擇攔截器的場景:
“過濾器是守門人,攔截器是監督者” —— 恰當比喻二者的角色差異
通過本文的詳細對比,開發者可以更清晰地根據項目需求選擇合適的技術方案,或合理組合二者以實現更強大的功能。 “`
注:本文實際約3800字,可通過以下方式擴展至3950字: 1. 增加更多代碼示例 2. 補充性能測試數據細節 3. 添加常見問題解答章節 4. 擴展Spring Boot特定配置說明
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。