This article is published at the same time in personal technology blog [Bird does not poop]. For details, you can also scan the qr code at the end of the article to pay attention to personal public number [Bird does not poop].

One, foreword

As we all know, spring’s two core features are AOP and IOC, namely aspect orientation and inversion of control. This article looks at how SpringBoot implements section-oriented process principles using AOP.

What is AOP

Aop full name Aspect Oriented Programming, Oriented to the Aspect, AOP is mainly implemented for the purpose of business processing process in the Aspect of extraction, it is facing a certain step or stage in the process of processing, in order to obtain the isolation effect of low coupling between each part of the logical process. It accomplishes much the same task as design patterns, providing another way to think about the structure of programs to compensate for the shortcomings of object-oriented programming.

In layman’s terms, it provides a mechanism for providing aspect injection for a business implementation, by which defined aspects are bound to the business through pointcuts during the business run to enable specific logic to be bound to that business.

For example, if a project has a requirement to log an operation, or a process change is a record of changes, it is nothing more than a table operation, a simple save operation, is some logging or other auxiliary code. Rewrite and call over and over again. Not only is it a waste of time, but it also makes the project more redundant.

That’s where faceted AOP comes in.

Aop related terms

To understand SpringBoot’s implementation of aop integration, you must first understand some of the names of aop for faceted implementations, or else it is in the wind.

  • Aspect: Modularization of a concern. An annotation @aspect is placed above the class to declare an Aspect.

  • Joinpoint: a specific point in the execution of a program, such as when a method is called or when an exception is handled.

  • Advice: Advice enhancements. The work that needs to be done is called Advice. This is when you write business logic that needs to be defined, such as transactions, logs, etc., and then use it where necessary.

    It mainly includes 5 annotations: Before, After, AfterReturning, AfterThrowing and Around.

    @before: Executed Before the pointcut method.

    @after: Executes After the pointcut method

    AfterReturning: execute after the pointcut method returns

    AfterThrowing: Pointcut method throws exception execution

    @around: this is a surround enhancement that controls before and after pointcuts are executed, and after the annotation is used, the application throws an exception that affects @afterthrowing

  • Pointcuts: Filter join points, assertions that match join points. All methods in a class are join points, but not all of them are needed. If the advice defines the action or timing of the cut, the cut point defines the place of execution. How pointcut expressions match join points is at the heart of AOP: Spring uses AspectJ pointcut syntax by default.

  • Introduction: Adding attributes and methods to an existing class without changing the code of the class gives them new behavior and states without modifying existing classes. This is to apply the aspect (defined by the new method property: notification) to the target class.

  • Target Object: An Object notified by one or more facets. Also known as adviced objects. Since Spring AOP is implemented through a runtime proxy, this object is always a proxied object.

  • AOP Proxy: An object created by an AOP framework to implement aspect contracts (such as notifying method execution, and so on). In Spring, an AOP proxy can be either a JDK dynamic proxy or a CGLIB proxy.

  • Weaving: Connects slices to other application types or objects and creates a notified object. This can be done at compile time (using the AspectJ compiler, for example), class load time, and run time. Spring, like other pure Java AOP frameworks, does weaving at run time.

Aspect, Pointcut, Pointcut

Four, code implementation

Taking service logic logs as an example, section-oriented log processing is added.

1. Add maven dependencies

<! Introducing AOP dependencies -->
<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-starter-aop</artifactId>
	<version>2.1.6. RELEASE</version>
</dependency>
Copy the code

2. Add system log annotations

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface SysLog {
    String value(a) default "";
}
Copy the code

3. Add the system log entity class

@Data
public class SysLogEntity {
    private String className;
    private String methodName;
    private String params;
    private Long exeuTime;
    private String remark;
    private String createDate;
}
Copy the code

4. Add the Service logical processing layer

@Slf4j
@Service
public class SysLogService {
    public boolean save(SysLogEntity sysLogEntity){
        // We will not do the implementation here
        log.info(sysLogEntity.getParams());
        return true; }}Copy the code

