JDK动态代理基础知识

16 篇文章 0 订阅
6 篇文章 0 订阅

可以简单的认为,动态代理就是实现在不修改源程序的基础上,对原有的类方法进行增强。

其有一点要求是:要实现动态代理的类,必须实现至少一个接口。否则需要CGLIB动态代理机制。

JDK的动态代理机制也是Spring AOP的底层实现方式的一种。我们来了解一下其机制:

实现:实际使用方式可能多种多样,我们就按自己的来。

如,下面有一个接口:UserDao

package com.imooc.aop.demo1;

public interface UserDao {

    public void save();

    public void update();

    public void delete();

    public void find();

}

其中有四个需要实现的方法。下面有一个实现类:UserDaoImpl

package com.imooc.aop.demo1;

public class UserDaoImpl implements UserDao {

    public void save() {
        System.out.println("保存用户...");
    }

    public void update() {
        System.out.println("修改用户...");

    }

    public void delete() {
        System.out.println("删除用户...");

    }

    public void find() {
        System.out.println("查询用户...");

    }
}

现在需要对save()方法进行权限的检查。使用动态代理方式。先编写一个工具类:MyJdkProxy。这个类的目的是用来生成动态代理对象,以及添加的业务逻辑,此处就是对save()方法进行权限检查。

package com.imooc.aop.demo1;

import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;

//实现InvocationHandler接口,实现其中的invoke()方法
public class MyJdkProxy implements InvocationHandler {

    //这里使用一个目标接口对象为属性,以方便获得其类加载器
    private UserDao userDao;

    //构造方法中传入一个目标类,赋值给属性
    public MyJdkProxy(UserDao userDao){
        this.userDao = userDao;
    }
    //获取代理对象的方法
    public Object createProxy(){
        //获得代理对象。使用Proxy的静态方法:newProxyInstance(目标类加载器,目标类的接口,InvocationHandler的实现类)
        Object proxy = Proxy.newProxyInstance(
userDao.getClass().getClassLoader(),userDao.getClass().getInterfaces(),this);
        return proxy;
    }
    //实现InvocationHandler的invoke(代理对象,目标方法,目标方法参数)。执行代理对象方法时,就是执行此invoke方法
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        //因为仅对save方法进行修改,此处进行判断,进行业务的处理。
        if("save".equals(method.getName())){
            System.out.println("权限校验=========");
        }
        //返回method的invoke方法。在java反射中提到过,方法对象最重要的方法就是invoke。该方法返回Object对象
        //反射机制使用此方法:invoke(方法调用对象,方法参数)来执行方法对象所对应的方法
        return method.invoke(userDao,args);
    }
}

以上程序实现了生成代理对象以及对save()方法进行处理。下面测试一下:

package com.imooc.aop.demo1;

import org.junit.Test;

public class SpringDemo1 {

    @Test
    public void demo1(){

        UserDao userDao = new UserDaoImpl();
        UserDao proxy = (UserDao)new MyJdkProxy(userDao).createProxy();
        proxy.save();
        proxy.delete();
        proxy.find();
        proxy.update();
    }
}

在输出结果可以看到,执行save()方法时进行了校验。

需要说明的时,使用spring时,我们通常不会写以上这些代码,spring已经封装好了动态代理机制。我们只需要修改配置文件即可。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值