CGlib与JDK动态代理

1 实现两种动态代理

1.1 JDK代理

JDK动态代理只能对接口实现代理
定义一个接口

public interface  Service {
    public abstract void say();
}

实现接口

public class ServiceImpl implements Service {
    @Override
    public void say() {
        System.out.println("Hello JDK");
    }
}

实现InvocationHandler

public class JDKInvocationHandler implements InvocationHandler {

    // 目标对象
    private Object target;
    /**
     * 构造方法
     * @param target 目标对象
     */
    public JDKInvocationHandler(Object target) {
        super();
        this.target = target;
    }
    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        // 在目标对象的方法执行之前简单的打印一下
        System.out.println("------------------before------------------");
        // 执行目标对象的方法
        Object result = method.invoke(target, args);
        // 在目标对象的方法执行之后简单的打印一下
        System.out.println("-------------------after------------------");

        return result;
    }
    public Object getProxy() {
        return Proxy.newProxyInstance(Thread.currentThread().getContextClassLoader(),
                target.getClass().getInterfaces(), this);
    }
}

测试类

public class TestJDKProxy {
    public static void main(String[] a) {
        // 实例化目标对象
        Service userService = new ServiceImpl();

        // 实例化InvocationHandler
        JDKInvocationHandler invocationHandler = new JDKInvocationHandler(userService);

        // 根据目标对象生成代理对象
        Service proxy = (Service) invocationHandler.getProxy();

        // 调用代理对象的方法
        proxy.say();
        //将生成的代理类写到E盘
        writeProxyClassToHardDisk("E:/$Proxy11.class");
    }
        public static void writeProxyClassToHardDisk(String path) {
        byte[] classFile = ProxyGenerator.generateProxyClass("$Proxy11", ServiceImpl.class.getInterfaces());
        FileOutputStream out = null;
        try {
            out = new FileOutputStream(path);
            out.write(classFile);
            out.flush();
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                out.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }
}

1.2 CGlib代理

CGlib动态代理需要cglib的jar包
maven引入

    <dependency>
      <groupId>cglib</groupId>
      <artifactId>cglib</artifactId>
      <version>3.1</version>
    </dependency>

定义一个被代理类

public class SomeClass {
    public void doSomething() {
        System.out.println("方法正在执行...");
    }
}

实现cglib的MethodInterceptor

public class CGlibProxy implements MethodInterceptor {
    private Object target;

    public Object getInstance(Object target) {
        this.target = target;
        Enhancer enhancer = new Enhancer();
        enhancer.setSuperclass(this.target.getClass());
        enhancer.setCallback(this);
        return enhancer.create();
    }

    @Override
    public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
        System.out.println("..........before..........");
        proxy.invokeSuper(obj, args);
        System.out.println("..........after ..........");
        return null;
    }
}

测试类

public class TestCGlib {
    public static void main(String[] a) throws Exception {
        //输出生成的代理类class文件到指定的目录
        System.setProperty(DebuggingClassWriter.DEBUG_LOCATION_PROPERTY, "E:\\cglib");

        CGlibProxy cglib = new CGlibProxy();
        SomeClass businessObject = (SomeClass) cglib.getInstance(new SomeClass());
//        System.out.println(businessObject.getClass().getName());
//        System.out.println(businessObject.getClass().getSuperclass().getName());
        businessObject.doSomething();
    }
}

2 代理生成的代理类解析

2.1 JDK代理类

