• JDK 动态代理原理


    代理模式

    客户端不直接访问目标对象,需要通过第三者来实现间接访问对象

    代理对象在客户端和目标对象之间起中介作用,能够屏蔽目标对象不想让客户端知道的内容,或增加额外的服务

    动态代理

    JDK 动态代理:基于接口,利用 JDK API 动态地在内存中构建代理对象,从而实现目标对象的代理功能。称为 JDK 代理或接口代理。

    JDK 动态代理例子

    • MapperInvocationHandler 实现 InvocationHandler 接口,实现 invoke 方法,该方法最终是代理类增强的目标类方法
    • JDKProxyFactory 用于生成代理对象的工厂,通过调用 Proxy.newProxyInstance 方法生成代理对象
    • UserMapper 目标类,JDK 代理的目标类必须实现某个接口
    • IUserMapper 目标类接口

    MapperInvocationHandler

    public class MapperInvocationHandler implements InvocationHandler {
        // 动态的目标对象
        private Object target;
    
        public MapperInvocationHandler(Object target) {
            this.target = target;
        }
        /**
         * 增强方法
         * @param proxy 代理实例
         * @param method 目标方法
         * @param args 目标方法参数
         * @return 返回值
         * @throws Throwable 异常
         */
        @Override
        public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
            System.out.println("=========JDK 动态代理前置增强=========");
            method.invoke(target, args);
            System.out.println("=========JDK 动态代理后置增强=========");
            return null;
        }
    }
    

    JDKProxyFactory

    public class JDKProxyFactory {
        // 动态的目标对象
        private Object target;
    
        public JDKProxyFactory(Object target) {
            this.target = target;
        }
    
        // 为目标对象生成代理对象
        public Object getTargetProxy(){
            return Proxy.newProxyInstance(
                    // 目标对象使用的类加载器
                    target.getClass().getClassLoader(),
                    // 目标对象实现的接口
                    target.getClass().getInterfaces(),
                    // 事件处理器
                    new MapperInvocationHandler(target)
            );
        }
    }
    

    IUserMapper

    public interface IUserMapper {
        void save();
    }
    

    UserMapper

    public class UserMapper implements IUserMapper {
        @Override
        public void save() {
            System.out.println("保存用户数据");
        }
    }
    

    Client

    public class Client {
        public static void main(String[] args) {
            JDKProxyFactory jdkProxyFactory = new JDKProxyFactory(new UserMapper());
            IUserMapper userMapperProxy = (IUserMapper) jdkProxyFactory.getTargetProxy();
            userMapperProxy.save();
        }
    }
    

    运行结果

    =========JDK 动态代理前置增强=========
    保存用户数据
    =========JDK 动态代理后置增强=========
    
    Process finished with exit code 0
    

    JDK 动态代理原理

  • 相关阅读:
    上游服务不可用了,下游服务如何应对?
    关于org.tio.core.udp的UDP交互使用示例
    细胞穿膜肽MPG,Mpa-GALFLGFLGAAGSTMGA-OH
    CUDA_VISIBLE_DEVICES
    在NodeJS中使用npm包实现JS代码混淆加密
    python矩阵可视化
    【python学习】基础篇-常用第三方库-psutil:用于获取CPU、磁盘与网络等系统信息和进程管理
    【学习笔记】博弈论
    RabbitMQ
    c++中的cin和getline()函数
  • 原文地址:https://www.cnblogs.com/SihanLin/p/17774778.html