Learn AOP of Spring together

Summary

In the software development, we focus on business logic code, but in the actual development, the code that needs to be written is not only business logic, but also need to deal with logging, exception handling, transaction control and other things unrelated to business. And these codes are also necessary for the server. Codes like this are scattered in all parts of the system. For example, almost all important operation methods will be preceded by logging codes. Such codes are tedious to write, occupy development time and energy, and are not easy to maintain. We call this kind of code as [tangent code] in a unified way. We need to use Spring's AOP technology to get away from these tedious work and focus more on business logic.

AOP principle: decompose complex requirements into different aspects, and solve the common functions scattered in the system in a centralized way, as shown in the following figure:

Classification of advice

The classification is as follows:

  • Pre notification: notification executed before a pointcut
  • Post notification: notification executed after a pointcut
  • Exception notification: notification when an exception occurs at a pointcut
  • Surround notification: the most powerful notification that surrounds an entry point

Preparation

jar package required by AOP

In addition to the five necessary jar packages of Spring, the following three are needed to support AOP:

  • aopalliance-1.0.jar
  • aspectjweaver-1.5.3.jar
  • spring-aop-4.0.6.RELEASE.jar

Define an interface and implementation class

As follows:

The IStudentService interface code is as follows:

 1 package com.hex.second;
 2 
 3 /**
 4  * Student service interface
 5  * @author Administrator
 6  *
 7  */
 8 public interface IStudentService {
 9     
10     /**
11      * New student
12      * @param student
13      */
14     void addStudent(Student student);
15     /**
16      * Delete students
17      * @param id
18      */
19     void deleteStudent(int id);
20     
21     /**
22      * Revision of students
23      * @param id
24      */
25     void updateStudent(int id);
26 }

The StudentServiceImpl class code is as follows:

 1 package com.hex.second;
 2 
 3 /**
 4  * Student services
 5  * @author Administrator
 6  *
 7  */
 8 public class StudentServiceImpl implements IStudentService {
 9 
10     /**
11      * New student
12      */
13     public void addStudent(Student student) {
14         // TODO Auto-generated method stub
15         System.out.println("New students...");
16     }
17     
18     /**
19      * Delete students
20      */
21     @Override
22     public void deleteStudent(int id) {
23         // TODO Auto-generated method stub
24         System.out.println("Delete students...");
25     }
26 
27     /**
28      * Revision of students
29      */
30     public void updateStudent(int id) {
31         // TODO Auto-generated method stub
32         System.out.println("Revision of students");
33         int i=1/0;
34     }
35 }

Before advice

1. Implementation interface

The pre notification class needs to implement the before method in the [MethodBeforeAdvice] interface, as shown below:

Method method represents the target method of execution

Object[] args indicates the parameter array passed in

Object target represents the target object, that is, the object indicated by the pointcut

 1 package com.hex.second;
 2 
 3 import java.lang.reflect.Method;
 4 
 5 import org.springframework.aop.MethodBeforeAdvice;
 6 
 7 public class LogBefore implements MethodBeforeAdvice {
 8 
 9     /***
10      * Before advice
11      * method:Represents the method called, that is, the pointcut
12      * args:Parameter representing the calling method
13      * target: Represents the target object of the method
14      */
15     @Override
16     public void before(Method method, Object[] args, Object target) throws Throwable {
17         // TODO Auto-generated method stub
18         System.out.println("Advance notice");
19         System.out.println("method="+method+",args Number="+args.length+",target="+target);
20     }
21 }

2. Configure applicationContext.xml file

If you want to support AOP, you need to introduce a namespace as follows:

1 <?xml version="1.0" encoding="UTF-8"?>
2 <beans xmlns="http://www.springframework.org/schema/beans"
3 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
4 xmlns:p="http://www.springframework.org/schema/p"
5 xmlns:aop="http://www.springframework.org/schema/aop"
6 xsi:schemaLocation="http://www.springframework.org/schema/beans
7  http://www.springframework.org/schema/beans/spring-beans.xsd
8  http://www.springframework.org/schema/aop
9  http://www.springframework.org/schema/aop/spring-aop.xsd">

