AOP註解說明:
- @Aspect 定義切面:切面由切點和增強(引介)組成(可以包含多個切點和多個增強),它既包括了橫切邏輯的定義,也包括了連接點的定義,SpringAOP就是負責實施切面的框架,它將切面所定義的橫切邏輯織入到切面所指定的鏈接點中。
- @Pointcut 定義切點:切點是一組連接點的集合。AOP通過“切點”定位特定的連接點。通過數據庫查詢的概念來理解切點和連接點的關係再適合不過了:連接點相當於數據庫中的記錄,而切點相當於查詢條件。
- @Before :在目標方法被調用之前做增強處理,@Before只需要指定切入點表達式即可。
- @AfterReturning : 在目標方法正常完成後做增強,@AfterReturning除了指定切入點表達式後,還可以指定一個返回值形參名returning,代表目標方法的返回值。
- @Afterthrowing: 主要用來處理程序中未處理的異常,@AfterThrowing除了指定切入點表達式後,還可以指定一個throwing的返回值形參名,可以通過該形參名來訪問目標方法中所拋出的異常對象。
- @After: 在目標方法完成之後做增強,無論目標方法時候成功完成。@After可以指定一個切入點表達式。
- @Around: 環繞通知,在目標方法完成前後做增強處理,環繞通知是最重要的通知類型,像事務,日誌等都是環繞通知,注意編程中核心是一個ProceedingJoinPoint。
用法:
package com.yl.spring.aop;
import java.util.Arrays;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.After;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.AfterThrowing;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.springframework.stereotype.Component;
@Component
@Aspect
public class LoggingAspect {
/**
* 在com.yl.spring.aop.ArithmeticCalculator接口的每一個實現類的每一個方法開始之前執行一段代碼
*/
@Before("execution(public int com.yl.spring.aop.ArithmeticCalculator.*(..))")
public void beforeMethod(JoinPoint joinPoint) {
// 函數名
String methodName = joinPoint.getSignature().getName();
// 獲得參數列表
Object[] args = joinPoint.getArgs();
System.out.println("The method " + methodName + " begins with " + Arrays.asList(args));
}
/**
* 在com.yl.spring.aop.ArithmeticCalculator接口的每一個實現類的每一個方法執行之後執行一段代碼
* 無論該方法是否出現異常
*/
@After("execution(public int com.yl.spring.aop.ArithmeticCalculator.*(..))")
public void afterMethod(JoinPoint joinPoint) {
String methodName = joinPoint.getSignature().getName();
Object[] args = joinPoint.getArgs();
System.out.println("The method " + methodName + " ends with " + Arrays.asList(args));
}
/**
* 方法正常結束後執行的代碼
* 返回通知是可以訪問到方法的返回值的
*/
@AfterReturning(value="execution(public int com.yl.spring.aop.ArithmeticCalculator.*(..))", returning="result")
public void afterReturning(JoinPoint joinPoint, Object result) {
String methodName = joinPoint.getSignature().getName();
System.out.println("The method " + methodName + " return with " + result);
}
/**
* 在方法出現異常時會執行的代碼
* 可以訪問到異常對象,可以指定在出現特定異常時在執行通知代碼
*/
@AfterThrowing(value="execution(public int com.yl.spring.aop.ArithmeticCalculator.*(..))", throwing="ex")
public void afterThrowing(JoinPoint joinPoint, Exception ex) {
String methodName = joinPoint.getSignature().getName();
System.out.println("The method " + methodName + " occurs exception: " + ex);
}
/**
* 環繞通知需要攜帶ProceedingJoinPoint類型的參數
* 環繞通知類似於動態代理的全過程:ProceedingJoinPoint類型的參數可以決定是否執行目標方法。
* 而且環繞通知必須有返回值,返回值即爲目標方法的返回值
*/
@Around("execution(public int com.yl.spring.aop.ArithmeticCalculator.*(..))")
public Object aroundMethod(ProceedingJoinPoint pjd) {
Object result = null;
String methodName = pjd.getSignature().getName();
//執行目標方法
try {
//前置通知
System.out.println("The method " + methodName + " begins with " + Arrays.asList(pjd.getArgs()));
result = pjd.proceed();
//返回通知
System.out.println("The method " + methodName + " ends with " + Arrays.asList(pjd.getArgs()));
} catch (Throwable e) {
//異常通知
System.out.println("The method " + methodName + " occurs expection : " + e);
throw new RuntimeException(e);
}
//後置通知
System.out.println("The method " + methodName + " ends");
return result;
}
}
總結:
Spring AOP 5中增強當時對比
增強方式 |
註解 |
返回值 |
切點 |
參數 |
---|
前置 |
@Before |
void |
@Before("execution(限定修飾詞 返回類型 com.yl.spring.aop.ArithmeticCalculator.*(..))") |
JoinPoint joinPoint |
---|
後置 |
@After |
void |
@After("execution(限定修飾詞 返回類型 com.yl.spring.aop.ArithmeticCalculator.*(..))") |
JoinPoint joinPoint |
---|
環繞 |
@Around |
Object |
@Around("execution(限定修飾詞 返回類型 com.yl.spring.aop.ArithmeticCalculator.*(..))") |
ProceedingJoinPoint pjd |
---|
異常增強 |
@AfterThrowing |
void |
@AfterThrowing("execution(限定修飾詞 返回類型 com.yl.spring.aop.ArithmeticCalculator.*(..))",throwing="ex") |
JoinPoint joinPoint, Exception ex |
---|
返回增強 |
@AfterReturning |
void |
@AfterReturning("execution(限定修飾詞 返回類型 com.yl.spring.aop.ArithmeticCalculator.*(..))",result="result") |
|
JoinPoint joinPoint, Object result |
---|