1. 概念介绍
在 Spring AOP(面向切面编程)中,JoinPoint是一个非常重要的概念。它表示程序执行过程中的一个点,这个点可以是方法的调用、方法的执行、构造函数的调用等。简单来说,它是切面(Aspect)能够切入的地方。通过JoinPoint,可以获取到关于目标方法(被切面拦截的方法)的很多信息,如方法签名、方法参数、目标对象等。
2. 获取JoinPoint对象
在切面的通知(Advice)方法中,可以将JoinPoint作为参数传入,从而获取相关信息。例如,在前置通知(Before Advice)中:
import org. aspectj. lang. JoinPoint ;
import org. aspectj. lang. annotation. Aspect ;
import org. aspectj. lang. annotation. Before ;
import org. aspectj. lang. annotation. Pointcut ;
import org. springframework. stereotype. Component ; @Aspect
@Component
public class LoggingAspect { @Pointcut ( "execution(* com.example.demo.service..*.*(..))" ) public void serviceMethods ( ) { } @Before ( "serviceMethods()" ) public void logBeforeServiceMethod ( JoinPoint joinPoint) { System . out. println ( "即将执行方法: " + joinPoint. getSignature ( ) . getName ( ) ) ; Object [ ] args = joinPoint. getArgs ( ) ; for ( Object arg : args) { System . out. println ( "方法参数: " + arg) ; } }
}
在这个例子中,logBeforeServiceMethod方法接收一个JoinPoint对象作为参数。通过joinPoint.getSignature().getName()可以获取目标方法的名称,通过joinPoint.getArgs()可以获取目标方法的参数数组。
3.JoinPoint的主要信息获取方法
获取方法签名(Signature) 方法签名包含了方法的名称、返回值类型、参数类型等信息。可以通过joinPoint.getSignature()获取方法签名对象,然后使用该对象的方法来获取具体信息。例如:
Signature signature = joinPoint. getSignature ( ) ;
String methodName = signature. getName ( ) ;
Class < ? > returnType = signature. getReturnType ( ) ;
Class < ? > [ ] parameterTypes = signature. getParameterTypes ( ) ;
这个方法在需要访问目标对象的状态或者其他属性时很有用,比如在事务管理切面中,可能需要检查目标对象的事务状态。 获取代理对象(Proxy Object) 有时候可能需要获取代理对象,可以通过joinPoint.getThis()方法来实现。在 AOP 中,代理对象是实际调用目标方法的对象。例如:
Object proxy = joinPoint. getThis ( ) ;
4.在不同通知类型中的使用
前置通知(Before) :如前面的例子所示,可以在前置通知中使用JoinPoint来获取目标方法的信息,如方法名称、参数等,用于记录日志、进行参数验证等操作。后置通知(After) :同样可以获取JoinPoint信息,用于记录目标方法执行后的状态。例如:
import org. aspectj. lang. JoinPoint ;
import org. aspectj. lang. annotation. After ;
import org. aspectj. lang. annotation. Aspect ;
import org. aspectj. lang. annotation. Pointcut ;
import org. springframework. stereotype. Component ; @Aspect
@Component
public class LoggingAspect { @Pointcut ( "execution(* com.example.demo.service..*.*(..))" ) public void serviceMethods ( ) { } @After ( "serviceMethods()" ) public void logAfterServiceMethod ( JoinPoint joinPoint) { System . out. println ( "方法 " + joinPoint. getSignature ( ) . getName ( ) + " 已执行" ) ; }
}
返回通知(AfterReturning)和异常通知(AfterThrowing) :在返回通知和异常通知中,JoinPoint也可以和其他返回值或者异常对象一起使用,来更全面地记录方法执行的情况。例如,在返回通知中:
import org. aspectj. lang. JoinPoint ;
import org. aspectj. lang. annotation. AfterReturning ;
import org. aspectj. lang. annotation. Aspect ;
import org. aspectj. lang. annotation. Pointcut ;
import org. springframework. stereotype. Component ; @Aspect
@Component
public class LoggingAspect { @Pointcut ( "execution(* com.example.demo.service..*.*(..))" ) public void serviceMethods ( ) { } @AfterReturning ( pointcut = "serviceMethods()" , returning = "result" ) public void logAfterReturningServiceMethod ( JoinPoint joinPoint, Object result) { System . out. println ( "方法 " + joinPoint. getSignature ( ) . getName ( ) + " 返回结果: " + result) ; }
}