代理模式
定义:
为其他对象提供一种代理,以控制对这个对象的访问
代理对象在客户端和目标对象之间起到中介的作用
适用场景:
保护目标对象
增强目标对象
优点:
代理模式能将代理对象与真实被调用的目标对象分离
一定程度上降低了系统的耦合度
保护目标对象
增强目标对象
缺点:
代理模式会造成系统设计中类的数目增加
在客户端和目标对象增加一个代理对象,会造成请求处理速度变慢
增加系统的复杂度
扩展:
静态代理
动态代理
CGlib代理
spring中的扩展:
当Bean有实现接口时,Spring就会用JDK的动态代理
当Bean没有实现接口时,Spring使用CGlib
可以强制使用CGlib
在Spring配置中加入<aop:aspectj-autoproxy proxy-target-class="true" />
相关设计模式:
代理模式和装饰者模式
代理模式和适配器模式
coding:
静态代理:
创建Order类
创建IOrderService接口
创建IOrderDao
创建OrderDaoImpl类实现IOrderDao接口
创建OrderServiceImpl类,实现IOrderService接口
创建OrderServiceStaticProxy来增加IOrderService。
方法的具体增强
创建DynamicDataSource
创建DataSourceContextHolder类
回到DynamicDataSource类
回到OrderServiceStaticProxy
对于dbTouter是用于分库分表的,也就是常说的路由算法,进入到下面那个设置dataSource。也就是大家常用的分库分表。
在进行一次修改,将方法具体的分离开来
上面的dbTouter只有两个值0、1对应下面的db0和db1数据库
创建Test类
运行:
当前UML类图
动态代理
创建OrderServiceDynamicProxy类
编写beforeMethod方法
编写afterMethod方法
编写invoke方法
创建Test类
运行:
debug来跑一下:
此处是动态代理的核心
这里面进行了安全检查
进入到getProxyClass0()方法中 ,当有缓存就直接返回
进入proxyClassCache.get()方法中
如果上面的if没有返回执行下面的程序:
返回继续执行,新的对象是通过反射的方式创建的
往下继续走:
结果:
Spring中的应用
ProxyFactoryBean类
核心方法getObject()方法
类JdkDynamicAopProxy
在mybatis中的应用:
MapperProxyFactory类