当前位置: 首页 > article >正文

手写JDK动态代理实现AOP

AOP底层?

AOP(Aspect Oriented Programming,面向切面编程)在 Java 中的实现有多种方式,其中使用 JDK 动态代理和 CGLIB 代理较为常见。

当你的应用程序遵循面向接口编程的原则时,JDK 动态代理是一个自然的选择。如果你的目标对象实现了一个或多个接口,并且你希望在不修改目标对象代码的情况下为其添加额外的功能,如日志记录、性能监测、安全检查等,那么可以使用 JDK 动态代理。

对象如果实现了接口就是用jdk动态代理,否则使用cglib

使用JDK动态代理实现环绕通知

1.Proxy.newProxyInstance()

这个方法的作用就是创建一个类的动态代理对象

三个参数:

ClassLoader loader:一个ClassLoader对象,用于定义代理对象的类加载器。通常可以使用目标对象的类加载器,以便代理对象能够访问目标对象所在的类路径。简称类加载器
Class<?>[] interfaces:一个Class对象的数组,表示代理对象要实现的接口列表。通过指定这些接口,确保代理对象可以像实现了这些接口的真实对象一样被使用。
InvocationHandler h:一个InvocationHandler对象,它是代理对象的调用处理程序。当在代理对象上调用方法时,这个处理程序会被调用

重点:InvocationHandler这个对象就是调用代理对象的方法时会执行里面的invoke()方法

2.InvocationHandler

因为调用代理对象的方法时会执行里面的invoke方法

因此我们需要实现这个接口去重写里面的方法去实现环绕通知。

这里我们使用OrderHandler实现InvocationHandler重写invoke方法实现环绕通知

public class OrderHandler implements InvocationHandler {

    private Object object;

    public OrderHandler(Object object){
        this.object = object;
    }
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        System.out.println("============环绕通知前:执行一些前置操作==========");
        Object invoke = method.invoke(object, args);
        System.out.println("============环绕通知后:执行一些后置操作==========");
        return invoke;
    }
}
method.invoke(object, args):这个方法的作用是在代理对象的方法被调用时,通过反射机制调用被代理对象的相应方法。

3.所有代码

——接口以及实现类

public interface OrderService{
    void add();
    void get();
    void del();
    void update();
}
public class OrderServiceImpl implements OrderService{
    @Override
    public void add() {
        System.out.println("添加商品方法add()");
    }

    @Override
    public void get() {
        System.out.println("获取商品方法get()");
    }

    @Override
    public void del() {
        System.out.println("删除商品方法del()");
    }

    @Override
    public void update() {
        System.out.println("更新商品方法update()");
    }
}

——OrderHandler

public class OrderHandler implements InvocationHandler {

    private Object object;

    public OrderHandler(Object object){
        this.object = object;
    }
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        System.out.println("============环绕通知前:执行一些前置操作==========");
        Object invoke = method.invoke(object, args);
        System.out.println("============环绕通知后:执行一些后置操作==========");
        return invoke;
    }
}

——main方法

使用newProxyInstance()方法创建OrderService的动态代理类,参数:类加载器、接口列表、InvocationHandler

public class main {
    public static void main(String[] args) {
        OrderService orderService = new OrderServiceImpl();
        OrderService proxyInstance =
                (OrderService)Proxy.newProxyInstance(
                orderService.getClass().getClassLoader(),
                orderService.getClass().getInterfaces(),
                new OrderHandler(orderService));
        System.out.println("使用动态代理:");
        proxyInstance.add();
        proxyInstance.del();
    }
}

结果


http://www.kler.cn/a/389703.html

相关文章:

  • uniapp使用scroll-view下拉刷新与上滑加载
  • C#文字识别API场景解析、表格识别提取
  • python: postgreSQL using psycopg2 or psycopg
  • Scala入门基础(17.1)Set集习题
  • Lucene 和 Elasticsearch 中更好的二进制量化 (BBQ)
  • 深度学习——权重初始化、评估指标、梯度消失和梯度爆炸
  • c# 开发web服务 webserver
  • MFC 重写了listControl类(类名为A),并把双击事件的处理函数定义在A中,主窗口如何接收表格是否被双击
  • sql速度优化多条合并为一条语句
  • 关于git使用的图文教程(包括基本使用,处理冲突问题等等)超详细
  • 调整TCP参数, 优化网络性能
  • 基于springboot的家装平台设计与实现
  • 【HCIP园区网综合拓扑实验】配置步骤与详解(已施工完毕)
  • 整合本地市场机会 同城小程序打造社区商圈
  • Uniapp去除顶部导航栏-小程序、H5、APP适用
  • 专业140+总分430+复旦大学875信号与系统考研经验原957电子信息通信考研,真题,大纲,参考书。
  • ssm基于BS的仓库在线管理系统的设计与实现+vue
  • 单链表算法题(数据结构)
  • 【网络安全 | 漏洞挖掘】Google SSO用户的帐户接管
  • 人工智能学习--分类模型的训练和应用
  • 了解 Open RAN 架构中的 DU 和 CU
  • c语言编程题(函数)
  • 如何在MT4中实现神经网络EA?
  • AI与隐私:Facebook如何在数据保护中平衡创新与安全
  • stm32对EV1527波形进行解码
  • 贪心算法-汽车加油