import com.lww.learnjdk.JDKProxy.Service;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.lang.reflect.UndeclaredThrowableException;
//看到这就明白为什么JDK只能代理接口了
//JDK动态代理自己就得继承Proxy类,而Java只能单继承
public final class $Proxy11
  extends Proxy
  implements Service
{
  private static Method m1;
  private static Method m2;
  private static Method m3;
  private static Method m0;

  public $Proxy11(InvocationHandler paramInvocationHandler)
    throws 
  {
    super(paramInvocationHandler);
  }

  public final boolean equals(Object paramObject)
    throws 
  {
    try
    {
      return ((Boolean)this.h.invoke(this, m1, new Object[] { paramObject })).booleanValue();
    }
    catch (Error|RuntimeException localError)
    {
      throw localError;
    }
    catch (Throwable localThrowable)
    {
      throw new UndeclaredThrowableException(localThrowable);
    }
  }

  public final String toString()
    throws 
  {
    try
    {
      return (String)this.h.invoke(this, m2, null);
    }
    catch (Error|RuntimeException localError)
    {
      throw localError;
    }
    catch (Throwable localThrowable)
    {
      throw new UndeclaredThrowableException(localThrowable);
    }
  }

  public final void say()
    throws 
  {
    try
    {
    //m3通过Java反射调用被代理接口的say方法
      this.h.invoke(this, m3, null);
      return;
    }
    catch (Error|RuntimeException localError)
    {
      throw localError;
    }
    catch (Throwable localThrowable)
    {
      throw new UndeclaredThrowableException(localThrowable);
    }
  }

  public final int hashCode()
    throws 
  {
    try
    {
      return ((Integer)this.h.invoke(this, m0, null)).intValue();
    }
    catch (Error|RuntimeException localError)
    {
      throw localError;
    }
    catch (Throwable localThrowable)
    {
      throw new UndeclaredThrowableException(localThrowable);
    }
  }

  static
  {
    try
    {
      m1 = Class.forName("java.lang.Object").getMethod("equals", new Class[] { Class.forName("java.lang.Object") });
      m2 = Class.forName("java.lang.Object").getMethod("toString", new Class[0]);
      m3 = Class.forName("com.lww.learnjdk.JDKProxy.Service").getMethod("say", new Class[0]);
      m0 = Class.forName("java.lang.Object").getMethod("hashCode", new Class[0]);
      return;
    }
    catch (NoSuchMethodException localNoSuchMethodException)
    {
      throw new NoSuchMethodError(localNoSuchMethodException.getMessage());
    }
    catch (ClassNotFoundException localClassNotFoundException)
    {
      throw new NoClassDefFoundError(localClassNotFoundException.getMessage());
    }
  }
}

2.2 CGlib代理类

生成的Class源码,使用jd-gui查看
使用jd-gui查看可能会出现反编译不全的情况。我后面使用procyon-decompiler-0.5.30.jar反编译的
jar地址https://bitbucket.org/mstrobel/procyon/downloads/
命令java -jar procyon-decompiler-0.5.30.jar SomeClass$$EnhancerByCGLIB$.$84389373.class
去掉一个两个$中间的.因为编辑器的原因加上的

package com.lww.learnjdk.CGlibProxy;

import java.lang.reflect.Method;
import net.sf.cglib.core.ReflectUtils;
import net.sf.cglib.core.Signature;
import net.sf.cglib.proxy.Callback;
import net.sf.cglib.proxy.Factory;
import net.sf.cglib.proxy.MethodInterceptor;
import net.sf.cglib.proxy.MethodProxy;

