JoinPoint可以让我们获取到哪些信息
JoinPoint
接口提供了多个方法,允许我们在切面中获取与连接点(即目标方法执行点)相关的信息。以下是一些常用的方法,以及它们能够提供的信息:
getArgs()
: 获取目标方法的参数列表。这些参数是在方法调用时传递给方法的实际参数。getSignature()
: 获取方法的签名(Signature
对象)。通过这个对象,你可以获取方法的名字、返回类型、方法所在的类等信息。getTarget()
: 获取目标对象,即被代理的对象。getThis()
: 获取AOP代理对象,即代理目标对象的代理对象。toString()
: 返回连接点的字符串表示形式,通常包含了方法的全名和其他相关信息。toShortString()
: 返回连接点的简短字符串表示形式,通常只包含方法名。getSourceLocation()
: 获取连接点对应的方法在源代码中的位置,如行号。getKind()
: 获取连接点的类型,例如方法执行(method-execution
)或方法调用(method-call
)。getStaticPart()
: 获取连接点的静态部分,即与特定连接点关联的代码本身的描述。
通过这些方法,你可以在切面中访问到目标方法的详细信息,从而可以根据这些信息执行不同的逻辑,如日志记录、权限校验等。
下面是一个使用JoinPoint
的示例,展示了如何在切面中获取连接点信息:
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.springframework.stereotype.Component;
@Aspect
@Component
public class InfoAspect {
@Before("execution(* com.example.service.*.*(..))")
public void beforeMethod(JoinPoint joinPoint) {
// 获取方法签名
String methodName = joinPoint.getSignature().toShortString();
System.out.println("方法名: " + methodName);
// 获取目标对象
Object target = joinPoint.getTarget();
System.out.println("目标对象: " + target.getClass().getSimpleName());
// 获取方法参数
Object[] args = joinPoint.getArgs();
System.out.println("方法参数: " + Arrays.toString(args));
// 获取代理对象
Object thisObject = joinPoint.getThis();
System.out.println("代理对象: " + thisObject.getClass().getSimpleName());
// 获取连接点类型
String kind = joinPoint.getKind();
System.out.println("连接点类型: " + kind);
// 获取源代码位置(如果可用)
SourceLocation sourceLocation = joinPoint.getSourceLocation();
System.out.println("源代码位置: " + sourceLocation);
// 输出连接点的详细信息
System.out.println("连接点详细信息: " + joinPoint.toString());
}
}
在这个示例中,我们定义了一个切面InfoAspect
,它有一个@Before
通知,该通知会在执行com.example.service
包下所有方法之前触发。在beforeMethod
方法中,我们通过JoinPoint
参数获取了方法名、目标对象、方法参数、代理对象、连接点类型和源代码位置等信息,并将它们打印出来。
当这个切面的通知被触发时,你会在控制台看到类似以下的信息输出:
方法名: UserService.save(..)
目标对象: UserService
方法参数: [Ljava.lang.Object;@12345678
代理对象: UserService$$EnhancerBySpringCGLIB$$12345678
连接点类型: method-execution
源代码位置: SourceLocation[...]
连接点详细信息: execution(UserService.save(User))
JoinPoint和ProceedingJoinPoint的区别
JoinPoint
:
JoinPoint
接口代表了程序运行过程中的一个特定点,例如方法的执行。在AOP术语中,这个点被称为“连接点”。JoinPoint
提供了获取代理方法的相关信息的方法,例如方法名称、参数、目标对象等。JoinPoint
通常用于@Before、@After和@AfterReturning等通知中,因为这些通知并不需要控制目标方法的执行。
ProceedingJoinPoint
:ProceedingJoinPoint
是JoinPoint
的子接口,专门用于环绕通知(@Around)。ProceedingJoinPoint
除了拥有JoinPoint
的所有功能外,还提供了一个proceed()
方法,这个方法用于控制目标方法的执行。调用proceed()
方法,会触发目标方法的执行。proceed()
方法可以传入参数,这些参数将会传递给目标方法。这使得环绕通知可以在目标方法执行前后执行自己的逻辑,并且可以修改传入目标方法的参数和返回值。