多图详解Spring框架

  Spring中AOP特性详解

  动态代理的实现原理

  要了解Spring的AOP就必须先了解的动态代理的原理,因为AOP就是基于动态代理实现的。动态代理还要从JDK本身说起。

  在Jdk的java.lang.reflect包下有个Proxy类,它正是构造代理类的入口。这个类的结构入下:

物联网

  图16.Proxy类结构

  从上图发现最后面四个是公有方法。而最后一个方法newProxyInstance就是创建代理对象的方法。这个方法的源码如下:

  清单6.Proxy.newProxyInstance

  public static Object newProxyInstance(ClassLoader loader,

  Class> [] interfaces,

  InvocationHandler h)

  throws IllegalArgumentException {

  if (h == null) {

  throw new NullPointerException();

  }

  Class cl = getProxyClass (loader, interfaces);

  try {

  Constructor cons = cl.getConstructor(constructorParams);

  return (Object) cons.newInstance(new Object[] { h });

  } catch (NoSuchMethodException e) {

  throw new InternalError(e.toString());

  } catch (IllegalAccessException e) {

  throw new InternalError(e.toString());

  } catch (InstantiationException e) {

  throw new InternalError(e.toString());

  } catch (InvocationTargetException e) {

  throw new InternalError(e.toString());

  }

  } !

  这个方法需要三个参数:ClassLoader,用于加载代理类的Loader类,通常这个Loader和被代理的类是同一个Loader类。Interfaces,是要被代理的那些那些接口。InvocationHandler,就是用于执行 除了被代理接口中方法之外的用户自定义的操作,他也是用户需要代理的最终目的。用户调用目标方法都被代理到InvocationHandler类中定义的唯一方法invoke中。这在后面再详解。

  下面还是看看Proxy如何产生代理类的过程,他构造出来的代理类到底是什么样子?下面揭晓啦。

物联网

  图17.创建代理对象时序图

  其实从上图中可以发现正在构造代理类的是在ProxyGenerator的generateProxyClass的方法中。ProxyGenerator类在sun.misc包下,感兴趣的话可以看看他的源码。

  假如有这样一个接口,如下:

  清单7.SimpleProxy类

  public interface SimpleProxy {

  public void simpleMethod1();

  public void simpleMethod2();

  }

  代理来生成的类结构如下:

  清单 8.$Proxy2类

  public class $Proxy2 extends java.lang.reflect.Proxy implements SimpleProxy{

  java.lang.reflect.Method m0;

  java.lang.reflect.Method m1;

  java.lang.reflect.Method m2;

  java.lang.reflect.Method m3;

  java.lang.reflect.Method m4;

  int hashCode();

  boolean equals(java.lang.Object);

  java.lang.String toString();

  void simpleMethod1();

  void simpleMethod2();

  }

  这个类中的方法里面将会是调用InvocationHandler的invoke方法,而每个方法也将对应一个属性变量,这个属性变量m也将传给invoke方法中的Method参数。整个代理就是这样实现的。

  SpringAOP如何实现

  从前面代理的原理我们知道,代理的目的是调用目标方法时我们可以转而执行InvocationHandler类的invoke方法,所以如何在InvocationHandler上做文章就是Spring实现Aop的关键所在。

  Spring的Aop实现是遵守Aop联盟的约定。同时Spring又扩展了它,增加了如Pointcut、Advisor等一些接口使得更加灵活。

  下面是Jdk动态代理的类图:

物联网

  图18.Jdk动态代理的类图

  上图清楚的显示了Spring引用了Aop Alliance定义的接口。姑且不讨论Spring如何扩展Aop Alliance,先看看Spring如何实现代理类的,要实现代理类在Spring的配置文件中通常是这样定一个Bean的 ,如下:

  清单9.配置代理类Bean

  

  class="org.springframework.aop.framework.ProxyFactoryBean">

  

  

  org.springframework.aop.framework.PrototypeTargetTests$TestBean

  value>

  property>

  ref> property>