public class SomeClass$$EnhancerByCGLIB$$84389373
  extends SomeClass
  implements Factory
{
  private boolean CGLIB$BOUND;
  private static final ThreadLocal CGLIB$THREAD_CALLBACKS;
  private static final Callback[] CGLIB$STATIC_CALLBACKS;
  private MethodInterceptor CGLIB$CALLBACK_0;
  private static final Method CGLIB$doSomething$0$Method;
  private static final MethodProxy CGLIB$doSomething$0$Proxy;
  private static final Object[] CGLIB$emptyArgs;
  private static final Method CGLIB$finalize$1$Method;
  private static final MethodProxy CGLIB$finalize$1$Proxy;
  private static final Method CGLIB$equals$2$Method;
  private static final MethodProxy CGLIB$equals$2$Proxy;
  private static final Method CGLIB$toString$3$Method;
  private static final MethodProxy CGLIB$toString$3$Proxy;
  private static final Method CGLIB$hashCode$4$Method;
  private static final MethodProxy CGLIB$hashCode$4$Proxy;
  private static final Method CGLIB$clone$5$Method;
  private static final MethodProxy CGLIB$clone$5$Proxy;

  static void CGLIB$STATICHOOK1()
  {
    CGLIB$THREAD_CALLBACKS = new ThreadLocal();
    CGLIB$emptyArgs = new Object[0];
    Class localClass1 = Class.forName("com.lww.learnjdk.CGlibProxy.SomeClass$$EnhancerByCGLIB$$84389373");
    Class localClass2;
    Method[] tmp95_92 = ReflectUtils.findMethods(new String[] { "finalize", "()V", "equals", "(Ljava/lang/Object;)Z", "toString", "()Ljava/lang/String;", "hashCode", "()I", "clone", "()Ljava/lang/Object;" }, (localClass2 = Class.forName("java.lang.Object")).getDeclaredMethods());
    CGLIB$finalize$1$Method = tmp95_92[0];
    CGLIB$finalize$1$Proxy = MethodProxy.create(localClass2, localClass1, "()V", "finalize", "CGLIB$finalize$1");
    Method[] tmp115_95 = tmp95_92;
    CGLIB$equals$2$Method = tmp115_95[1];
    CGLIB$equals$2$Proxy = MethodProxy.create(localClass2, localClass1, "(Ljava/lang/Object;)Z", "equals", "CGLIB$equals$2");
    Method[] tmp135_115 = tmp115_95;
    CGLIB$toString$3$Method = tmp135_115[2];
    CGLIB$toString$3$Proxy = MethodProxy.create(localClass2, localClass1, "()Ljava/lang/String;", "toString", "CGLIB$toString$3");
    Method[] tmp155_135 = tmp135_115;
    CGLIB$hashCode$4$Method = tmp155_135[3];
    CGLIB$hashCode$4$Proxy = MethodProxy.create(localClass2, localClass1, "()I", "hashCode", "CGLIB$hashCode$4");
    Method[] tmp175_155 = tmp155_135;
    CGLIB$clone$5$Method = tmp175_155[4];
    CGLIB$clone$5$Proxy = MethodProxy.create(localClass2, localClass1, "()Ljava/lang/Object;", "clone", "CGLIB$clone$5");
    tmp175_155;
    Method[] tmp223_220 = ReflectUtils.findMethods(new String[] { "doSomething", "()V" }, (localClass2 = Class.forName("com.lww.learnjdk.CGlibProxy.SomeClass")).getDeclaredMethods());
    CGLIB$doSomething$0$Method = tmp223_220[0];
    CGLIB$doSomething$0$Proxy = MethodProxy.create(localClass2, localClass1, "()V", "doSomething", "CGLIB$doSomething$0");
    tmp223_220;
    return;
  }
  //调用父类方法
  //在后面会用到
  //千万要记得这个方法
    final void CGLIB$doSomething$0() {
        super.doSomething();
    }   

    public final void doSomething() {
        MethodInterceptor cglib$CALLBACK_2;
        MethodInterceptor cglib$CALLBACK_0;
        if ((cglib$CALLBACK_0 = (cglib$CALLBACK_2 = this.CGLIB$CALLBACK_0)) == n
ull) {
            CGLIB$BIND_CALLBACKS(this);
            cglib$CALLBACK_2 = (cglib$CALLBACK_0 = this.CGLIB$CALLBACK_0);
        }
        if (cglib$CALLBACK_0 != null) {
        //调用你实现MethodInterceptor的intercept方法
            cglib$CALLBACK_2.intercept((Object)this, SomeClass$$EnhancerByCGLIB$
$84389373.CGLIB$doSomething$0$Method, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB
$emptyArgs, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$doSomething$0$Proxy);
            return;
        }
        super.doSomething();
    }

    final void CGLIB$finalize$1() throws Throwable {
        super.finalize();
    }

    protected final void finalize() throws Throwable {
        MethodInterceptor cglib$CALLBACK_2;
        MethodInterceptor cglib$CALLBACK_0;
        if ((cglib$CALLBACK_0 = (cglib$CALLBACK_2 = this.CGLIB$CALLBACK_0)) == n
ull) {
            CGLIB$BIND_CALLBACKS(this);
            cglib$CALLBACK_2 = (cglib$CALLBACK_0 = this.CGLIB$CALLBACK_0);
        }
        if (cglib$CALLBACK_0 != null) {
            cglib$CALLBACK_2.intercept((Object)this, SomeClass$$EnhancerByCGLIB$
$84389373.CGLIB$finalize$1$Method, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$em
ptyArgs, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$finalize$1$Proxy);
            return;
        }
        super.finalize();
    }

    final boolean CGLIB$equals$2(final Object o) {
        return super.equals(o);
    }

    public final boolean equals(final Object o) {
        MethodInterceptor cglib$CALLBACK_2;
        MethodInterceptor cglib$CALLBACK_0;
        if ((cglib$CALLBACK_0 = (cglib$CALLBACK_2 = this.CGLIB$CALLBACK_0)) == n
ull) {
            CGLIB$BIND_CALLBACKS(this);
            cglib$CALLBACK_2 = (cglib$CALLBACK_0 = this.CGLIB$CALLBACK_0);
        }
        if (cglib$CALLBACK_0 != null) {
            final Object intercept = cglib$CALLBACK_2.intercept((Object)this, So
meClass$$EnhancerByCGLIB$$84389373.CGLIB$equals$2$Method, new Object[] { o }, So
meClass$$EnhancerByCGLIB$$84389373.CGLIB$equals$2$Proxy);
            return intercept != null && (boolean)intercept;
        }
        return super.equals(o);
    }

    final String CGLIB$toString$3() {
        return super.toString();
    }

    public final String toString() {
        MethodInterceptor cglib$CALLBACK_2;
        MethodInterceptor cglib$CALLBACK_0;
        if ((cglib$CALLBACK_0 = (cglib$CALLBACK_2 = this.CGLIB$CALLBACK_0)) == n
ull) {
            CGLIB$BIND_CALLBACKS(this);
            cglib$CALLBACK_2 = (cglib$CALLBACK_0 = this.CGLIB$CALLBACK_0);
        }
        if (cglib$CALLBACK_0 != null) {
            return (String)cglib$CALLBACK_2.intercept((Object)this, SomeClass$$E
nhancerByCGLIB$$84389373.CGLIB$toString$3$Method, SomeClass$$EnhancerByCGLIB$$84
389373.CGLIB$emptyArgs, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$toString$3$Pr
oxy);
        }
        return super.toString();
    }

    final int CGLIB$hashCode$4() {
        return super.hashCode();
    }

    public final int hashCode() {
        MethodInterceptor cglib$CALLBACK_2;
        MethodInterceptor cglib$CALLBACK_0;
        if ((cglib$CALLBACK_0 = (cglib$CALLBACK_2 = this.CGLIB$CALLBACK_0)) == n
ull) {
            CGLIB$BIND_CALLBACKS(this);
            cglib$CALLBACK_2 = (cglib$CALLBACK_0 = this.CGLIB$CALLBACK_0);
        }
        if (cglib$CALLBACK_0 != null) {
            final Object intercept = cglib$CALLBACK_2.intercept((Object)this, So
meClass$$EnhancerByCGLIB$$84389373.CGLIB$hashCode$4$Method, SomeClass$$EnhancerB
yCGLIB$$84389373.CGLIB$emptyArgs, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$has
hCode$4$Proxy);
            return (intercept == null) ? 0 : ((Number)intercept).intValue();
        }
        return super.hashCode();
    }

    final Object CGLIB$clone$5() throws CloneNotSupportedException {
        return super.clone();
    }

    protected final Object clone() throws CloneNotSupportedException {
        MethodInterceptor cglib$CALLBACK_2;
        MethodInterceptor cglib$CALLBACK_0;
        if ((cglib$CALLBACK_0 = (cglib$CALLBACK_2 = this.CGLIB$CALLBACK_0)) == n
ull) {
            CGLIB$BIND_CALLBACKS(this);
            cglib$CALLBACK_2 = (cglib$CALLBACK_0 = this.CGLIB$CALLBACK_0);
        }
        if (cglib$CALLBACK_0 != null) {
            return cglib$CALLBACK_2.intercept((Object)this, SomeClass$$EnhancerB
yCGLIB$$84389373.CGLIB$clone$5$Method, SomeClass$$EnhancerByCGLIB$$84389373.CGLI
B$emptyArgs, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$clone$5$Proxy);
        }
        return super.clone();
    }

    public static MethodProxy CGLIB$findMethodProxy(final Signature signature) {

        final String string = signature.toString();
        switch (string.hashCode()) {
            case -1574182249: {
                if (string.equals("finalize()V")) {
                    return SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$finalize$1
$Proxy;
                }
                break;
            }
            case -508378822: {
                if (string.equals("clone()Ljava/lang/Object;")) {
                    return SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$clone$5$Pr
oxy;
                }
                break;
            }
            case 1826985398: {
                if (string.equals("equals(Ljava/lang/Object;)Z")) {
                    return SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$equals$2$P
roxy;
                }
                break;
            }
            case 1913648695: {
                if (string.equals("toString()Ljava/lang/String;")) {
                    return SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$toString$3
$Proxy;
                }
                break;
            }
            case 1984935277: {
                if (string.equals("hashCode()I")) {
                    return SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$hashCode$4
$Proxy;
                }
                break;
            }
            case 2121560294: {
                if (string.equals("doSomething()V")) {
                    return SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$doSomethin
g$0$Proxy;
                }
                break;
            }
        }
        return null;
    }

    public SomeClass$$EnhancerByCGLIB$$84389373() {
        CGLIB$BIND_CALLBACKS(this);
    }

    public static void CGLIB$SET_THREAD_CALLBACKS(final Callback[] array) {
        SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$THREAD_CALLBACKS.set(array);
    }

    public static void CGLIB$SET_STATIC_CALLBACKS(final Callback[] cglib$STATIC_
CALLBACKS) {
        CGLIB$STATIC_CALLBACKS = cglib$STATIC_CALLBACKS;
    }

    private static final void CGLIB$BIND_CALLBACKS(final Object o) {
        final SomeClass$$EnhancerByCGLIB$$84389373 someClass$$EnhancerByCGLIB$$8
4389373 = (SomeClass$$EnhancerByCGLIB$$84389373)o;
        if (!someClass$$EnhancerByCGLIB$$84389373.CGLIB$BOUND) {
            someClass$$EnhancerByCGLIB$$84389373.CGLIB$BOUND = true;
            Object o2;
            if ((o2 = SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$THREAD_CALLBACK
S.get()) != null || (o2 = SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$STATIC_CALL
BACKS) != null) {
                someClass$$EnhancerByCGLIB$$84389373.CGLIB$CALLBACK_0 = (MethodI
nterceptor)((Callback[])o2)[0];
            }
        }
    }

    public Object newInstance(final Callback[] array) {
        CGLIB$SET_THREAD_CALLBACKS(array);
        final SomeClass$$EnhancerByCGLIB$$84389373 someClass$$EnhancerByCGLIB$$8
4389373 = new SomeClass$$EnhancerByCGLIB$$84389373();
        CGLIB$SET_THREAD_CALLBACKS(null);
        return someClass$$EnhancerByCGLIB$$84389373;
    }

    public Object newInstance(final Callback callback) {
        CGLIB$SET_THREAD_CALLBACKS(new Callback[] { callback });
        final SomeClass$$EnhancerByCGLIB$$84389373 someClass$$EnhancerByCGLIB$$8
4389373 = new SomeClass$$EnhancerByCGLIB$$84389373();
        CGLIB$SET_THREAD_CALLBACKS(null);
        return someClass$$EnhancerByCGLIB$$84389373;
    }

    public Object newInstance(final Class[] array, final Object[] array2, final
Callback[] array3) {
        CGLIB$SET_THREAD_CALLBACKS(array3);
        switch (array.length) {
            case 0: {
                final SomeClass$$EnhancerByCGLIB$$84389373 someClass$$EnhancerBy
CGLIB$$84389373 = new SomeClass$$EnhancerByCGLIB$$84389373();
                CGLIB$SET_THREAD_CALLBACKS(null);
                return someClass$$EnhancerByCGLIB$$84389373;
            }
            default: {
                throw new IllegalArgumentException("Constructor not found");
            }
        }
    }

    public Callback getCallback(final int n) {
        CGLIB$BIND_CALLBACKS(this);
        Object cglib$CALLBACK_0 = null;
        switch (n) {
            case 0: {
                cglib$CALLBACK_0 = this.CGLIB$CALLBACK_0;
                break;
            }
            default: {
                cglib$CALLBACK_0 = null;
                break;
            }
        }
        return (Callback)cglib$CALLBACK_0;
    }

    public void setCallback(final int n, final Callback callback) {
        switch (n) {
            case 0: {
                this.CGLIB$CALLBACK_0 = (MethodInterceptor)callback;
                break;
            }
        }
    }

    public Callback[] getCallbacks() {
        CGLIB$BIND_CALLBACKS(this);
        return new Callback[] { this.CGLIB$CALLBACK_0 };
    }

    public void setCallbacks(final Callback[] array) {
        this.CGLIB$CALLBACK_0 = (MethodInterceptor)array[0];
    }

    static {
        CGLIB$STATICHOOK1();
    }
}

