AOP concepts, underlying principles, AspectJ

AOP (concept):
  1. What is AOP?

    (1) Aspect-oriented programming (aspect), AOP can be used to isolate various parts of business logic, thereby reducing the coupling between parts of business logic, improving program reusability, and improving development efficiency.

    (2) Popular description: Add new functions to the main functions without modifying the source code.

    (3) Use the login function to explain

    (4) Application scenarios: logs, permission checks,
    Insert image description here

The underlying principles of AOP:
  1. The bottom layer of AOP uses dynamic proxy

    (1) There are two situations of dynamic proxy

    The first one has an interface and uses JDK dynamic proxy

    *Create interface implementation classes and use JDK proxy to implement class enhancement methods

Insert image description here

The second type has no interface and uses CGLIB dynamic proxy.

*Create proxy objects of subclasses and enhance class methods

Insert image description here

AOP (JDK Dynamic Proxy):
  1. Use JDK dynamic proxy to create proxy objects using methods in the Proxy class

Insert image description here

(1) Call newProxyInstance method
Insert image description here

The method has three parameters:

The first parameter, the class loader

The second parameter is the class where the enhancement method is located. The interface implemented by this class supports multiple interfaces.

The third parameter implements the interface IncocationHandler, creates a proxy object, and writes an enhancement method.

  1. Write JDK dynamic proxy code

(1) Create interface

public interface UserDao {
    
    
    public int add(int a,int b);
    public String  update(String id);
}

(2) Create the implementation class in the interface

public class UserDaoImpi implements  UserDao{
    
    
    @Override
    public int add(int a, int b) {
    
    
        return a+b;
    }
    @Override
    public String update(String id) {
    
    
        return id;
    }
}

(3) Use the Proxy class to create an interface proxy object
https://blog.csdn.net/zhangzhen02/article/details/106121718?utm_medium=distribute.pc_relevant.none- task-blog-2defaultbaidujs_baidulandingword~default-4.pc_relevant_without_ctrlist&spm=1001.2101.3001.4242.3&utm_relevant_index=7

public class JDKProxy {
    
    
    public static void main(String[] args) {
    
    
        Class[] interfaces={
    
    UserDao.class};
        UserDaoImpi userDaoImpi=new UserDaoImpi();
        UserDao dao=(UserDao) Proxy.newProxyInstance(JDKProxy.class.getClassLoader(),interfaces,new UserDaoPRoxy(userDaoImpi));
        int add=dao.add(1,2);
        System.out.println(add);
    }
    //创建代理对象代码
    static class  UserDaoPRoxy implements InvocationHandler{
    
    
        //1. 把创建的是谁的代理对象,把谁传递过来
        //有参构造传递
        private Object obj;
        public UserDaoPRoxy(Object obj){
    
    
            this.obj=obj;
        }

        // 增强的逻辑
        @Override
        public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
    
    
            // 方法之前
            System.out.println("方法执行之前...."+method.getName()+":传递的参数"+ Arrays.toString(args));
            // 被增强的方法执行
            Object res=method.invoke(obj,args);
            //方法之后
            System.out.println("方法执行之后....."+obj);
            return res;
        }
    }
}
AOP (terminology)
  1. Junction

    Which methods in the class can be enhanced, these methods are called connection points

  2. entry point

    The point that is actually enhanced is called the entry point

  3. Notifications (enhanced)

    (1) The logical part of the actual enhancement is called notification (enhancement)

    (2) There are many types of notifications

    ​ *Pre-notification

    ​ *Post notification

    ​ *Surround notifications

    *Exception notification

    ​ *Final Notice

  4. section

    The process of applying notifications to pointcuts

AOP operation (preparation):
  1. The Spring framework generally implements AOP operations based on AspectJ.

    (1) What is AspectJ

    • Aspect-oriented framework
    • AspectJ is not a part of spring, it is an independent AOP framework. Generally, AspectJ and spring framework are used together to perform AOP operations.
  2. Implementing AOP operations based on AspectJ

    (1) Implementation based on xml configuration file

    (2) Implementation based on annotation method

  3. Introduce AOP related dependencies into the project project

