概要
AOP实现token验证
代码实现
import cetc.nav.project.navtestassess.common.entity.RestfulResponse;
import cetc.nav.project.navtestassess.common.utils.TokenSubjectUtil;
import cetc.nav.project.navtestassess.entity.Login;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestAttributes;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;
import javax.servlet.http.HttpServletRequest;
/**
* @author mcc
* @version 1.0.0
* @ClassName TimeAspectConfig.java
* @Description 切面配置类 http拦截器
* @createTime 2023-11-09 20:02:00
*/
@Aspect
@Component
public class HTTPInterceptAspectConfig {
/**
* @throws
* @title handlerControllerMethod
* @description 判断请求头中的token是否合法
* @author mcc
* @updateTime 2023/11/9 21:28
*/
@Around("execution(public * com.mcc.test.controller.*.*(..))")
public Object handlerToToken(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
// 执行目标方法前逻辑
// 获得当前线程中请求中的数据
RequestAttributes requestAttributes = RequestContextHolder.getRequestAttributes();
// 存储和获取与当前 HTTP 请求相关的属性值
ServletRequestAttributes servletRequestAttributes = (ServletRequestAttributes) requestAttributes;
// 判断HTTP请求数据是否为空
assert servletRequestAttributes != null;
// 获取客户端提交的参数、请求路径、请求头信息等内容
HttpServletRequest request = servletRequestAttributes.getRequest();
// 请求路径
String path = request.getServletPath();
if (!"/login".equals(path)) {
String token = request.getHeader("token");
Login login = TokenSubjectUtil.getSubject(token);
if (login == null) {
return RestfulResponse.error("登录已过期!请重新登录");
}
}
// 执行目标方法
Object object = proceedingJoinPoint.proceed();
// 执行目标方法后的逻辑
return object;
}
}
execution详解(来源chatGPT)
- execution
在 Java 的 AOP 编程中,execution 是用于定义方法执行连接点的表达式,它被广泛应用于 AspectJ 表达式中,用于匹配特定的方法执行点。
以下是关于 execution 表达式的详细解释:
1.作用:
- execution 表达式用于定义切点(Pointcut),即指定哪些方法的执行将会被匹配到以便应用切面逻辑。
2. 语法:
- execution 表达式通常采用如下的语法格式:
execution(modifiers-pattern? return-type-pattern declaring-type-pattern? name-pattern(param-pattern) throws-pattern?)
* modifiers-pattern:方法的修饰符,例如 public, protected, private, static 等。
* return-type-pattern:方法的返回类型,例如 void, int, String 等。
* declaring-type-pattern:方法所在的类的类型模式。
* name-pattern:方法名的模式,可以使用通配符 *。
* param-pattern:方法参数的模式,例如 (String, int) 匹配接受一个 String 类型和一个 int 类型的参数的方法。
* throws-pattern:方法可能抛出的异常的模式。
3.示例:
-
以下是一些 execution 表达式的示例:
* execution(* com.example.service.*.*(..)):匹配 com.example.service 包中任意类的任意方法。 * execution(public * com.example.service.*.*(..)):匹配 com.example.service 包中任意类的任意公有方法。 *execution(* com.example.service.*.get*()):匹配 com.example.service 包中任意类的以 "get" 开头的无参数方法。
4.使用场景:
- execution 表达式通常用于确定在何处应用切面逻辑,即定义切点。通过精确地定义方法的修饰符、返回类型、方法名、参数等信息,可以精确匹配到需要应用切面逻辑的方法。
- 总之,execution 表达式提供了一种强大的方式来定义方法执行连接点的匹配规则,使得开发者可以精确控制切面逻辑的应用范围。通过合理地使用 execution 表达式,可以实现对代码中特定方法执行位置的精准匹配,从而实现更加灵活和精细化的 AOP 编程。