3 两种方式解析

前面已经知道怎么实现,看了完整的源码。现在看怎么实现以及调用过程

3.1 CGlib代理解析

1、创建
在TestCGlib调用CGlibProxy的getInstance方法

        SomeClass businessObject = (SomeClass) cglib.getInstance(new SomeClass());

CGlibProxy的getInstance方法

    public Object getInstance(Object target) {
        this.target = target;
        Enhancer enhancer = new Enhancer();
        //设置父类
        enhancer.setSuperclass(this.target.getClass());
        //用来生成的代理类回调intercept()方法
        //在生成的代理类源码有判断
        enhancer.setCallback(this);
        //主要
        return enhancer.create();
    }

Enhancer的create方法

    public Object create() {
        this.classOnly = false;
        this.argumentTypes = null;
        return this.createHelper();
    }

Enhancer的createHelper方法

    private Object createHelper() {
        this.validate();
        if(this.superclass != null) {
            this.setNamePrefix(this.superclass.getName());
        } else if(this.interfaces != null) {
            this.setNamePrefix(this.interfaces[ReflectUtils.findPackageProtected(this.interfaces)].getName());
        }
        //调用父类AbstractClassGenerator生成代理类
        return super.create(KEY_FACTORY.newInstance(this.superclass != null?this.superclass.getName():null, ReflectUtils.getNames(this.interfaces), this.filter, this.callbackTypes, this.useFactory, this.interceptDuringConstruction, this.serialVersionUID));
    }

