تنفيذ الوكيل الديناميكي
الوضع المستخدم: وضع الوكيل.
تتمثل وظيفة وضع الوكيل في توفير وكيل للكائنات الأخرى للتحكم في الوصول إلى هذا الكائن. على غرار وكالة تأجير.
بروكسي ديناميكيان:
(1) الوكيل الديناميكي JDK. يتم تنفيذ الوكيل الديناميكي JDK بواسطة آلية الانعكاس داخل Java. تعتمد الفئة المستهدفة على واجهة موحدة (InvOckOndler)
(2) يتم تنفيذ الوكيل الديناميكي CGLIB ، والطبقة الأساسية من الوكيل الديناميكي CGLIB بمساعدة ASM. يتم استخدام الوكيل الديناميكي الذي تنفذه مكتبة الطرف الثالث مثل CGLIB على نطاق أوسع ولديه المزيد من المزايا في الكفاءة.
إطار التطبيق الرئيسي:
AOP في الربيع ، اعتراض في دعامات 2
تطبيق محدد:
1. تحديد الواجهات وتنفيذ الفصول
package com.example.service ؛ public interface uservice {public string getName (int id) ؛ عدد صحيح عام getage (int id) ؛} package com.example.service.impl ؛ import com.example.service.userservice ؛ public class userviceImpl تنفذ المستخدمين {public string getName (int id) {system.out.println ("------ getName -----") ؛ إرجاع "القط" ؛ } integer getage (int id) {system.out.println ("------ getage -----") ؛ العودة 10 ؛ }}2. تنفيذ الوكيل الديناميكي JDK
package com.example.jdk ؛ import java.lang.reflect.invocationHandler ؛ import java.lang.reflect.method ؛ import java.lang.reflect.proxy ؛ public myinvocationHandler تنفس invocationHandler {الهدف الخاص ؛ / ** * ربط كائن مندوب وإرجاع فئة وكيل * * param الهدف * @REGARN */ الكائن العام BIND (هدف الكائن) {this.target = target ؛ // احصل على كائن الوكيل proxy.newproxyinstance (target.getClass (). getClassloader () ، target.getClass (). getInterfaces () ، هذا) ؛ // لربط الواجهة (هذا عيب ، يعوض CGLIB لهذا العيب)} Override الكائن العام استدعاء (وكيل الكائن ، الطريقة ، الكائن [] args) يلقي رمي {if ("getName" .equals (method.getName ()))) {system.out.println ("--------- نتيجة الكائن = method.invoke (الهدف ، args) ؛ System.out.println ("------ بعد" + method.getName () + "------") ؛ نتيجة العودة } آخر {object result = method.invoke (الهدف ، args) ؛ نتيجة العودة }}} package com.example.jdk ؛ import com.example.service.userservice ؛ import com.example.service.impl.userserviceImpl ؛/*** test class*/public class runjdk {public static void main (string [] args) {myinvocationHandler proxy = new myinvocationHandler () ؛ UserService orperServiceProxy = (UserveserVice) proxy.bind (New UsperServiceImpl ()) ؛ System.out.println (userviceproxy.getName (1)) ؛ System.out.println (UserviceRviceProxy.getage (1)) ؛ }}نتائج التشغيل:
------ قبل getName ----
------ getName -----
------ بعد getName -----
قطة
----- getage -----
10
3. تنفيذ الوكيل الديناميكي CGLIB:
لا يمكن لآلية الوكيل الديناميكي لـ JDK الوكلاء فقط إلى الطبقات التي تنفذ واجهات ، لكن الفئات التي لا تستطيع تنفيذ واجهات لا يمكنها تنفيذ الوكيل الديناميكي لـ JDK. CGLIB ينفذ الوكيل للفصول. مبدأها هو إنشاء فئة فرعية للفئة المستهدفة المحددة والكتابة فوق تحسين تنفيذ الطريقة. ومع ذلك ، نظرًا لاستخدام الميراث ، لا يمكن أن يتم تصنيف التصنيف بواسطة النهائي.
الطبقات الأساسية من CGLIB:
net.sf.cglib.proxy.enhancer فئة التحسين الرئيسية
net.sf.cglib.proxy.MethodInterceptor تعترض الطريقة الرئيسية للفئة ، وهي واجهة فرعية لواجهة رد الاتصال وتتطلب تنفيذ المستخدم.
net.sf.cglib.proxy.methodproxy يمكن لفئة الوكيل من java.lang.reflect.method من JDK تنفيذ المكالمات بسهولة على أساليب كائن المصدر.
إن واجهة net.sf.cglib.proxy.methodinterceptor هي أكثر أنواع الاتصال العامة ، وغالبًا ما يتم استخدامها بواسطة AOP المستندة إلى الوكيل لتنفيذ مكالمات طريقة التقاطع. تحدد هذه الواجهة طريقة واحدة فقط
اعتراض الكائن العام (كائن كائن ، java.lang.reflect.method طريقة ،
Object [] args ، methodproxy proxy) رمي رمي ؛
المعلمة الأولى هي كائن الوكيل ، والمعلمات الثانية والثالثة هي الطريقة المعتادة ومعلمات الطريقة ، على التوالي. يمكن استدعاء الطريقة الأصلية باستخدام مكالمة انعكاس عامة باستخدام كائن java.lang.reflect.method ، أو باستخدام كائن net.sf.cglib.proxy.methodproxy. net.sf.cglib.proxy.methodproxy عادة ما يكون مفضلاً لأنه أسرع.
package com.example.cglib ؛ استيراد org.springframework.cglib.proxy.enhancer ؛ استيراد org.springframework.cglib.proxy.methodinterceptor تنفذ methodInterceptor {هدف الكائن الخاص ؛ / ** * إنشاء كائن بروكسي * * param الهدف * return */ كائن عام getInstance (الهدف الكائن) {this.target = target ؛ Enhancer Enhancer = New Enhancer () ؛ ensancer.SetSuperClass (this.target.getClass ()) ؛ // طريقة رد الاتصال المحسّن. // إنشاء proxy object return ensancer.create () ؛ } Override Public Object Intercept (Object O ، method ، Object [] Objects ، MethodProxy methodproxy) يلقي رمي {system.out.println ("++++++++ قبل"+methodproxy.getsuperName ()+"++++++") ؛ System.out.println (method.getName ()) ؛ نتيجة الكائن = methodproxy.invokesuper (O ، الكائنات) ؛ System.out.println ("++++++ بعد"+methodproxy.getSuperName ()+"++++++++") ؛ نتيجة العودة }} package com.example.cglib ؛ import com.example.service.userservice ؛ import com.example.service.impl.userserviceimpl ؛/** * test cglib */public class runcglib {public static void main (string [] args) {cglibproxy cglibproxy = new cglibroxy () ؛ UserService userService = (userService) cglibproxy.getInstance (New UserserviceImpl ()) ؛ userService.getName (1) ؛ userService.getage (1) ؛ }}نتائج التشغيل:
++++++ قبل cglib $ getName $ 0 ++++++++
getName
------ getName -----
++++++ بعد cglib $ getName $ 0 ++++++++
++++++ قبل cglib $ getage $ 1 ++++++++
getage
----- getage -----
++++++ بعد cglib $ getage $ 1 ++++++++
ما سبق هو كل محتوى هذه المقالة. آمل أن يكون محتوى هذه المقالة من بعض المساعدة في دراسة أو عمل الجميع. آمل أيضًا دعم wulin.com أكثر!