抽丝剥茧——代理设计模式执墨人

这个就是静态代理,兄弟们应该已经发现了它的缺点,只能指定自己想要进行代理的类,而不能对所有的类进行代理,扩展性太差,所以引出了动态代理

谈到动态代理,脑子里第一个出现的肯定就是Java动态代理了。我们先来聊一下Java动态代理。

先来看一个动态代理的案例

NaiKenaiKe=newNaiKe();Shoesshoes=(Shoes)Proxy.newProxyInstance(NaiKe.class.getClassLoader(),newClass[]{Shoes.class},newInvocationHandler(){@OverridepublicObjectinvoke(Objectproxy,Methodmethod,Object[]args)throwsThrowable{System.out.println("begintimer:"+System.currentTimeMillis());method.invoke(naiKe,args);System.out.println("aftertimer:"+System.currentTimeMillis());returnnull;}});shoes.run();我们看一下动态代理的源码。

我们可以通过以下方式让JVM将动态生成的代理类保存到我们的项目中

生成的代理类如下:

finalclass$Proxy0extendsProxyimplementsShoes{privatestaticMethodm1;privatestaticMethodm3;privatestaticMethodm2;privatestaticMethodm0;public$Proxy0(InvocationHandlervar1)throws{super(var1);}publicfinalbooleanequals(Objectvar1)throws{}publicfinalvoidrun()throws{try{super.h.invoke(this,m3,(Object[])null);}catch(RuntimeException|Errorvar2){throwvar2;}catch(Throwablevar3){thrownewUndeclaredThrowableException(var3);}}publicfinalStringtoString()throws{}publicfinalinthashCode()throws{}static{try{m1=Class.forName("java.lang.Object").getMethod("equals",Class.forName("java.lang.Object"));m3=Class.forName("desgin.proxy.Shoes").getMethod("run");m2=Class.forName("java.lang.Object").getMethod("toString");m0=Class.forName("java.lang.Object").getMethod("hashCode");}catch(NoSuchMethodExceptionvar2){thrownewNoSuchMethodError(var2.getMessage());}catch(ClassNotFoundExceptionvar3){thrownewNoClassDefFoundError(var3.getMessage());}}}从这个类的结构中,我们可以看出很多的东西

上面两个也是动态代理的原理了。我们来仔细看一下我们的run()方法,也就是我们代理对象要实现的接口

publicfinalvoidrun()throws{try{super.h.invoke(this,m3,(Object[])null);}catch(RuntimeException|Errorvar2){throwvar2;}catch(Throwablevar3){thrownewUndeclaredThrowableException(var3);}}这个就是动态代理的全部实现过程

还有一个非常牛逼的点,它怎么生成的这个代理类。来看一下代理的全过程

图中的ASM就是为我们动态生成一个代理类的工具,它直接操作了Class字节码的二进制,然后创建了一个代理类,返回给我们。

Java动态代理就聊到这里了。下面看一看CGLIb和AOP

弥补了Java动态代理的不足,CGLIB动态代理可以代理类。它直接创建了一个被代理对象的子类,实现了对其的代理过程。我们来看一下它的代理过程

//打印生成的代理对象,放置于当前项目下System.setProperty(DebuggingClassWriter.DEBUG_LOCATION_PROPERTY,".");//创建Enhancer对象,类似于JDK动态代理的Proxy类,下一步就是设置几个参数Enhancerenhancer=newEnhancer();//设置目标类的字节码文件enhancer.setSuperclass(Tank.class);//设置回调函数enhancer.setCallback(newMethodInterceptor(){@OverridepublicObjectintercept(Objecto,Methodmethod,Object[]objects,MethodProxymethodProxy)throwsThrowable{methodProxy.invokeSuper(o,objects);returnnull;}});//这里的creat方法就是正式创建代理类TankproxyDog=(Tank)enhancer.create();//调用代理类的eat方法proxyDog.tank();还是和Java动态代理相似,传入一个需要代理的Class,设置代理的回调函数。然后调用create创建一个代理对象,调用代理对象的方法。

代理第一行可以输出代理对象,会生成三个代理对象。

查看中间那个,可以看到我们被代理对象的方法