具体怎么生成我也看不太懂<.-.>
2、调用
在TestCGlib中

//此处businessObject已经是代理类了
businessObject.doSomething();

代理类的doSomething方法查看源码

    public final void doSomething() {
        MethodInterceptor cglib$CALLBACK_2;
        MethodInterceptor cglib$CALLBACK_0;
        if ((cglib$CALLBACK_0 = (cglib$CALLBACK_2 = this.CGLIB$CALLBACK_0)) == n
ull) {
            CGLIB$BIND_CALLBACKS(this);
            cglib$CALLBACK_2 = (cglib$CALLBACK_0 = this.CGLIB$CALLBACK_0);
        }
        if (cglib$CALLBACK_0 != null) {
        //调用CGlibProxy的intercept方法
        //参数1、代理对象;2、委托类方法;3、方法参数;4、代理方法的MethodProxy对象。
            cglib$CALLBACK_2.intercept((Object)this, SomeClass$$EnhancerByCGLIB$
$84389373.CGLIB$doSomething$0$Method, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB
$emptyArgs, SomeClass$$EnhancerByCGLIB$$84389373.CGLIB$doSomething$0$Proxy);
            return;
        }
        super.doSomething();
    }

CGlibProxy的intercept方法

    @Override
    public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
    //这里只是调用输出的前后消息并没有执行被调类的方法
        System.out.println("..........before..........");
        //进入这个函数
        proxy.invokeSuper(obj, args);
        System.out.println("..........after ..........");
        return null;
    }