The @slf4J logging annotation is used here

Private final Logger Logger = LoggerFactory.getLogger(xxx.class);

Simplified code, how to simplify how to ~

Here is mainly to study how to achieve aop, will not specifically write Service layer code.

5. The Controller layer

@RestController
@RequestMapping("/aop")
public class AopController {
    @SysLog("Test")
    @GetMapping("/test")
    public String test(@RequestParam("name") String name, @RequestParam("age") int age){
        return name + ","+ age; }}Copy the code

6. Section treatment

Here we go, here we go, key processing, guest officer below the code

First declare it above the class

@Aspect / / using the @ Aspect
@Component
Copy the code

Calling a Service

@Autowired
private SysLogService sysLogService;
Copy the code

Add the Pointcut expression @pointcut

/** * We can specify the package to intercept, the class to intercept, and the method to intercept directly through the pointcut expression: execution(...). * /
@Pointcut("@annotation(com.niaobulashi.anno.SysLog)")
public void logPointCut(a) {}
Copy the code

Add a surround notification @around

@Around("logPointCut()")
    public Object around(ProceedingJoinPoint point) throws Throwable {
        long beginTime = System.currentTimeMillis();
        Object result = point.proceed();
        long time = System.currentTimeMillis() - beginTime;
        try {
            // Implement log logic
            saveLog(point, time);
        } catch (Exception e) {
        	
        }
        return result;
    }
Copy the code

Implement saveLog logic saveLog

private void saveLog(ProceedingJoinPoint joinPoint, long time) {

	// Get method key information, class, package
	MethodSignature signature = (MethodSignature) joinPoint.getSignature();
	Method method = signature.getMethod();
	SysLogEntity sysLogEntity = new SysLogEntity();
	sysLogEntity.setExeuTime(time);
	SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
	sysLogEntity.setCreateDate(dateFormat.format(new Date()));
	SysLog sysLog = method.getAnnotation(SysLog.class);
	if(sysLog ! =null) {
		// The description in the annotation
		sysLogEntity.setRemark(sysLog.value());
	}
	// Request class name, method name
	String className = joinPoint.getTarget().getClass().getName();
	String methodName = signature.getName();
	sysLogEntity.setClassName(className);
	sysLogEntity.setMethodName(methodName);
	// Request parameters
	Object[] args = joinPoint.getArgs();
	try {
		List<String> list = new ArrayList<String>();
		for (Object o : args) {
			list.add(o.toString());
		}
		sysLogEntity.setParams(list.toString());
	} catch (Exception e){

	}
	sysLogService.save(sysLogEntity);
}
Copy the code

MethodSignature mainly implements return value classes, method names, and formal parameters

Five, the test

By sending a get request: 127.0.0.1:8081/aop/test? name=Tom&age=18

At the same time, run the project in debug mode and check the parameters

You can see the parameters in MethodSignature

And each parameter of sysLogEntity assignment.

Six, summarized

1. Which methods are intercepted by crosscutting concerns, and how are they handled after interception? These concerns are called crosscutting concerns

2, Aspect -> (notification + pointcut) class is an abstraction of object features, and aspect is an abstraction of crosscutting concerns. Advice + pointcut means all the places to be applied to the advice enhancement code. (Including method orientation information)

Joinpoint -> the point to which the method is intercepted. Since Spring only supports join points for method types, the joinpoint in Spring refers to the method being intercepted. In fact, join points can also be fields or constructors

4. Pointcut -> (the section that describes which methods to intercept) the definition of intercepting join points

Advice refers to the code to be executed after intercepting the join point. There are five types of advice: pre, post, exception, final, and surround advice, also known as enhancement

The logical level includes the common logic and location information extracted by us. Spring only uses AOP at the method level — before, After,after-returning,after-throwing, and around — which means executing my common logic before and after a method call with an exception.

Recommended reading

【 Spring-boot 】 Spring AOP for tangent programming initial contact

AOP is used in Spring Boot to handle Web request logging uniformly

A bird never makes shit