(八)DI 和 IOC 概念
依赖注入或控制反转的定义中,调用者不负责被调用者的实例创建工作,该工作由Spring框架中的容器来负责,它通过开发者的配置来判断实例类型,创建后再注入调用者。由于Spring容器负责被调用者实例,实例创建后又负责将该实例注入调用者,因此称为依赖注入。而被调用者的实例创建工作不再由调用者来创建而是由Spring来创建,控制权由应用代码转移到了外部容器,控制权发生了反转,因此称为控制反转。
(九)AOP代理对象
如以下代码:
当我们调用其它方法的时候,我们需要对user进行判断,看是否存在,如果存在,则执行,如果不存在则不执行update,save等方法。
问题:如果每个方法都进行判断,则代码繁琐,可在方法调用前进行统一的判断,如果user存在则调用update,save等方法,这种统一的判断可称为拦截业务方法,使用代理技术:
为目标对象创建代理对象的过程如下:
- 创建一个代理工厂类,它实现InvocationHandler的接口,其成员变量为目标对象
- 在代理工厂类中创建代理实例方法,public Object creatPorxyIntance(Object targetObject){},参数为代理对象,此参数赋值给成员变量,使用Proxy代理类的静态方法newProxyInstance()实现代理对象过程的创建。
- 重写回调函数,先将目标对象强制转换,再增加判断条件调用相应的方法,如下图所示。
- 进行测试
测试代码如下:
(十)CGLIB实现AOP代理对象
在上面的代码中目标对象PersonServiceBeanAOP是实现了PersonService接口,然后代理对象CGLIBProxyFactory通过实现MethodInterceptor接口来实现回调,如果目标对象没有实现PersonService接口,而只是一个普通的Bean类将怎么来实现代理呢?
使用CGLIB方法:
- 编写PersonServiceBeanCGLIB目录对象类,不需要实现接口
- 编写代理对象类CGLIBProxyFactory,它需要实现接口MethodInterceptor以便实现方法的调用
- CGLIBProxyFactory中编写为目标对象创建代理对象的方法public Object creatPorxyIntance(Object targetObject),在此方法中设置PersonServiceBeanCGLIB为代理的父类,且使用此类进行回调,如下图所示。
- CGLIBProxyFactory中重写回调函数,此方法是重写的接口的方法,当调用PersonServiceBeanCGLIB的方法时,会通过此方法进行调用,代码如下:
- 测试
(十一)AOP原理
要spring框架中,实现AOP的代理方法就是8、9两种方法,当目标对象业务bean有实现接口方法时,使用AOP代理,当业务Bean没有实现接口时,会合适CGLIB方法来创建代理对象。此过程的判断及调用及由spring框架来实现。