1、cglib是一个强大的,高性能,高质量的Code生成类库,它可以在运行期扩展Java类与实现Java接口。Hibernate用它来实现PO字节码的动态生成。
2、代理为控制要访问的目标对象提供了一种途径。当访问对象时,它引入了一个间接的层。JDK自从1.3版本开始,就引入了动态代理,并且经常被用来动态地创建代理。JDK的动态代理用起来非常简单,但它有一个限制,就是使用动态代理的对象必须实现一个或多个接口。如果想代理没有实现接口的继承的类,该怎么办?现在我们可以使用CGLIB包。
3、CGLIB是一个强大的高性能的代码生成包。它广泛的被许多AOP的框架使用,例如Spring AOP和dynaop,为他们提供方法的interception(拦截)。最流行的OR Mapping工具hibernate也使用CGLIB来代理单端single-ended(多对一和一对一)关联(对集合的延迟抓取,是采用其他机制实现的)。EasyMock和jMock是通过使用模仿(moke)对象来测试java代码的包。它们都通过使用CGLIB来为那些没有接口的类创建模仿(moke)对象。
4、CGLIB包的底层是通过使用一个小而快的字节码处理框架ASM,来转换字节码并生成新的类。除了CGLIB包,脚本语言例如Groovy和BeanShell,也是使用ASM来生成java的字节码。当然不鼓励直接使用ASM,因为它要求你必须对JVM内部结构包括class文件的格式和指令集都很熟悉
5、创建一个简单的代理类:
package com.sxit; import java.lang.reflect.Method; import net.sf.cglib.proxy.Enhancer; import net.sf.cglib.proxy.MethodInterceptor; import net.sf.cglib.proxy.MethodProxy; /** * @功能: * @作者:smile * @时间:2013-3-4 上午11:23:39 * @版本: 1.0 */ public class proxyUtil implements MethodInterceptor { private Object target; public proxyUtil(){} //通过构造函数传入需要代理的目标对象 public proxyUtil(Object target){ this.target = target; } //这里类似一个拦截器 在方法调用前后编制业务逻辑 public Object intercept(Object target, Method method, Object[] args, MethodProxy proxy) throws Throwable { System.out.println(method+"方法开始前..."); //调用原来的方法 Object o = proxy.invokeSuper(target, args); System.out.println(method+"方法结束了..."); System.out.println("返回对象为:"+o); return o; } }
6、一个简单的接口和它的实现类:
package com.sxit; /** * @功能: * @作者:smile * @时间:2013-3-4 上午11:22:32 * @版本: 1.0 */ public interface Person { /** * @功能:说话 */ public String say(String name); /** * @功能:看 */ public String look(String name); }
package com.sxit; /** * @功能: * @作者:smile * @时间:2013-3-4 上午11:23:08 * @版本: 1.0 */ public class Chinese implements Person { public String say(String name) { System.out.println("打印>>>>>>你好:"+name); return "你好:"+name; } public String look(String name) { System.out.println("打印>>>>>>我看到:"+name); return "我看到:"+name; } }
7、创建代理:
package com.sxit; import net.sf.cglib.proxy.Enhancer; public class Test { public static void main(String[] args) { //需要被代理的目標對象 Chinese c = new Chinese(); Enhancer hancer = new Enhancer(); //通过继承目标对象来实现代理 所以目标对象一定要有一个默认无参构造函数 反射的时候需要实例化父类对象 hancer.setSuperclass(c.getClass()); //设置代理回调函数 hancer.setCallback(new proxyUtil(c)); //代理后的对象 Chinese c2 = (Chinese) hancer.create(); c2.say("sb"); c2.look("傻逼"); } }
8、打印信息:
public java.lang.String com.sxit.Chinese.say(java.lang.String)方法开始前... 打印>>>>>>你好:sb public java.lang.String com.sxit.Chinese.say(java.lang.String)方法结束了... 返回对象为:你好:sb public java.lang.String com.sxit.Chinese.look(java.lang.String)方法开始前... 打印>>>>>>我看到:傻逼 public java.lang.String com.sxit.Chinese.look(java.lang.String)方法结束了... 返回对象为:我看到:傻逼
9、CallbackFilter可以实现不同的方法使用不同的回调方法:
package com.sxit; import java.lang.reflect.Method; import net.sf.cglib.proxy.CallbackFilter; public class CallBackFilterImp implements CallbackFilter { //方法名过滤 public int accept(Method method) { if(method.getName().equals("say")){ return 0; }else if(method.getName().equals("look")){ return 1; } return 0; } }
10、新写一个代理处理类proxyUtil2,只改动了打印信息:
package com.sxit; import java.lang.reflect.Method; import net.sf.cglib.proxy.Enhancer; import net.sf.cglib.proxy.MethodInterceptor; import net.sf.cglib.proxy.MethodProxy; /** * @功能: * @作者:smile * @时间:2013-3-4 上午11:23:39 * @版本: 1.0 */ public class proxyUtil2 implements MethodInterceptor { private Object target; public proxyUtil2(){} public proxyUtil2(Object target){ this.target = target; } //这里类似一个拦截器 在方法调用前后编制业务逻辑 public Object intercept(Object target, Method method, Object[] args, MethodProxy proxy) throws Throwable { System.out.println(method+"方法啦啦啦开始啦..."); //调用原来的方法 Object o = proxy.invokeSuper(target, args); System.out.println(method+"方法啦啦啦结束啦..."); System.out.println("返回对象为:"+o); return o; } }
11、测试:
package com.sxit; import net.sf.cglib.proxy.Callback; import net.sf.cglib.proxy.Enhancer; public class Test { public static void main(String[] args) { // 需要被代理的目標對象 Chinese c = new Chinese(); Enhancer hancer = new Enhancer(); // 通过继承目标对象来实现代理 所以目标对象一定要有一个默认无参构造函数 反射的时候需要实例化父类对象 hancer.setSuperclass(c.getClass()); // 一个回调函数数组 Callback[] callbacks = new Callback[] { new proxyUtil(c), new proxyUtil2(c) }; hancer.setCallbacks(callbacks); // 设置方法过滤器 hancer.setCallbackFilter(new CallBackFilterImp()); // 代理后的对象 Chinese c2 = (Chinese) hancer.create(); c2.say("sb"); c2.look("傻逼"); } }
12、打印信息:
public java.lang.String com.sxit.Chinese.say(java.lang.String)方法开始前... 打印>>>>>>你好:sb public java.lang.String com.sxit.Chinese.say(java.lang.String)方法结束了... 返回对象为:你好:sb public java.lang.String com.sxit.Chinese.look(java.lang.String)方法啦啦啦开始啦... 打印>>>>>>我看到:傻逼 public java.lang.String com.sxit.Chinese.look(java.lang.String)方法啦啦啦结束啦... 返回对象为:我看到:傻逼
13、注意:
CallBackFilterImp中的return 0和return 1这里的值是指回调数组callbacks数组下表,0则对应proxyUtil这个代理类处理,1则对应proxyUtil2这个代理类处理。
相关推荐
在Java开发中,动态代理和CGLIB代理是两种常见的面向切面编程(AOP)实现方式,它们都用于在不修改原有代码的情况下,增强或扩展对象的功能。本篇文章将深入探讨JDK动态代理和CGLIB代理的区别,以及它们在实际应用中...
以上就是CGLIB代理模式的基本原理和使用方法。CGLIB的动态代理在很多场景下都非常实用,例如在AOP框架中拦截方法执行,进行日志记录、性能监控、事务管理等。然而,由于CGLIB是基于继承的,所以如果目标类为final...
本文将深入探讨两种主要的Java代理实现:JDK动态代理和CGLIB代理。 一、JDK动态代理 JDK动态代理基于接口实现,它要求被代理的类必须实现至少一个接口。在运行时,Java会动态地创建一个新的类,这个类实现了与原始...
在Java编程领域,动态代理和Cglib代理是两种常用的技术,用于在运行时创建对象的代理,以实现额外的功能,如AOP(面向切面编程)中的日志、事务管理等。本篇文章将深入探讨这两种代理机制,尤其是Cglib代理。 首先...
Spring支持两种代理机制:基于接口的JDK动态代理和基于类的CGLIB代理。 CGLIB(Code Generation Library)是一个强大的高性能代码生成库,其底层是通过使用操作Java字节码的开源字节码操作框架(比如ASM)来实现的...
CGLib代理是Java中实现动态代理的一种方式,与另一种常用的JDK动态代理相比,CGLib在处理非接口类的代理时具有更高的性能优势。 CGLib的核心是通过ASM库来操作字节码生成新的类,这些新生成的类是对原始类的扩展,...
CGLib代理主要分为两种类型:接口代理和类代理。对于实现了接口的类,CGLib可以像JDK的动态代理一样工作,但如果目标类没有实现任何接口,CGLib则可以通过生成目标类的子类来实现动态代理。CGLib的核心类包括...
JDK动态代理和CGLIB代理是两种常用的实现方式。 首先,我们来看看JDK动态代理。JDK动态代理主要通过`java.lang.reflect.Proxy`类和`java.lang.reflect.InvocationHandler`接口来实现。Proxy类用于创建一个代理对象...
JDK代理和Cglib代理是两种常用的动态代理实现方式。 **JDK代理(Java Dynamic Proxy)** JDK动态代理是Java标准库提供的一种代理机制,位于`java.lang.reflect`包下的`Proxy`类和`InvocationHandler`接口。JDK代理...
了解和掌握CGlib代理技术,能够极大地提升我们的代码复用性和可维护性,特别是在构建复杂的企业级应用时,CGlib代理能够帮助我们更好地实现面向切面的编程。 总的来说,`cloud-cglib.jar`这个压缩包中的CGlib库为...
CGlib代理通过继承目标类并覆写其方法来实现,因此即使目标类没有接口也可以进行代理。 总结来说,JDK静态代理适用于目标类实现了接口的情况,而动态代理和CGlib则更灵活,可以处理无接口的目标类。动态代理更简洁...
**CGlib代理详解** 1. **原理介绍** CGlib代理机制主要是通过动态创建一个目标类的子类,并重写其方法来实现代理。当调用代理对象的方法时,实际上是调用了子类的方法,从而可以在不修改原有代码的情况下对目标类...
动态代理主要分为两种:JDK代理和CGLIB代理。 **JDK代理**是基于接口的代理,它通过`java.lang.reflect.Proxy`类和`java.lang.reflect.InvocationHandler`接口实现。当我们的目标对象实现了特定的接口时,我们可以...
Java动态代理和CGLIB代理是两种常用的在Java中实现面向切面编程(AOP)的技术,它们允许我们在不修改原有代码的情况下,为方法添加额外的功能,如日志记录、性能监控、事务管理等。本篇文章将深入探讨这两种代理机制...
以上就是关于静态代理、动态代理(JDK)和CGlib代理的基本介绍。它们在Java开发中都有广泛的应用,尤其是在AOP(面向切面编程)和框架设计中,如Spring AOP就使用了这两种代理技术。了解并熟练掌握这些代理机制,...
Spring AOP提供了两种代理方式:JDK动态代理和Cglib代理。 Cglib代理是Spring AOP在无法使用JDK动态代理(例如代理的目标对象没有实现接口)时的另一种选择。Cglib是一个强大的、高性能的代码生成库,它基于ASM库来...
jdk 的动态代理和CGLIB代理
springAOP等框架中,大量用到代理技术; 两类代理技术: 1,java动态代理,见JDK文档或相关java书; 2.cglib创建代理类,比第一种更加简单,代理类和背代理类不需要实现共同接口。本例子就是cglib代理的例子,很简单
CGLIB代理是一种在Java编程中广泛使用的动态代理技术,尤其在Spring框架中扮演着重要角色。CGLIB(Code Generation Library)是一个强大的高性能的代码生成库,它可以在运行期扩展Java类与实现Java接口。当JDK动态...
Cglib代理模式实现步骤 1) 需要引入cglib的jar文件 2) 在内存中动态构建子类,注意代理的类不能为final,否则报错 java.lang.IllegalArgumentException: 3) 目标对象的方法如果为final/static,那么就不会被拦截,即...