MethodProxy的invokeSuper方法

//这里面就是关键
    public Object invokeSuper(Object obj, Object[] args) throws Throwable {
        try {
            this.init();
            MethodProxy.FastClassInfo fci = this.fastClassInfo;
            //f2是由CGlib生成的在输出的class中有
            //SomeClass$$EnhancerByCGLIB$$831e1f52$$FastClassByCGLIB$$513605b2.class
            return fci.f2.invoke(fci.i2, obj, args);
        } catch (InvocationTargetException var4) {
            throw var4.getTargetException();
        }
    }

查看f2.invoke方法

    public Object invoke(final int n, final Object o, final Object[] array) thro
ws InvocationTargetException {
        final SomeClass$$EnhancerByCGLIB$$831e1f52 someClass$$EnhancerByCGLIB$$8
31e1f52 = (SomeClass$$EnhancerByCGLIB$$831e1f52)o;
        try {
            switch (n) {
                case 0: {
                    return new Boolean(someClass$$EnhancerByCGLIB$$831e1f52.equa
ls(array[0]));
                }
                case 1: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.toString();
                }
                case 2: {
                    return new Integer(someClass$$EnhancerByCGLIB$$831e1f52.hash
Code());
                }
                case 3: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.newInstance((Cla
ss[])array[0], (Object[])array[1], (Callback[])array[2]);
                }
                case 4: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.newInstance((Cal
lback)array[0]);
                }
                case 5: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.newInstance((Cal
lback[])array[0]);
                }
                case 6: {
                    someClass$$EnhancerByCGLIB$$831e1f52.setCallbacks((Callback[
])array[0]);
                    return null;
                }
                case 7: {
                    someClass$$EnhancerByCGLIB$$831e1f52.setCallback(((Number)ar
ray[0]).intValue(), (Callback)array[1]);
                    return null;
                }
                case 8: {
                    someClass$$EnhancerByCGLIB$$831e1f52.doSomething();
                    return null;
                }
                case 9: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.getCallback(((Nu
mber)array[0]).intValue());
                }
                case 10: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.getCallbacks();
                }
                case 11: {
                    SomeClass$$EnhancerByCGLIB$$831e1f52.CGLIB$SET_STATIC_CALLBA
CKS((Callback[])array[0]);
                    return null;
                }
                case 12: {
                    SomeClass$$EnhancerByCGLIB$$831e1f52.CGLIB$SET_THREAD_CALLBA
CKS((Callback[])array[0]);
                    return null;
                }
                case 13: {
                    return new Boolean(someClass$$EnhancerByCGLIB$$831e1f52.CGLI
B$equals$2(array[0]));
                }
                case 14: {
                    someClass$$EnhancerByCGLIB$$831e1f52.CGLIB$finalize$1();
                    return null;
                }
                case 15: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.CGLIB$toString$3