Insert image description here

  1. pointcut expression

    (1) The function of entry point expression:

    (2) Grammatical structure:

    execution([Permission modifier] [Return type] [Class Quanlujin] [Method name] ([Parameter list])

AOP operations (AspectJ annotations)
  1. Create a class and define methods in the class

    public class User {
          
          
        public void add(){
          
          
            System.out.println("add .......");
        }
    }
    
  2. Create enhancement classes (write enhancement logic)

    In the enhanced class, create methods so that different methods represent different notification types.

  3. Enable generation of proxy objects in the spring configuration file

    <?xml version="1.0" encoding="UTF-8"?>
    <beans xmlns="http://www.springframework.org/schema/beans"
           xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
           xmlns:context="http://www.springframework.org/schema/context"
           xmlns:aop="http://www.springframework.org/schema/aop"
           xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
                            http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd
                            http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop.xsd">
        <!-- 开启注解扫描 -->
        <context:component-scan base-package="com.atguigu.spring5.aopanno"></context:component-scan>
    
        <!-- 开启Aspect生成代理对象-->
        <aop:aspectj-autoproxy proxy-target-class="true"></aop:aspectj-autoproxy>
    </beans>
    
  4. Configure different types of notifications

    (1) In the enhanced class, add notification type annotation on the notification method and use pointcut expression configuration

package com.atguigu.spring5.aopanno;

import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.*;
import org.springframework.core.annotation.Order;
import org.springframework.stereotype.Component;

//增强的类
@Component
@Aspect  //生成代理对象
public class UserProxy {
    
    
    //前置通知
    //@Before注解表示作为前置通知
    @Before(value = "execution(* com.atguigu.spring5.aopanno.User.add(..))")
    public void before() {
    
    
        System.out.println("before.........");
    }
    //相同切入点抽取
    @Pointcut(value = "execution(* com.atguigu.spring5.aopanno.User.add(..))")
    public void pointdemo() {
    
    

    }
    
    //后置通知(返回通知)
    @AfterReturning(value = "execution(* com.atguigu.spring5.aopanno.User.add(..))")
    public void afterReturning() {
    
    
        System.out.println("afterReturning.........");
    }

    //最终通知,相当于try-catch中的 finally
    @After(value = "execution(* com.atguigu.spring5.aopanno.User.add(..))")
    public void after() {
    
    
        System.out.println("after.........");
    }

    //异常通知
    @AfterThrowing(value = "execution(* com.atguigu.spring5.aopanno.User.add(..))")
    public void afterThrowing() {
    
    
        System.out.println("afterThrowing.........");
    }

    //环绕通知
    @Around(value = "execution(* com.atguigu.spring5.aopanno.User.add(..))")
    public void around(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
    
    
        System.out.println("环绕之前.........");
        //被增强的方法执行
        proceedingJoinPoint.proceed();
        System.out.println("环绕之后.........");
    }
}

@Test
public void testAopAnno() {
    
    
    ApplicationContext context =
        new ClassPathXmlApplicationContext("bean1.xml");
    User user = context.getBean("user", User.class);
    user.add();
}
运行结果:
before.........
add.......
  1. Same entry point extraction
//相同切入点抽取
@Pointcut(value = "execution(* com.atguigu.spring5.aopanno.User.add(..))")
public void pointdemo() {
    
    

}
//前置通知
//@Before注解表示作为前置通知
@Before(value = "pointdemo()")
public void before() {
    
    
    System.out.println("before.........");
}
  1. There are multiple enhancement classes, and priorities can be set

    Add the annotation, @Order (value), to the enhanced class. The smaller the value, the higher the priority.

@Component
@Aspect
@Order(1)    //通过@Order(1)来设置优先级
public class PersonProxy {
    
    
    //后置通知(返回通知)
    @Before(value = "execution(* com.atguigu.spring5.aopanno.User.add(..))")
    public void afterReturning() {
    
    
        System.out.println("Person Before.........");
    }
}

Insert image description here

  1. Developed entirely using annotations

    @Configuration
    @ComponentScan(basePackages = {
          
          "com.atguigu"})
    @EnableAspectJAutoProxy(proxyTargetClass = true)
    public class ConfigAop {
          
          
    }
    
AOP operations (AspectJ configuration files)
  1. Create two classes, the enhanced class and the enhanced class, and create methods

  2. Create two objects in the spring configuration file

  3. <!--创建对象-->
    <bean id="book" class="com.atguigu.spring5.aopxml.Book"></bean>
    <bean id="bookProxy" class="com.atguigu.spring5.aopxml.BookProxy"></bean>
    
  4. Configure the entry point in the spirng configuration file

<!--配置aop增强-->
<aop:config>
    <!--切入点-->
    <aop:pointcut id="p" expression="execution(* com.atguigu.spring5.aopxml.Book.buy(..))"/>
    <!--配置切面-->
    <aop:aspect ref="bookProxy">
        <!--增强作用在具体的方法上-->
        <aop:before method="before" pointcut-ref="p"/>
    </aop:aspect>
</aop:config>

Guess you like

Origin blog.csdn.net/qq_14930709/article/details/124460075