多多色-多人伦交性欧美在线观看-多人伦精品一区二区三区视频-多色视频-免费黄色视屏网站-免费黄色在线

國內(nèi)最全I(xiàn)T社區(qū)平臺(tái) 聯(lián)系我們 | 收藏本站
阿里云優(yōu)惠2
您當(dāng)前位置:首頁 > php框架 > 框架設(shè)計(jì) > 動(dòng)態(tài)代理實(shí)現(xiàn)Spring Aop

動(dòng)態(tài)代理實(shí)現(xiàn)Spring Aop

來源:程序員人生   發(fā)布時(shí)間:2016-06-25 15:32:16 閱讀次數(shù):3415次

引言


我們在前兩篇文章中,都為這篇做了鋪墊,我們現(xiàn)在來做這樣1件事情,在業(yè)務(wù)邏輯中添加Aop的非業(yè)務(wù)邏輯。



AopClinetTest:

package com.tgb.client; import com.tgb.config.BeanFactory; import com.tgb.config.ClassPathXmlApplicationContext; import com.tgb.dao.UserDao; import com.tgb.domain.User; /** * AOP效果測試 * @ClassName: AopClientTest * @Description: TODO(這里用1句話描寫這個(gè)類的作用) * @author [qmx] * @date * */ public class AopClientTest { public static void main(String[] args) throws Exception { //初始化容器對(duì)象 BeanFactory factory = new ClassPathXmlApplicationContext(); User user = new User(); user.setUserName("hanyankun"); //獲得容器中userDao對(duì)象 UserDao userDao = (UserDao)factory.getBean("UserDao"); userDao.update(user); } }

AspectCacheBean:


package com.tgb.config; import com.tgb.util.MethodCatch; /** * @ClassName: AspectCachBean * @Description: * 緩存服務(wù)類,實(shí)現(xiàn)了對(duì)緩存的,前置,后置, 保存的方法 * @author [qmx] * @date * */ public class AspectCachBean { @MethodCatch(methodName="cacheBefore") public void cacheBefore(Object proxy) { System.out.println("---這是切入 類AspectCachBean cacheBefore()-方法--"); } @MethodCatch(methodName="cacheAfter") public static void cacheAfter(Object proxy) { System.out.println("---這是切入 類AspectCachBean cacheAfter()-方法--"); } @MethodCatch(methodName="cacheSave") public void cacheSave(Object proxy){ System.out.println("---這是切入 類AspectCachBean cacheSave()-方法--"); } }

AspectCertifiyBean:

package com.tgb.config; import com.tgb.util.MethodCatch; /** * * @ClassName: AspectCertifiyBean * @Description: 認(rèn)證服務(wù)類,提供了認(rèn)證前, 認(rèn)證后,認(rèn)證保存的方法 * @author [qmx] * @date * */ public class AspectCertifiyBean { @MethodCatch(methodName = "certifiyBefore") public void certifiyBefore(Object proxy) { System.out.println("---這是切入 類AspectCertifiyBean certifiyBefore()-方法--"); } @MethodCatch(methodName = "certifyAfter") public void certifyAfter(Object proxy) { System.out.println("---這是切入 類AspectCertifiyBean certifyAfter()-方法--"); } @MethodCatch(methodName = "certifySave") public void certifySave(Object proxy) { System.out.println("---這是切入 類AspectCertifiyBean certifySave()-方法--"); } }

BeanFactory:


package com.tgb.config; import java.util.List; import java.util.Map; /** * * @ClassName: ContainerBeans * @Description: 容器接口,提供容器公共服務(wù)方法, 增加,刪除,遍歷,獲得對(duì)象,遍歷類型,容器大小等方法 * @author [qmx] * @date * */ public interface BeanFactory { /** * 獲得容器中指定對(duì)象 * * @param id * 對(duì)象名稱如: getBean("user") * @return */ public Object getBean(String id); /** * 容器中放入對(duì)象 * * @param k * @param v * @return */ public Object put(String k, Object v); /** * 打印容器中所有對(duì)象類型 */ public void printTypeName(); /** * 獲得容器中所有對(duì)象 返回類型 Map<string(對(duì)象類型),Object(對(duì)象)> * * @return Map<string(對(duì)象類型),Object(對(duì)象)> */ public Map<String, Object> getAllBean(); /** * 獲得容器所有bean */ public void printAllbeanId(); public void remove(String id); /** * 容器中對(duì)象的數(shù)量 * @return */ public int size(); }

ClassPathXmlApplicationContext:


package com.tgb.config; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.util.ArrayList; import java.util.HashMap; import java.util.HashSet; import java.util.Iterator; import java.util.LinkedHashSet; import java.util.List; import java.util.Map; import java.util.Map.Entry; import java.util.Set; import java.util.TreeSet; import net.sf.cglib.asm.ClassVisitor; import org.jdom.Document; import org.jdom.Element; import org.jdom.input.SAXBuilder; /*** * * * @author 容器組裝類, 裝載 業(yè)務(wù)容器 和 切入容器。 分別將其中的 顆粒裝載到各自的 beans 中 */ public class ClassPathXmlApplicationContext implements BeanFactory { // 業(yè)務(wù)容器beans private Map<String, Object> containerBeans = new HashMap<String, Object>(); // 切面容器beans private Map<String, Object> aspectBeans = new HashMap<String, Object>(); // 設(shè)置是不是需要aop private boolean isAop = true; /* * 構(gòu)造函數(shù)加載個(gè)容器內(nèi)對(duì)象 */ public ClassPathXmlApplicationContext() throws Exception { SAXBuilder sb = new SAXBuilder(); // 掃描業(yè)務(wù)容器對(duì)象 Document containerDoc = sb.build(Thread.currentThread().getContextClassLoader() .getResourceAsStream("beans.xml")); // 掃描切入容器對(duì)象 Document aspectDoc = sb.build(Thread.currentThread().getContextClassLoader() .getResourceAsStream("aspecbeans.xml")); // 設(shè)置切面容器 getAspectBeans(aspectDoc); // 設(shè)置業(yè)務(wù)容器bean getContainerBeans(containerDoc); } /*** * 設(shè)置業(yè)務(wù)容器裝配 * @param doc * @throws ClassNotFoundException * @throws IllegalAccessException * @throws InstantiationException * @throws SecurityException * @throws NoSuchMethodException * @throws InvocationTargetException * @throws IllegalArgumentException */ private void getContainerBeans(Document doc) throws InstantiationException, IllegalAccessException, ClassNotFoundException, NoSuchMethodException, SecurityException, IllegalArgumentException, InvocationTargetException { //讀取文檔根目錄 Element root = doc.getRootElement(); //獲得aop節(jié)點(diǎn)信息 Element aopElement = (Element) root.getChildren("aop").get(0); //aop節(jié)點(diǎn)屬性 isAop = Boolean.parseBoolean(aopElement.getAttributeValue("isaop")); //獲得bean節(jié)點(diǎn) List list = root.getChildren("bean"); // 前置增強(qiáng)節(jié)點(diǎn) List aopBeforeList = root.getChildren("aspectbefore"); //后置節(jié)點(diǎn) List aopAfterList = root.getChildren("aspectafter"); //辨別增強(qiáng)節(jié)點(diǎn)是不是有配置,放入bean關(guān)系容器中 if (aopBeforeList != null) { containerBeans.put("aspectbefore", aopBeforeList); } if (aopAfterList != null) { containerBeans.put("aspectafter", aopAfterList); } //調(diào)用設(shè)備對(duì)象方法,裝配業(yè)務(wù)對(duì)象 putAllBeans(list, containerBeans); } /** * 設(shè)置切入容器裝配對(duì)象 * * @param doc * @throws InstantiationException * @throws IllegalAccessException * @throws ClassNotFoundException * @throws InvocationTargetException * @throws IllegalArgumentException * @throws SecurityException * @throws NoSuchMethodException */ private void getAspectBeans(Document doc) throws InstantiationException, IllegalAccessException, ClassNotFoundException, NoSuchMethodException, SecurityException, IllegalArgumentException, InvocationTargetException { //讀取文檔根目錄 Element root = doc.getRootElement(); List aspectElements = root.getChildren("aspectbean");//讀取切入配置文件 putAllBeans(aspectElements,aspectBeans); } /** * 對(duì)象裝配方法 * @param list 讀取的配置文件 * @param allBeans 設(shè)置裝配的容器對(duì)象 * @throws InstantiationException * @throws IllegalAccessException * @throws ClassNotFoundException * @throws NoSuchMethodException * @throws SecurityException * @throws IllegalArgumentException * @throws InvocationTargetException */ public void putAllBeans(List list, Map<String, Object> allBeans) throws InstantiationException, IllegalAccessException, ClassNotFoundException, NoSuchMethodException, SecurityException, IllegalArgumentException, InvocationTargetException { for (int i = 0; i < list.size(); i++) { //獲得傳入父親節(jié)點(diǎn)中的每一個(gè)子節(jié)點(diǎn),為行element Element element = (Element) list.get(i); //獲得子節(jié)點(diǎn)中的id屬性 String id = element.getAttributeValue("id"); //獲得子節(jié)點(diǎn)中的class屬性 String clazz = element.getAttributeValue("class"); //實(shí)例化class Object o = Class.forName(clazz).newInstance(); //將實(shí)例化的class放入容器 allBeans.put(id, o); //for循環(huán)獲得 bean中的 屬性property for (Element propertyElement : (List<Element>) element .getChildren("property")) { //獲得property屬性中的name屬性 String name = propertyElement.getAttributeValue("name"); // userDAO //獲得property屬性中的ref屬性 String bean = propertyElement.getAttributeValue("ref"); // //獲得子屬性的試題 Object beanObject = allBeans.get(bean);// UserDAOImpl //調(diào)用 依賴實(shí)體中的set方法(為籽實(shí)體的方法) String methodName = "set" + name.substring(0, 1).toUpperCase() + name.substring(1); Method m = o.getClass().getMethod(methodName, beanObject.getClass().getInterfaces()[0]); m.invoke(o, beanObject); } } } /** * 獲得容器中指定對(duì)象 * * @param id * 對(duì)象名稱如: getBean("user") * @return */ public Object getBean(String id) { if (!isAop) { return containerBeans.get(id); } return new JDKDynamicProxy(containerBeans.get(id), aspectBeans, containerBeans) .getProxy(); } /** * 容器中放入對(duì)象 * * @param k * @param v * @return */ public Object put(String k, Object v) { return containerBeans.put(k, v); } /** * 打印容器中所有對(duì)象類型 */ public void printTypeName() { Set<String> hashSet = new HashSet<String>(); Set<Entry<String, Object>> entryset = containerBeans.entrySet(); { Iterator iterator = entryset.iterator(); while (iterator.hasNext()) { Entry<String, Object> entry = (Entry<String, Object>) iterator.next(); hashSet.add(entry.getValue().getClass().getSimpleName()); } } for (String setType : hashSet) { System.out.println(setType); } } /** * 獲得容器中所有對(duì)象 * * @return Map<string(對(duì)象類型),Object(對(duì)象)> */ public Map<String, Object> getAllBean() { Map<String, Object> beanList = new HashMap<String, Object>(); Iterator iterator = containerBeans.entrySet().iterator(); while (iterator.hasNext()) { Entry<String, Object> entry = (Entry<String, Object>) iterator.next(); beanList.put(entry.getValue().getClass().getSimpleName(), entry.getValue()); } return beanList; } /*** * 刪除指定對(duì)象 */ public void remove(String id) { containerBeans.remove(id); } /*** * 打印所有注入對(duì)象 */ public void printAllbeanId() { Set<Entry<String, Object>> entryset = containerBeans.entrySet(); Set<String> linkSet = new TreeSet<String>(); { Iterator iterator = entryset.iterator(); while (iterator.hasNext()) { Entry<String, Object> entry = (Entry<String, Object>) iterator.next(); linkSet.add(entry.getKey()); // System.out.println(entry.getKey()); } System.out.println(linkSet.toString()); System.out.println("容器中的對(duì)象個(gè)數(shù)是" + size() + "個(gè)"); } } /** * 獲得容器中對(duì)象的個(gè)數(shù) */ public int size() { return containerBeans.size(); } }

JDKDynamicProxy:


package com.tgb.config; import java.lang.reflect.InvocationHandler; import java.lang.reflect.InvocationTargetException; import java.lang.reflect.Method; import java.lang.reflect.Proxy; import java.util.Iterator; import java.util.List; import java.util.Map; import java.util.Map.Entry; import org.jdom.Element; import com.tgb.util.MethodCatch; /* @ClassName: JDKDynamicProxy * @Description: AOP實(shí)現(xiàn)對(duì)業(yè)務(wù)容器 的增強(qiáng),對(duì)業(yè)務(wù)容器中每一個(gè)對(duì)象增強(qiáng) 服務(wù)類中的方法,根據(jù) 關(guān)系容器配置, * 實(shí)現(xiàn)特性方法增強(qiáng) * @author [qmx] */ public class JDKDynamicProxy implements InvocationHandler { private Object target; private Map<String, Object> aspectBeans; // 切入容器 private Map<String, Object> containerBeans;// 業(yè)務(wù)容器 /** * 代理類獲得代理對(duì)象,業(yè)務(wù)容器,切面容器 * * @param target * 被代理對(duì)象 * @param aspectBeans * 切面容器 * @param containerBeans * 業(yè)務(wù)容器 */ public JDKDynamicProxy(Object target, Map<String, Object> aspectBeans, Map<String, Object> containerBeans) { this.target = target; this.aspectBeans = aspectBeans; this.containerBeans = containerBeans; } @SuppressWarnings("unchecked") public <T> T getProxy() { return (T) Proxy.newProxyInstance(target.getClass().getClassLoader(), target .getClass().getInterfaces(), this); } @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { List beforeList = (List) containerBeans.get("aspectbefore");//獲得關(guān)系容器中的配置 invokeAspectName(beforeList, method, args);// 調(diào)用切面類中匹配方法 Object result = method.invoke(target, args);// 調(diào)用 被代理類本身方法 return result; } /** * 攔截方法匹配 * * @param beforeList * 攔截器的所有對(duì)象 * @param method * @param args * @throws NoSuchMethodException * @throws SecurityException * @throws IllegalAccessException * @throws IllegalArgumentException * @throws InvocationTargetException */ public void invokeAspectName(List beforeList, Method method, Object[] args) throws NoSuchMethodException, SecurityException, IllegalAccessException, IllegalArgumentException, InvocationTargetException { //if判斷獲得的集合是不是為空,若為空則履行所有服務(wù)對(duì)象的所有方法 if (beforeList != null && beforeList.size() != 0) { //for循環(huán)遍歷 集合對(duì)象中的對(duì)象,獲得每一個(gè)對(duì)象,履行該對(duì)象中的方法 for (int i = 0; i < beforeList.size(); i++) { Element element = (Element) beforeList.get(i); //獲得每一個(gè)對(duì)象 String aspectClass = element.getAttributeValue("aspectId");// 獲得容器中切入類名稱 String aspectName = element.getAttributeValue("aspectMethod");// 履行的切入方法 //若對(duì)象為空,則說明 if (aspectBeans.get(aspectClass) == null) { System.out.println("未找到該切入類,請(qǐng)查看配置的切入類名稱是不是正確"); return; } Class clazz = aspectBeans.get(aspectClass).getClass(); // 獲得切入類 String elementMethod = element.getAttributeValue("method");// 獲得被切入類方法 // 未聲明切入方法,則履行所有切入方法 if (aspectName == null) { if (method.getName() != null) { if (method.getName().equals(elementMethod)) { getAllMethod(clazz, aspectClass, args); } } aspactAllClass(aspectClass, args==null? new Object[1]: args); } else { //if判斷是不是 聲明l切入方法,若是則履行指定切入方法,否則履行所有方法 if (method.getName().equals(elementMethod)) { Method jinectmethod = clazz.getMethod(aspectName, Object.class); // 反射調(diào)用切入類方法 jinectmethod.invoke(aspectBeans.get(aspectClass), args==null? new Object[1]: args); } aspactAllClass(aspectClass, args==null? new Object[1]: args); } } } //傳入集合對(duì)象為空,則履行多有對(duì)象的所有方法 else { Iterator aspectClass = aspectBeans.entrySet().iterator(); while (aspectClass.hasNext()) { Entry<String, Object> entry = (Entry<String, Object>) aspectClass.next(); Class clazz = entry.getValue().getClass();// 獲得切入類 Method[] methods = clazz.getMethods(); for (int j = 0; j < methods.length; j++) { // 讀取切入類注解中的所有方法 if (methods[j].isAnnotationPresent(MethodCatch.class) == true) { MethodCatch methodCatch = methods[j] .getAnnotation(MethodCatch.class);// 獲得注解類 Method jinectmethod = clazz.getMethod(methodCatch.methodName(), Object.class); // 反射調(diào)用切入類方法 jinectmethod.invoke(entry.getValue(), args==null? new Object[1]: args); } } } } } /** * * @Title: aspactAllClass * @Description: 履行容器中所有服務(wù)類中的方法(除指定的對(duì)象不履行,其他的都履行) * @param @param aspectId * @param @param args * @param @throws NoSuchMethodException * @param @throws SecurityException * @param @throws IllegalAccessException * @param @throws IllegalArgumentException * @param @throws InvocationTargetException 設(shè)定文件 * @return void 返回類型 * @throws */ public void aspactAllClass(String aspectId, Object[] args) throws NoSuchMethodException, SecurityException, IllegalAccessException, IllegalArgumentException, InvocationTargetException { Iterator aspectClass = aspectBeans.entrySet().iterator(); //while循環(huán)獲得服務(wù)集合中的所有對(duì)象,調(diào)用該對(duì)象中的方法 while (aspectClass.hasNext()) { Entry<String, Object> entry = (Entry<String, Object>) aspectClass.next(); if (!aspectId.equals(entry.getKey())) { Class clazz = entry.getValue().getClass();// 獲得切入類 Method[] methods = clazz.getMethods(); for (int j = 0; j < methods.length; j++) { // 讀取切入類注解中的所有方法 if (methods[j].isAnnotationPresent(MethodCatch.class) == true) { MethodCatch methodCatch = methods[j] .getAnnotation(MethodCatch.class);// 獲得注解類 Method jinectmethod = clazz.getMethod(methodCatch.methodName(), Object.class); // 反射調(diào)用切入類方法 jinectmethod.invoke(entry.getValue(), args==null? new Object[1]: args); } } } } } /** * 履行某個(gè)服務(wù)類中的所有方法 * @Title: getAllMethod * @Description: TODO(這里用1句話描寫這個(gè)方法的作用) * @param @param clazz * @param @param aspectClass * @param @param args * @param @throws IllegalAccessException * @param @throws IllegalArgumentException * @param @throws InvocationTargetException * @param @throws NoSuchMethodException * @param @throws SecurityException 設(shè)定文件 * @return void 返回類型 * @throws */ public void getAllMethod(Class clazz, String aspectClass, Object[] args) throws IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException, SecurityException { Method[] methods = clazz.getMethods(); for (int j = 0; j < methods.length; j++) { if (methods[j].isAnnotationPresent(MethodCatch.class) == true) { MethodCatch methodCatch = methods[j].getAnnotation(MethodCatch.class);// 獲得注解類 Method jinectmethod = clazz.getMethod(methodCatch.methodName(), Object.class); // 反射調(diào)用切入類方法 jinectmethod.invoke(aspectBeans.get(aspectClass), args==null? new Object[1]: args); } } } }

UserDao:


package com.tgb.dao; import com.tgb.domain.User; /** * 用于操作用戶信息類。 * @ClassName: UserDao * @Description: TODO(這里用1句話描寫這個(gè)類的作用) * @author [qmx] * @date * */ public interface UserDao { void save(User user); void update(User user); public void delete( User user); }

UserDaoImpl:


package com.tgb.daoImpl; import com.tgb.dao.UserDao; import com.tgb.domain.User; /** * 用戶操作類,用于添加用戶信息 * * @ClassName: UserDaoImpl * @Description: TODO(這里用1句話描寫這個(gè)類的作用) * @author [qmx] * @date * */ public class UserDaoImpl implements UserDao { @Override public void save(User user) { System.out.println("這是業(yè)務(wù)類 " + this.getClass() + "-----的 userDao.save()方法-----"); } @Override public void update(User user) { System.out.println("這是業(yè)務(wù)類 " + this.getClass() + "-----的 userDao.update()方法-----"); } @Override public void delete(User user) { System.out.println("這是業(yè)務(wù)類 " + this.getClass() + "-----的 userDao.delete()方法-----"); } }

User:


package com.tgb.domain; public class User { private String userName; private String password; public String getUserName() { return userName; } public void setUserName(String userName) { this.userName = userName; } public String getPassword() { return password; } public void setPassword(String password) { this.password = password; } }

MethodCatch:


package com.tgb.util; /** * 自定義注解類,用于類方法上讀取方法名稱 */ import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; @Target(ElementType.METHOD) @Retention(RetentionPolicy.RUNTIME) public @interface MethodCatch { /** * 用于 獲得方法名稱 * @Title: methodName * @Description: * @param @return 設(shè)定文件 * @return String 返回類型 * @throws */ public String methodName(); }

aspectbeans.xml:


<beans> <!-- 服務(wù)類配置 --> <aspectbean id="aspectCachBean" class="com.tgb.config.AspectCachBean"></aspectbean> <aspectbean id="aspectCertifiyBean" class="com.tgb.config.AspectCertifiyBean"></aspectbean> </beans>

beans.xml:

<beans> <!-- 業(yè)務(wù)類 --> <bean id="UserDao" class="com.tgb.daoImpl.UserDaoImpl" /> <!-- 是不是啟用aop --> <aop isaop="true"></aop> <!-- 關(guān)系配置 --> <!-- aspectMethod="save" --> <aspectbefore aspectId="aspectCachBean" method="update" aspectMethod="cacheAfter" ></aspectbefore> <aspectbefore aspectId="aspectCertifiyBean" method="update" aspectMethod="certifyAfter" ></aspectbefore> </beans>






生活不易,碼農(nóng)辛苦
如果您覺得本網(wǎng)站對(duì)您的學(xué)習(xí)有所幫助,可以手機(jī)掃描二維碼進(jìn)行捐贈(zèng)
程序員人生
------分隔線----------------------------
分享到:
------分隔線----------------------------
關(guān)閉
程序員人生
主站蜘蛛池模板: 国产精品久久久久久爽爽爽 | 在线亚洲天堂 | 有色视频在线观看免费高清 | 欧美日韩国产成人综合在线 | 亚洲a级在线观看 | 欧美激情二区 | 影视精品网站入口 | 欧美最刺激好看的一级毛片 | 国产一级一级片 | www网站在线观看 | 亚洲精品一区91 | 一级毛片一级毛片一级毛片aaav | 黄网站在线播放视频免费观看 | 福利盒子手机看片 | 亚洲色图欧美一区 | 欧美另类 videos黑人极品 | 亚洲精品国产一区二区 | 亚洲综合日韩精品欧美综合区 | 成人亚洲综合 | 日韩欧美~中文字幕 | 亚洲精品午夜久久久伊人 | 成人精品一级毛片 | 国产精品视频久久久久 | 亚洲在线h| 日韩精品a在线视频 | 午夜精品久久久久久毛片 | 欧美日韩看片 | 国产精品亚洲精品日韩动图 | 手机看片福利在线 | 在线a视频网站 | 激情老妇xxx | 亚洲邪恶天堂影院在线观看 | 国产三级做爰高清视频a | 狠狠躁天天躁夜夜躁婷婷 | 午夜精品久久久久久久 | 久久综合爱 | 欧美日韩性视频一区二区三区 | 欧美妇色| 国产福利视频一区二区三区四区 | 色www永久免费网站国产 | 自拍偷拍第一页 |