();
                }
                case 16: {
                    return new Integer(someClass$$EnhancerByCGLIB$$831e1f52.CGLI
B$hashCode$4());
                }
                case 17: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.CGLIB$clone$5();

                }
                case 18: {
                    return SomeClass$$EnhancerByCGLIB$$831e1f52.CGLIB$findMethod
Proxy((Signature)array[0]);
                }
                case 19: {
                    SomeClass$$EnhancerByCGLIB$$831e1f52.CGLIB$STATICHOOK1();
                    return null;
                }
                case 20: {
                //看到这doSomething$0方法是不是很惊喜。没错就是调用父类doSomething。
                //前面的一串someClass$$EnhancerByCGLIB$$831e1f52是CGlib生成的代理类
                //那么会不会走这个方法呢。我们调试就知道了,记住case 20!!!
                    someClass$$EnhancerByCGLIB$$831e1f52.CGLIB$doSomething$0();
                    return null;
                }
                case 21: {
                    someClass$$EnhancerByCGLIB$$831e1f52.wait();
                    return null;
                }
                case 22: {
                    someClass$$EnhancerByCGLIB$$831e1f52.wait(((Number)array[0])
.longValue(), ((Number)array[1]).intValue());
                    return null;
                }
                case 23: {
                    someClass$$EnhancerByCGLIB$$831e1f52.wait(((Number)array[0])
.longValue());
                    return null;
                }
                case 24: {
                    return someClass$$EnhancerByCGLIB$$831e1f52.getClass();
                }
                case 25: {
                    someClass$$EnhancerByCGLIB$$831e1f52.notify();
                    return null;
                }
                case 26: {
                    someClass$$EnhancerByCGLIB$$831e1f52.notifyAll();
                    return null;
                }
            }
        }
        catch (Throwable t) {
            throw new InvocationTargetException(t);
        }
        throw new IllegalArgumentException("Cannot find matching method/construc
tor");
    }

惊喜
我们看到直接就是20。
进入case 20调用父类的方法,然后就返回到CGlibProxy的intercept方法,因为还有最后一句after没有输出啊!

    @Override
    public Object intercept(Object obj, Method method, Object[] args, MethodProxy proxy) throws Throwable {
        System.out.println("..........before..........");
        proxy.invokeSuper(obj, args);
        System.out.println("..........after ..........");
        return null;
    }