publicclassTank$$EnhancerByCGLIB$$a4ec679aextendsTankimplementsFactory{//构造方法publicTank$$EnhancerByCGLIB$$a4ec679a(){CGLIB$BIND_CALLBACKS(this);}//被代理方法finalvoidtank(){MethodInterceptorvar10000=this.CGLIB$CALLBACK_0;if(var10000==null){CGLIB$BIND_CALLBACKS(this);var10000=this.CGLIB$CALLBACK_0;}if(var10000!=null){//调用增强的方法var10000.intercept(this,CGLIB$tank$0$Method,CGLIB$emptyArgs,CGLIB$tank$0$Proxy);}else{super.tank();}}}在之前的CGLIB动态代理实现中,我们看到了拦截的回调中传入了四个参数,从上面的源码中可以看到对应参数的作用。

我们可以看一下superinvoke的源码

publicObjectinvokeSuper(Objectobj,Object[]args)throwsThrowable{try{this.init();MethodProxy.FastClassInfofci=this.fastClassInfo;returnfci.f2.invoke(fci.i2,obj,args);}catch(InvocationTargetExceptionvar4){throwvar4.getTargetException();}}privatestaticclassFastClassInfo{FastClassf1;FastClassf2;inti1;inti2;privateFastClassInfo(){}}一个图理解CgLib动态代理过程

写了这么多,感觉对于代理设计模式讲解的篇幅不是很大,而是着重讲解了动态代理的实现方式。总的而言,代理设计模式与我们日常生活非常的接近,生活中的事物几乎都在被代理,所以这个设计模式应该很好懂,所以着重讲解了动态代理的实现方式。

THE END
1.专业的天猫代运营公司是如何运营保健品的呢?电商平台天猫代运营公司运营保健品的过程是一个综合性的策略实施过程,旨在帮助保健品品牌在天猫平台上实现高效运营和市场拓展。以下是具体的运营步骤和策略: 一、注册与开店 代运营公司首先会在天猫平台上为保健品品牌注册一个店铺,并完成相关的开店流程。 提交保健品品牌的相关资质证明,如企业的营业执照、产品资质证明(保健食品https://www.163.com/dy/article/JINDFP0H05568LAH.html
2.如何做好一个品牌代理商ppt模板如何做好一个品牌代理商ppt模板由专业的PPT模板网站当图网提供,免费如何做好一个品牌代理商ppt模板下载,如何做好一个品牌代理商ppt模板免费下载,更多精美PPT模板,尽在当图网。https://www.99ppt.com/P_540331.html
3.如何选择一个好的除甲醛品牌加盟?2019邀您“免费”加盟心呼吸如何选择一个好的除甲醛品牌加盟? 清工集团从事化工环保行业30余年之久,对环保领域有充足的实践经验。心呼吸是天津箐润环保科技发展有限公司旗下空气净化、除甲醛、去异味产品品牌。 公司与日本公司、中国疾控、中国科学院、香港科学院、天津大学等知名企业、学校和机构密切合作,系统从事生物酶净化技术及相关室内空气净化https://www.qingrunkj.com/news/119.html
4.度小满收款码怎么代理,个人怎么代理度小满收银机构?度小满作为一款先进的金融科技产品,其收款码功能不仅具备高效、便捷的支付特性,还为代理商提供了广阔的市场空间和盈利机会。以下将详细介绍如何成为度小满收款码的代理商,以及个人如何代理度小满收银机构。 一、度小满收款码代理流程 1.了解品牌与产品:首先,对度小满品牌及其收款码产品进行全面了解。这包括度小满的发展历程、https://www.jianshu.com/p/9cd0ce38cf67
5.散白酒代理加盟创业并非易事,如果不想自己的血汗钱打水漂,选择一个有利可图的品牌加盟尤其重要,散白酒代理就是这样的一个品牌。 目前散白酒代理品牌是白酒行业中较为受欢迎的一个品牌,从创立起就依靠着优质的产品和贴心的服务收获了消费者的一致好评,市场口碑极好。经过多年的坚持与努力,如今散白酒代理已经在全国拓展了多家加盟https://www.jiamengfei.com/xm/128862
6.解读标杆:自然堂全国第一代理商是这样炼成的专栏CBO众所周知,在2013年以前,上海伽蓝集团旗下自然堂品牌的全国冠军代理商一直是长沙兆顺百货公司,但这一现状在2014年却发生了戏剧性的变化。那就是,作为自然堂综合排名全国前五位的深圳茂华公司后来者居上,一举摘得了自然堂全国代理商销售回款第一的桂冠。 深圳市茂华实业有限公司总经理胡向东一直是个低调的人。在谈到茂华公https://www.cbo.cn/article/id/29647.html
7.雨果跨境一个商圈,两种形态,恰如广州美妆的过去与现在。 凌政和·4小时前 广州产业带凌政和 遭遇TRO,怎么收集证据有效降低和解金? 在跨境电商的征途中,卖家们难免会遇到各种挑战,其中TRO(临时限制令)无疑是最为棘手的一种。 老蔡聊美国和解与应诉·昨天 19:59 https://www.cifnews.com/
8.我给“蜜雪冰城”留了个电话,结果引来了半个奶茶界一位业内人士告诉盒饭财经,这样的公司并不常见,可能公司是空壳,也可能是同一个代理记账公司,空壳可能性更大。 03 加盟反噬 蜜雪冰城围绕在“假”上的相关消息,并不少。 我们在检索时发现,除了公主茶妆套上蜜雪冰城的牌子之外,何必问、猫小森等品牌也曾被网友称是蜜雪冰城旗下的品牌。 https://36kr.com/p/1281630265880576.html