3. Configure bean s corresponding to two classes

1 <!-- Service class -->
2 <bean id="studentService" class="com.hex.second.StudentServiceImpl"></bean>
3 <!-- Pre notice class -->
4 <bean id="logBefore" class="com.hex.second.LogBefore"></bean>

4. configure AOP

Through the AOP configuration, associate the notification class with the business logic class as follows:

A configuration file can have multiple < aop:config > configurations. Each aop:config can only have one aop:pointcut configuration. If there are multiple pointcuts, expression must be configured, and the pointcut must be full path configuration. As follows:

<! -- associate addStudent with notification -- >
<aop:config>
     <! -- each config has only one poingcut. If there are more than one, you need to configure more than one config -- >
     <! -- configure pointcut id customization, and expression represents the function name of pointcut -- >
     <aop:pointcut expression="execution(public void com.hex.second.StudentServiceImpl.addStudent(com.hex.second.Student))" id="pc"/>
     <! -- configure notifications -- >
     <aop:advisor advice-ref="logBefore" pointcut-ref="pc"/>
</aop:config>

Post notification

1. Implementation interface

You need to implement the following in the AfterReturningAdvice interface afterreturningmethod:

 1 package com.hex.second;
 2 
 3 import java.lang.reflect.Method;
 4 
 5 import org.springframework.aop.AfterReturningAdvice;
 6 
 7 /**
 8  * Change common classes into post notifications by implementing interfaces
 9  * @author Administrator
10  *
11  */
12 public class LogAfter implements AfterReturningAdvice {
13 
14     /**
15      * Post notification implementation class
16      * returnValue: Return value
17      * method:Represents the method called, that is, the pointcut
18      * args:Parameter representing the calling method
19      * target: Represents the target object of the method
20      */
21     @Override
22     public void afterReturning(Object returnValue, Method method, Object[] args, Object target) throws Throwable {
23         // TODO Auto-generated method stub
24         System.out.println("Post notice");
25         System.out.println("returnValue="+returnValue+",method="+method+",args Number="+args.length+",target="+target);
26     }
27 
28 }

2. Configure the Bean for pointcuts and notifications

1 <bean id="studentService" class="com.hex.second.StudentServiceImpl"></bean>
2 <bean id="logAfter" class="com.hex.second.LogAfter"></bean>

3. AOP configuration

If pre notification and post notification are the same entry point, they can be configured in an aop:config node as follows:

Multiple pointcuts are connected by or, and multiple AOP: advisors are configured for multiple notifications.

 1 <! -- associate addStudent with notification -- >
 2 <aop:config>
 3 <! -- each config has only one poingcut. If there are more than one config, you need to configure more than one config -- >
 4 <! -- configure pointcut id customization, and expression represents the function name of pointcut -- >
 5      <aop:pointcut expression="execution(public void com.hex.second.StudentServiceImpl.deleteStudent(int)) or execution(public void com.hex.second.StudentServiceImpl.addStudent(com.hex.second.Student))" id="pc"/>
 6 <! -- configuration notification -- >
 7      <aop:advisor advice-ref="logBefore" pointcut-ref="pc"/>
 8          
 9      <aop:advisor advice-ref="logAfter" pointcut-ref="pc"/>
10 </aop:config>

Exception notification

1. Implementation interface

Exception notification is a notification that will be triggered only when an exception occurs. The [ThrowsAdvice] interface needs to be implemented, and there is no way to implement this interface, but the agreement is given at the same time:

Methods must be implemented in a fixed format: public void afterThrowing([Method, args, target], ThrowableSubclass);

 1 package com.hex.second;
 2 
 3 import java.lang.reflect.Method;
 4 
 5 import org.springframework.aop.ThrowsAdvice;
 6 
 7 /**
 8  * Exception notification
 9  * @author Administrator
10  *
11  */
12 public class LogException implements ThrowsAdvice {
13     
14     /**
15      * Exception notification execution
16      * @param method breakthrough point
17      * @param args Number of parameters
18      * @param target Call target object
19      * @param ex abnormal
20      */
21     public void afterThrowing(Method method, Object[] args, Object target, Exception ex){
22         System.out.println("Exception notification...");
23         System.out.println("method="+method+",args Number="+args.length+",target="+target+",ex="+ex);
24     }
25 }

2. Configure Bean class

1 <!-- Service class -->
2 <bean id="studentService" class="com.hex.second.StudentServiceImpl"></bean>
3 <bean id="logException" class="com.hex.second.LogException"></bean>

3. configure AOP

As shown below: parameters only need to write parameter type, not parameter name.

1 <!-- Configurable aop:config -->
2 <aop:config>
3         <aop:pointcut expression="execution(public void com.hex.second.StudentServiceImpl.updateStudent(int))" id="pc1"/>
4      <!-- Configuration notice -->
5      <aop:advisor advice-ref="logException" pointcut-ref="pc1"/>
6 </aop:config>

Around Advice

1. Implementation interface

Around the notification, you need to implement the [MethodInterceptor] interface and the [invoke] method, where obj = invocation. Processed(); means to call the target method. If you do not write this sentence, the target method will not be called. As follows:

 1 package com.hex.second;
 2 
 3 import org.aopalliance.intercept.MethodInterceptor;
 4 import org.aopalliance.intercept.MethodInvocation;
 5 
 6 /**
 7  * Around Advice
 8  * Circular notification is essentially an interceptor
 9  * @author Administrator
10  *
11  */
12 public class LogAround implements MethodInterceptor {
13 
14     /**
15      * 
16      */
17     @Override
18     public Object invoke(MethodInvocation invocation) throws Throwable {
19         Object obj = null;
20         try {
21 
22             // Before advice
23             System.out.println("Surround implementation pre notification...");
24             System.out.println("Surround notification: target="+invocation.getThis()+",method="+invocation.getMethod().getName()+",args="+invocation.getArguments().length);
25             // Implementation of control objective method obj Represents the return value of the target method, and represents execution addStudent(student)Method
26             //This method controls the execution of the target method. If this method is not written, the target method will not execute. The method is preceded by a pre notification and followed by a post notification.
27             obj = invocation.proceed();
28             // Post notification
29             System.out.println("Surround implementation post notification...");
30         } catch (Exception e) {
31             // Exception notification
32             System.out.println("Surround implementation exception notification...");
33             throw e;
34         }
35         // TODO Auto-generated method stub
36         return obj;
37     }
38 
39 }

2. Configure Bean

1 <!-- Service class -->
2 <bean id="studentService" class="com.hex.second.StudentServiceImpl"></bean>
3 <bean id="logAround" class="com.hex.second.LogAround"</bean>

3. configure AOP

All configuration pointcut notifications are the same. As follows:

1 <aop:config>
2      <aop:pointcut expression="execution(public void com.hex.second.StudentServiceImpl.addStudent(com.hex.second.Student))" id="pc2"/>
3      <aop:advisor advice-ref="logAround" pointcut-ref="pc2"/>
4 </aop:config>

All the calling methods are consistent. There is no need to call the notification class, and the system will call automatically, as shown below:

 1 package com.hex.second;
 2 
 3 import org.springframework.context.ApplicationContext;
 4 import org.springframework.context.support.ClassPathXmlApplicationContext;
 5 
 6 public class TestMain {
 7 
 8     public static void main(String[] args) {
 9         // TODO Auto-generated method stub
10         //adopt Spring Injection, Spring Context object
11         ApplicationContext context=new ClassPathXmlApplicationContext("applicationContext.xml");
12         IStudentService studentService=(IStudentService)context.getBean("studentService");
13         Student student =new Student();
14         studentService.addStudent(student);
15         //studentService.deleteStudent(1);
16         //studentService.updateStudent(0);
17     }
18 
19 }

 

Remarks

The wood that holds together is born in the first place; the platform with nine layers starts from the accumulated soil; the journey of a thousand miles starts from a single step.

Keywords: Java Spring xml encoding

Added by vipes on Sun, 20 Oct 2019 18:13:02 +0300