Custom enhancement methods, also known as notification methods, are Java methods annotated with @ Before, @ AfterRunning, @ AfterThrowing, @ After or @ Around annotations.
@Before
Pre enhancement (also known as pre notification): in the target methodimplementPrevious implementation
@After
Post enhancement (also known as post notification): executed after target method execution,Whether or not an exception occurred during the target method run. Be careful:Post enhancement failed to get target method execution results,Available in return enhancement
@AfterRunning
Return enhancement (also known as return notification): intargetAfter the method is executed normally, you can get theresults of enforcement
@AfterThrowing
Exception enhancement (also known as exception notification): target methodAfter throwing an exceptionExecute, you can access the exception object, and you can specify which exception occurs before the enhanced code is executed
import org.aspectj.lang.JoinPoint; import org.aspectj.lang.annotation.After; import org.aspectj.lang.annotation.AfterReturning; import org.aspectj.lang.annotation.AfterThrowing; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Before; import org.springframework.stereotype.Component; @Aspect//Declare a class as a tangent class @Component// Store class objects in containers public class CalculatorAspect { //Preamplifier @Before("execution(int div(int , int ))") public void before(JoinPoint jp) { Object target=jp.getTarget(); Object[] params = jp.getArgs(); System.out.println(target.getClass().getName()+": The mul method begins."); System.out.println(target.getClass().getName()+": Parameters of the mul method: ["+params[0]+","+params[1]+"]"); } //Return enhancement @AfterReturning(value="execution(int div(..))" ,returning="a") public void afterRrturning(JoinPoint jp,Object a) { Object object = jp.getTarget(); String name = jp.getSignature().getName(); System.out.println(object.getClass().getName()+"Result of the "+name+" method :"+a); } //Post enhancement @After("execution(int div(int , int ))") public void after(JoinPoint jp) { Object object = jp.getTarget(); String name = jp.getSignature().getName(); System.out.println(object.getClass().getName()+"the"+name+"method ends"); } //Abnormal enhancement @AfterThrowing(value="execution(int div(..))" ,throwing="ex") public void afterThrowing(JoinPoint jp, RuntimeException ex) { Object object = jp.getTarget(); String name = jp.getSignature().getName(); System.out.println(object.getClass().getName() + " the "+ name+ " have a exception : " + ex.getMessage()); } }
Be careful:
The data type of ex variable is Exception, the subclass of RuntimeException in case of ArithmeticException Exception, so the afterThrowing method can be executed in case of Exception in the target method; if the data type of ex is NullPointerException, the afterThrowing method will not be executed in case of Exception in the target method.
@Before,@After,@AfterReturning,@AfterThrowing
The call here is the div method in the proxy object. The execution process of this method is as follows: ① execute pre enhancement; ② execute the div method of the target object; ③ execute post enhancement; ④ execute return enhancement; ⑤ if the previous method is abnormal, the return enhancement will not be executed but the exception enhancement will be executed directly.
import org.springframework.context.support.ClassPathXmlApplicationContext; import com.zzu.calculator.ICalculatorService; public class Test { public static void main(String[] args) { //Create a collection (IOC container) and place the bean s in spring.xml in the container ClassPathXmlApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring.xml");// ICalculatorService calculatorService =applicationContext.getBean(ICalculatorService.class); //ICalculatorService calculatorService = new CalculatorService(); System.out.println(calculatorService.getClass().getName()); int result = calculatorService.div(6, 2); System.out.println("div---->"+result); } }
Operation result:
When an exception occurs to the called method
@Around
Surround enhancement: Enhanced processing can be woven into the target method before and after implementation
AspectJ Five types of enhanced annotations are supported, except@Before,@After,@AfterReturning and@AfterThrowing In addition, there is an enhanced annotation——@Around,stay@Around Can be realized in the modified method@Before,@After,@AfterReturning and@AfterThrowing The enhanced effect can realize the whole process of dynamic agent, and the code is as follows:
import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; import org.springframework.stereotype.Component; @Aspect//Declare a class as a tangent class @Component// Store class objects in containers public class CalculatorAspect { @Around("execution(int div(..))") public Object around(ProceedingJoinPoint jp) { Object result=null; Object object=jp.getTarget(); String name = jp.getSignature().getName(); Object[] params = jp.getArgs(); try { try { //Preamplifier System.out.println(object.getClass().getName()+": The "+name+" method begins."); System.out.println(object.getClass().getName()+": Parameters of the "+name+" method: ["+params[0]+","+params[1]+"]"); result = jp.proceed(); //Execute method in target object } finally { //Post enhancement System.out.println(object.getClass().getName()+"the"+name+"method ends"); } //Return enhancement System.out.println(object.getClass().getName()+"Result of the "+name+" method :"+result); } catch (Throwable e) { //Abnormal enhancement System.out.println(object.getClass().getName() + " the "+ name+ " have a exception : " + e.getMessage()); } return result; } }
Execute test class:
import org.springframework.context.support.ClassPathXmlApplicationContext; import com.zzu.calculator.ICalculatorService; public class Test { public static void main(String[] args) { //Create a collection (IOC container) and place the bean s in spring.xml in the container ClassPathXmlApplicationContext applicationContext = new ClassPathXmlApplicationContext("spring.xml");// ICalculatorService calculatorService =applicationContext.getBean(ICalculatorService.class); System.out.println(calculatorService.getClass().getName()); int result = calculatorService.div(6, 2); System.out.println("div---->"+result); } }
Run results:
Be careful:
1. Methods decorated with @ Before, @ After, @ AfterRunning and @ AfterThrowing can obtain the information of the target method (method name, parameter list, etc.) by declaring parameter variables of JoinPoint type; methods decorated with @ Around must declare parameters of ProceedingJoinPoint type, which can decide whether to execute the target method or not.
2. The methods decorated with @ Before, @ After, @ AfterRunning and @ AfterThrowing have no return value, while the methods decorated with @ Around must have a return value, which is the return value of the target method.