最后就结束了!

3.2 JDK动态代理解析

1、生成代理类
TestJDKProxy

        // 实例化目标对象
        Service userService = new ServiceImpl();
        // 实例化InvocationHandler
        JDKInvocationHandler invocationHandler = new JDKInvocationHandler(userService);
        // 根据目标对象生成代理对象
        Service proxy = (Service) invocationHandler.getProxy();

跟入getProxy方法(JDKInvocationHandler类)

    public Object getProxy() {
        return Proxy.newProxyInstance(Thread.currentThread().getContextClassLoader(),
                target.getClass().getInterfaces(), this);
    }

生成部分还是等我看懂了,再来补充吧
2、调用
TestJDKProxy中

    // 已经是代理类了
        // 调用代理对象的方法
        proxy.say();

查看代理类

  public final void say()
    throws 
  {
    try
    {
      this.h.invoke(this, m3, null);
      return;
    }
    catch (Error|RuntimeException localError)
    {
      throw localError;
    }
    catch (Throwable localThrowable)
    {
      throw new UndeclaredThrowableException(localThrowable);
    }
  }
//在静态方法执行的。
m3 = Class.forName("com.lww.learnjdk.JDKProxy.Service").getMethod("say", new Class[0]);

回到JDKInvocationHandler类查看invoke方法

    @Override
    public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
        System.out.println("------------------before------------------");
        Object result = method.invoke(target, args);
        System.out.println("-------------------after------------------");

        return result;
    }

Method的invoke方法
到这再往下就是java反射(方法)的源码了

    public Object invoke(Object obj, Object... args)
        throws IllegalAccessException, IllegalArgumentException,
           InvocationTargetException
    {
        if (!override) {
            if (!Reflection.quickCheckMemberAccess(clazz, modifiers)) {
                Class<?> caller = Reflection.getCallerClass();
                checkAccess(caller, clazz, obj, modifiers);
            }
        }
        MethodAccessor ma = methodAccessor;             // read volatile
        if (ma == null) {
            ma = acquireMethodAccessor();
        }
        //执行这句
        return ma.invoke(obj, args);
    }

MethodAccessor 类继承结构图
继承图
具体执行方法是 DelegatingMethodAccessorImpl

    private MethodAccessorImpl delegate;

    public Object invoke(Object var1, Object[] var2) throws IllegalArgumentException, InvocationTargetException {
        return this.delegate.invoke(var1, var2);
    }

NativeMethodAccessorImpl的invoke方法

    public Object invoke(Object var1, Object[] var2) throws IllegalArgumentException, InvocationTargetException {
        if(++this.numInvocations > ReflectionFactory.inflationThreshold() && !ReflectUtil.isVMAnonymousClass(this.method.getDeclaringClass())) {
            MethodAccessorImpl var3 = (MethodAccessorImpl)(new MethodAccessorGenerator()).generateMethod(this.method.getDeclaringClass(), this.method.getName(), this.method.getParameterTypes(), this.method.getReturnType(), this.method.getExceptionTypes(), this.method.getModifiers());
            this.parent.setDelegate(var3);
        }
        //调用本地方法
        return invoke0(this.method, var1, var2);
    }
    //本地方法执行方法
        private static native Object invoke0(Method var0, Object var1, Object[] var2);

调用ServiceImpl的say方法

    @Override
    public void say() {
        System.out.println("Hello JDK");
    }

4 总结

4.1 JDK动态代理

1、生成代理类快,因为方法调用交给Java反射做了
2、只能面向接口,因为代理类默认继承Proxy类
3、不需要其他jar包

4.2 CGlib动态代理

优点:
1、执行速度快,因为CGlib生成代理类的时候会将被代理类的方法进行编号,直接传入编号就调用了。
2、可以为没有接口的类进行动态代理
劣势:
1、就因为它要编号所以它生成代理类的速度比较慢。尤其是需要多次生成代理类的时候。
2、因为是继承关系所以如果父类的final方法它就无能为力了

5 补充

参考资料:
http://blog.csdn.net/tiandesheng111/article/details/39833901
http://www.cnblogs.com/chinajava/p/5880870.html
http://www.cnblogs.com/chinajava/p/5880887.html

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值