前面說完了Spring、Hibernate,很自然今天輪到struts了。struts的核心原理就是通過攔截器來處理客戶端的請求,經過攔截器一系列的處理后,再交給Action。下面先看看struts官方的工作原理圖:
圖1 struts原理圖
簡單分析一下:首先客戶端發(fā)來HttpServletRequest請求,傳遞給FilerDispatcher(ActionMapper是訪問靜態(tài)資源(struts的jar文件等)時用的,平時很少用),然后FilerDispatcher會為我們創(chuàng)建一個ActionProxy,ActionProxy會通過ConfigurationManager獲得struts.xml文件中的信息,ActionProxy擁有一個ActionInvocation實例,通過調用ActionInvocation的invoke()方法,來挨個處理Interceptor,最后處理Action,接著Result返回,再逆序經過Interceptor,最后得到HttpServletResponse返回給客戶端。
如果不太明白呢,那就看看下面這張時序圖,也許你就懂了:
圖2 struts原理時序圖
上面的時序圖邏輯就比較清晰了,我就不過多解釋了??赐阺truts的原理圖,我們還是需要通過代碼來進一步了解它具體是怎么實現(xiàn)的。首先,我們需要一個ActionInvocation:
package com.tgb.struts;
import java.util.ArrayList;
import java.util.List;
public class ActionInvocation {
List<Interceptor> interceptors = new ArrayList<Interceptor>();
int index = -1;
Action a = new Action();
public ActionInvocation() {
this.interceptors.add(new FirstInterceptor());
this.interceptors.add(new SecondInterceptor());
}
public void invoke() {
index ++;
if(index >= this.interceptors.size()) {
a.execute();
}else {
this.interceptors.get(index).intercept(this);
}
}
}
我們實現(xiàn)的ActionInvocation是將Interceptor寫在里面的,但實際上是通過反射加載的,原理同之前寫的Spring與Hibernate的博客,相同的代碼就不在這里占用篇幅了,也沒啥意思。不知道怎么實現(xiàn)的朋友請查看前面幾篇博客。
接下來是我們的Interceptor接口以及兩個簡單的實現(xiàn):
package com.tgb.struts;
public interface Interceptor {
public void intercept(ActionInvocation invocation) ;
}
package com.tgb.struts;
public class FirstInterceptor implements Interceptor {
public void intercept(ActionInvocation invocation) {
System.out.println("FirstInterceptor Begin...");
invocation.invoke();
System.out.println("FirstInterceptor End...");
}
}
package com.tgb.struts;
public class SecondInterceptor implements Interceptor {
public void intercept(ActionInvocation invocation) {
System.out.println("SecondInterceptor Begin...");
invocation.invoke();
System.out.println("SecondInterceptor End...");
}
}
然后就是我們的Action:
[java] view plaincopy在CODE上查看代碼片派生到我的代碼片
package com.tgb.struts;
public class Action {
public void execute() {
System.out.println("Action Run...");
}
}
最后是我們的客戶端調用:
package com.tgb.struts;
public class Client {
public static void main(String[] args) {
new ActionInvocation().invoke();
}
}
差點忘了,還有我們最后的執(zhí)行結果:
FirstInterceptor Begin...
SecondInterceptor Begin...
Action Run...
SecondInterceptor End...
FirstInterceptor End...
通過上面的執(zhí)行結果,我們可以很清楚的看到,請求來的時候會按照順序被所有配置的攔截器攔截一遍,然后返回的時候會按照逆序再被攔截器攔截一遍。這跟數(shù)據(jù)結構中的“棧”非常類似(FIFO-先進先出),數(shù)據(jù)結構我不太懂,也許這樣比喻有些不妥。各位根據(jù)自己的認識理解吧。
最近一直在研究這三大框架,折騰半天它們都離不開集合,離不開反射。其實它們道理都是想通的,搞懂一個,其他的也就很好懂了。等著吧,早晚咱們自己寫一個更好用的。
更多建議: