Spring5学习笔记(8) — “Spring AOP底层原理(动态代理)”

Spring AOP底层原理(动态代理)


一、AOP 底层使用 “动态代理”

动态代理有两种情况

  • 第一种:有接口情况,使用JDK 动态代理

在这里插入图片描述


  • 第二种:无接口情况,使用CGLIB动态代理

在这里插入图片描述
动态代理即为创建(被增强类/实现类的)代理对象
通过类的代理对象增加原来类的功能


二、“JDK 动态代理”(代码实例)

1.使用 JDK 动态代理,调用 Proxy 类里的newProxyInstance方法创建代理对象

public static Object newProxyInstance(
	ClassLoader loader,
	Class<?>[] interfaces,
	InvocationHandler h
)

1)ClassLoader loader
类加载器
2)Class<?>[] interfaces
被增强方法所在的类,这个类实现的接口,支持多个接口
3)InvocationHandler h
实现这个接口 InvocationHandler,创建代理对象,写增强的部分


2.编写 JDK 动态代理代码

//1.编写一个接口,定义方法
public interface UserDao {
    public int add(int a,int b);
    public String update(String id);
}
//2.定义接口的实现类,这个类即为“被增强类”
public class UserDaoImpl implements UserDao{
	@Override
    public int add(int a,int b){
        System.out.println("add方法执行啦!");
        return a+b;
    }
    @Override
    public String update(String id){
        return id;
    }
}
//3.使用 Proxy 类创建接口代理对象
public class JDKproxy {
    public static void main(String[] args) {
        Class[] interfaces = {UserDao.class};
        
        //创建实现类的对象,将对象传入下面的第三个参数
        UserDaoImpl ud = new UserDaoImpl();
        
        //创建UserDao接口的代理对象( Proxy.newProxyInstance()方法返回Object类对象,使用要进行强转)
        UserDao dao=(UserDao) Proxy.newProxyInstance(JDKproxy.class.getClassLoader(),interfaces,new UserDaoProxy(ud));
        /** 
         Proxy.newProxyInstance()方法:
         第一参数,类加载器 
         第二参数,增强方法所在的类,这个类实现的接口,(支持多个接口)
         第三参数,实现这个接口 InvocationHandler,创建代理对象,写增强的部分  
         **/
       
        int result = dao.add(1, 3);
        System.out.println(result);
    }
}
//4.InvocationHandler接口的实现类,作为第三参数传入Proxy方法
class UserDaoProxy implements InvocationHandler{
    /*
    * 创建谁的对象,就把谁的对象传过来
    * 通过有参构造传对象
    */
    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("方法之前执行......");

        //被增强的方法执行
        Object res=method.invoke(obj,args);

        //方法之后执行
        System.out.println("方法之后执行......");

        return res;
    }
}

代码执行结果:
在这里插入图片描述


重点理解:

动态代理就是要生成一个包装类对象,由于代理的对象是动态的,所以叫动态代理。

由于我们需要增强,这个增强是需要留给开发人员开发代码的,因此代理类不能直接包含被代理对象,而是一个InvocationHandler
InvocationHandler包含被代理对象,并负责分发请求给被代理对象,分发前后均可以做增强。从原理可以看出,JDK动态代理是“对象”的代理。

这个对象的invoke()方法就是Proxy这个动态代理类所代理的接口类的抽象方法的真实实现

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值