一、使用的背景(也不能算是使用的背景,最多只能算是一個在什么條件下面我想到了使用動態代理實現AOP的攔截功能):
因為在項目中程序的結構是使用SOAP調用JNI,因此在SOAP服務端里面沒有任何實現代碼,僅僅是new一個JNI的對象,然后調用JNI對應的方法。但是在調用JNI方法之前需要對傳進JNI的javaBean進行初始化,而且還需要記錄日志。而SOAP服務端的代碼是通過ant自動生成的,需要對他進行手工的修改,在修改過程中發現每一個方法里面都是相同的:記錄進入方法的日志、初始化JavaBean和記錄退出方法的日志,這寫東西都是通過拷貝粘貼來完成的,想到假如以后再加一個什么功能的時候又得每一個方法進行拷貝粘貼,而且方法的數量還不少,所以覺得這樣來實現是不科學的。示例代碼如下:
public class SOAP{
PRivate JniInterface jni = null;
private Log log = 。。。;
public SOAP(){
jni=new JniClass();
}
/**方法A**/
public JavaBeanA aMethod(JavaBeanA javaBeanA){
log.debug("進入A方法");
//初始化JavaBean
Init(javaBeanA);
//調用JNI對應的方法
JavaBeanA result = jni.aMethod(javaBeanA);
log.debug("退出A方法");
return result;
}
……………………………………
……………………………………
等等,很多這樣的方法
……………………………………
……………………………………
}
從示例代碼里面可以看出,除了調用JNI對應的方法不同之外,其他的都是相同的代碼,把所有的東西進行拷貝復制是不合理的。每當對SOAP進行修改,就必須將所有的方法重新拷貝粘貼。為了省去拷貝粘貼這一工序,所以使用動態代理實現AOP攔截共能。
二、實現AOP攔截
1. 定義Interceptor接口
public interface Interceptor {
//在調用之前調用該方法
public void before(InvokeJniInfo invInfo);
//在調用之后調用該方法
public void after(InvokeJniInfo invInfo);
//出現異常之后調用該方法
public void exceptionThrow(InvokeJniInfo invInfo);
}
2. 定義 InvokeJniInfo 類
在Interceptor接口中的InvokeJniInfo類,該類的定義如下:
public class InvokeJniInfo {
//被代理的對象
Object proxy;
//被調用的方法
Method method;
//被調用方法的參數列表
Object[] args;
//調用之后的結果
Object result;
//拋出的異常
Throwable exception;
新聞熱點
疑難解答