前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >CGLIB动态代理

CGLIB动态代理

作者头像
itlemon
发布2020-04-03 14:42:02
4810
发布2020-04-03 14:42:02
举报
文章被收录于专栏:深入理解Java

[JDK动态代理][1]必须提供接口才可以使用,但是在某些环境下,接口这个条件是无法满足的,这时候[JDK动态代理][1]就无法使用了,只能采取第三方技术,比如CGLIB动态代理技术。它的最大的优势就是不需要提供接口,只要一个非抽象类就可以实现动态代理。

第一步:定义真实服务类

代码语言:javascript
复制
package com.lemon.designmode.bean;

/**
 * @author lemon
 * @date 2018/2/11 下午12:37
 */
public class CglibTarget {

    public void sayHello() {
        System.out.println("向CGLIB问好...");
    }
}

这个真实服务类可以不需要实现任何接口。

第二步:动态代理绑定和代理逻辑实现

这里将获取代理对象和对真实服务类进行代理的逻辑代码集中在一个类中,实现代理逻辑的类需要实现MethodInterceptor接口中的intercept方法。

代码语言:javascript
复制
package com.lemon.designmode.proxy;

import net.sf.cglib.proxy.Enhancer;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;

import java.lang.reflect.Method;

/**
 * @author lemon
 * @date 2018/2/11 下午12:28
 */
public class CglibProxyExample implements MethodInterceptor {

    /**
     * 获取代理对象
     *
     * @param clazz 真实服务类的Class对象
     * @return 代理对象
     */
    public Object getProxy(Class clazz) {
        // CGLIB增强类
        Enhancer enhancer = new Enhancer();
        // 设置需要被增强的类型
        enhancer.setSuperclass(clazz);
        // 设置代理逻辑对象,此对象必须实现MethodInterceptor接口
        enhancer.setCallback(this);
        return enhancer.create();
    }

    /**
     * 代理的逻辑方法
     *
     * @param proxy       代理对象
     * @param method      代理方法
     * @param args        被代理方法的参数
     * @param methodProxy 方法代理
     * @return 代码逻辑返回
     * @throws Throwable 异常
     */
    @Override
    public Object intercept(Object proxy, Method method, Object[] args, MethodProxy methodProxy) throws Throwable {
        System.out.println("进入代理方法");
        System.out.println("代理方法调用真实对象之前的逻辑处理");
        Object obj = methodProxy.invokeSuper(proxy, args);
        System.out.println("代理方法调用真实对象之后的逻辑处理");
        return obj;
    }
}

这里用了CGLIB的加强者Enhancer,通过设置超类的方法(setSuperclass),然后通过setCallback方法设置哪个类为它的代理类。其中this表示当前类对象,也就是说当前类就是逻辑代码的主要类。

第三步:测试CGLIB动态代理

代码语言:javascript
复制
package com.lemon.designmode.test;

import com.lemon.designmode.bean.CglibTarget;
import com.lemon.designmode.proxy.CglibProxyExample;

/**
 * @author lemon
 * @date 2018/2/11 下午12:46
 */
public class CglibProxyTest {

    public static void main(String[] args) {
        CglibProxyExample cglibProxyExample = new CglibProxyExample();
        CglibTarget proxy = (CglibTarget) cglibProxyExample.getProxy(CglibTarget.class);
        proxy.sayHello();
    }
}

测试方法运行结果如下:

代码语言:javascript
复制
进入代理方法
代理方法调用真实对象之前的逻辑处理
向CGLIB问好...
代理方法调用真实对象之后的逻辑处理

如果想了解[JDK动态代理][1],请移步另一篇博客《[JDK动态代理][1]》。 [1]: http://blog.csdn.net/lammonpeter/article/details/79309754

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2018/02/11 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 第一步:定义真实服务类
  • 第二步:动态代理绑定和代理逻辑实现
  • 第三步:测试CGLIB动态代理
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档