在Java開發中,對后端接口調用進行攔截處理是一種常見的需求,通常用于權限驗證、Token校驗、狀態更新等操作。本文將圍繞 Spring框架的攔截器(Interceptor)、Spring AOP(面向切面編程) 和 Spring Security 三種實現方式,結合注解的應用,詳細講解如何設計和實現接口攔截邏輯。
一、基于Spring框架的攔截器(Interceptor)
1. 攔截器簡介
攔截器(Interceptor)是Spring MVC框架提供的功能,能夠在請求到達控制器之前或之后執行特定邏輯。它適合用于全局范圍的攔截操作,例如統一的日志記錄、Token校驗、權限驗證等。
2. 實現步驟
(1)創建自定義攔截器
通過實現 HandlerInterceptor
接口,可以定義攔截器的具體邏輯。以下是代碼示例:
import org.springframework.stereotype.Component;
import org.springframework.web.servlet.HandlerInterceptor;import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;@Component
public class TokenInterceptor implements HandlerInterceptor {@Overridepublic boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {// 獲取請求頭中的TokenString token = request.getHeader("Authorization");if (token == null || token.isEmpty()) {response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);response.getWriter().write("Missing token");return false; // 阻止請求繼續執行}// 校驗Token有效性if (!validateToken(token)) {response.setStatus(HttpServletResponse.SC_FORBIDDEN);response.getWriter().write("Invalid or expired token");return false; // 阻止請求繼續執行}// 更新Token狀態updateTokenStatus(token);return true; // 放行請求}private boolean validateToken(String token) {// 簡單模擬Token校驗邏輯return token.startsWith("valid_");}private void updateTokenStatus(String token) {// 模擬更新Token狀態System.out.println("Token updated: " + token);}
}
(2)注冊攔截器
在Spring配置類中,通過實現 WebMvcConfigurer
接口,將自定義攔截器注冊到應用中,并指定攔截規則:
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;@Configuration
public class WebConfig implements WebMvcConfigurer {@Autowiredprivate TokenInterceptor tokenInterceptor;@Overridepublic void addInterceptors(InterceptorRegistry registry) {// 攔截所有路徑,但排除登錄和注冊接口registry.addInterceptor(tokenInterceptor).addPathPatterns("/**").excludePathPatterns("/login", "/register");}
}
(3)測試效果
- 當用戶訪問受保護的接口時,攔截器會先檢查Token。
- 如果Token無效或缺失,直接返回錯誤響應。
- 如果Token有效,則更新狀態并放行請求。
3. 適用場景
攔截器適合全局范圍的攔截需求,例如統一的日志記錄、Token校驗、權限驗證等。
二、基于Spring AOP的細粒度控制
1. Spring AOP簡介
Spring AOP(Aspect-Oriented Programming)是一種面向切面編程的技術,允許開發者在不修改業務代碼的情況下,動態地插入邏輯。它適合需要對某些特定方法進行攔截的場景。
2. 實現步驟
(1)定義自定義注解
創建一個注解,用于標記需要攔截的方法:
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface CheckToken {
}
(2)創建切面類
使用AOP切面,在方法執行前進行Token校驗:
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.stereotype.Component;import javax.servlet.http.HttpServletRequest;@Aspect
@Component
public class TokenAspect {private final HttpServletRequest request;public TokenAspect(HttpServletRequest request) {this.request = request;}// 定義切入點:所有被@CheckToken注解的方法@Pointcut("@annotation(CheckToken)")public void checkTokenPointcut() {}// 在方法執行前進行攔截@Before("checkTokenPointcut()")public void checkToken() {String token = request.getHeader("Authorization");if (token == null || token.isEmpty()) {throw new RuntimeException("Missing token");}if (!validateToken(token)) {throw new RuntimeException("Invalid or expired token");}updateTokenStatus(token);}private boolean validateToken(String token) {return token.startsWith("valid_");}private void updateTokenStatus(String token) {System.out.println("Token updated: " + token);}
}
(3)在控制器中使用注解
在需要攔截的方法上添加 @CheckToken
注解:
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;@RestController
public class UserController {@GetMapping("/profile")@CheckTokenpublic String getProfile() {return "User Profile";}
}
(4)測試效果
- 訪問
/profile
時,AOP會自動攔截并校驗Token。 - 如果Token無效或缺失,拋出異常,阻止方法執行。
3. 適用場景
AOP適合細粒度的控制,例如僅對某些特定方法進行攔截,靈活性高但稍顯復雜。
三、基于Spring Security的權限管理
1. Spring Security簡介
Spring Security是一個強大的安全框架,提供了全面的身份驗證和授權功能。如果項目中已經集成了Spring Security,可以通過自定義過濾器或配置來實現接口攔截。
2. 實現步驟
(1)創建自定義過濾器
繼承 OncePerRequestFilter
,并在其中實現Token校驗邏輯:
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.stereotype.Component;
import org.springframework.web.filter.OncePerRequestFilter;import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;@Component
public class JwtTokenFilter extends OncePerRequestFilter {@Overrideprotected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain filterChain)throws ServletException, IOException {String token = request.getHeader("Authorization");if (token == null || !validateToken(token)) {response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);response.getWriter().write("Invalid token");return;}updateTokenStatus(token);// 設置認證信息到SecurityContextSecurityContextHolder.getContext().setAuthentication(new CustomAuthentication(token));filterChain.doFilter(request, response);}private boolean validateToken(String token) {return token.startsWith("valid_");}private void updateTokenStatus(String token) {System.out.println("Token updated: " + token);}
}
(2)注冊過濾器
在Spring Security配置中添加自定義過濾器:
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;@Configuration
public class SecurityConfig {private final JwtTokenFilter jwtTokenFilter;public SecurityConfig(JwtTokenFilter jwtTokenFilter) {this.jwtTokenFilter = jwtTokenFilter;}@Beanpublic SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception {http.csrf().disable().authorizeRequests().antMatchers("/login", "/register").permitAll().anyRequest().authenticated().and().addFilterBefore(jwtTokenFilter, UsernamePasswordAuthenticationFilter.class);return http.build();}
}
(3)測試效果
- Spring Security會在每次請求時調用自定義過濾器。
- 如果Token無效或缺失,直接返回未授權響應。
3. 適用場景
Spring Security適合復雜的權限管理場景,集成度高,但學習成本較高。
四、總結
方案 | 特點 | 適用場景 |
---|---|---|
攔截器 | 全局攔截,簡單易用,適合統一的日志記錄、Token校驗、權限驗證等操作 | 大多數基礎攔截需求 |
AOP | 細粒度控制,靈活但稍顯復雜 | 僅對某些特定方法進行攔截 |
Spring Security | 功能強大,支持復雜的權限管理 | 復雜的安全性需求 |
根據項目需求選擇合適的方案:
- 如果只是簡單的Token校驗,推薦使用攔截器;
- 如果需要更復雜的權限管理,建議使用Spring Security;
- 如果需要細粒度的控制,可以選擇Spring AOP。
通過以上三種方式,你可以輕松實現對后端接口調用的攔截處理,從而提升系統的安全性和可維護性。