The difference between Proxy and CGLIB

JAVA实现动态代理常用的有两种方式:

1, java.lang.reflect.Proxy (JDK)

2, net.sf.cglib.proxy.Enhancer(cglib)

两者之间的区别如图1-1 所示。

                                                            图1-1 jdk 和 cglib 概要图

jdk和cglib实现动态代理的原理是完全不同的,jdk是通过目标class所实现的接口,而cglib是通过目标对象的子类完成的。

他们二者互相补充,基本上能够满足所有的动态代理需求。


jdk和cglib实现动态代理的简单例子如下所示:


jdk:

****************************************************************************************************

1,定义接口

public interface SubInter {
    
    public abstract void display() ;
    
    public abstract void display2();

}


2, 定义实现类

public class SonObject implements SubInter {

    @Override
    public void display() {
        System.out.println("This is a realy object !");
    }

    @Override
    public void display2() {
        System.out.println("This is a test2!");
        
    }

}

3, 设置回调类

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

public class Dynamic implements InvocationHandler {

    private Object object;
    
    private String validateString;
    
    public Dynamic(Object object, String validateString) {
        this.object = object;
        this.validateString = validateString;
    }

    @Override
    public Object invoke(Object arg0, Method arg1, Object[] arg2)
            throws Throwable {
        boolean b = validateMehod(arg1.getName());
        Object object = null;
        if (b) {
            before();
            object = arg1.invoke(this.object, arg2);
            after();
        }else {
            object = arg1.invoke(this.object, arg2);
        }
        return object;
    }
    
    public boolean validateMehod(String methodName) {
        boolean b = false;
        String methodNames[] = validateString.split("&");
        for (String name : methodNames) {
            if (methodName.contains(name)) {
                b = true;
                return b;
            }
        }
        return b;
    }

    public void before() {
        System.out.println("Before");
    }

    public void after() {
        System.out.println("after");
    }

}

4, 动态代理工厂

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

/**
 *
 * @author gyf
 *
 *         We can get a proxy instance for the target object by the specify
 *         InvocationHandler.
 *
 */
public class DynamicProxyFactory {

    public static Object createProxyInstance(Object targetObject,
            InvocationHandler handler) {
        return Proxy.newProxyInstance(targetObject.getClass().getClassLoader(),
                targetObject.getClass().getInterfaces(), handler);
    }

}


5, 单元测试

public class Junit {
    
   @Test
    public void testJDK() {
        SubInter targetObject = new SonObject();
        InvocationHandler handler = new Dynamic(targetObject, "2&3");
        SubInter object = (SubInter)DynamicProxyFactory.createProxyInstance(targetObject, handler);
        object.display2();
    }

}

cglib

*************************************************************************************************

1, 定义目标类

public class TargetObject {
    
    public void display() {
        System.out.println("This is a test");
    }
    
    public void display2() {
        System.out.println("This is a test2");
    }

}


2, 定义回调类

import java.lang.reflect.Method;

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

public class CglibDynamic implements MethodInterceptor{
    
    private Object targetObject;
    
    public CglibDynamic(){}
    
    public CglibDynamic(Object object) {
        this.targetObject = object;
    }

    @Override
    public Object intercept(Object arg0, Method arg1, Object[] arg2,
            MethodProxy arg3) throws Throwable {
        
        Object object = arg3.invoke(targetObject, arg2);
        
        return object;
    }

}

3, 定义动态代理工厂

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

public class CglibDynamicFactory {

    public static Object getProxyInstance(Object targetObject,
            MethodInterceptor methodInterceptor) {
        
        Enhancer enhancer = new Enhancer();
        enhancer.setSuperclass(targetObject.getClass());
        enhancer.setCallback(methodInterceptor);
        
        return enhancer.create();
    }

}


4, 单元测试

import net.sf.cglib.proxy.MethodInterceptor;

import org.junit.Test;

import com.cglib.proxy.CglibDynamic;
import com.cglib.proxy.CglibDynamicFactory;
import com.cglib.proxy.TargetObject;

public class Junit {
    
    @Test
    public void testCglib() {
        TargetObject object = new TargetObject();
        MethodInterceptor interceptor = new CglibDynamic(object);
        
        TargetObject son = (TargetObject)CglibDynamicFactory.getProxyInstance(object, interceptor);
        son.display();
    }

}


当然Hibernate现在采用了javasist来取代cglib, 有关javasist我会继续学习。




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值