最近發(fā)現(xiàn)很多朋友連攔截器都不知道,于是想寫個BLOG總結(jié)一下。
java攔截器的基本原理其實非常簡單,說白了就是動態(tài)代理類。
下面來看一個簡單的例子
首先,我建立一個攔截器的類InterceptorClass,這里的before()和after()方法是以后攔截器會執(zhí)行的方法
CODE清單一:
//攔截器
public class InterceptorClass {
public void before() {
System.out.println("攔截器InterceptorClass方法調(diào)用:before()!");
}
public void after() {
System.out.println("攔截器InterceptorClass方法調(diào)用:after()!");
}
}
??
?
我們模擬一個業(yè)務組件接口BusinessInterface,和一個業(yè)務組件實現(xiàn)類BusinessClass
CODE清單二:
/**
* Created by IntelliJ IDEA.
* User: Ming
* Date: 2010-9-7
* Time: 8:45:26
*/
//業(yè)務組件接口
public interface BusinessInterface {
public void doSomething();
}
????
?
?
CODE清單三:
/**
* Created by IntelliJ IDEA.
* User: Ming
* Date: 2010-9-7
* Time: 8:46:27
*/
//業(yè)務組件實現(xiàn)類
public class BusinessClass implements BusinessInterface {
public void doSomething() {
System.out.println("業(yè)務組件BusinessClass方法調(diào)用:doSomething()");
}
}
?
?
然后,創(chuàng)建一個動態(tài)代理類DynamicProxyHandler,這個類是集成InvocationHandler接口的,動態(tài)類的原理實際上是使得當你執(zhí)行一個動態(tài)方
法的時候,他可以把這個動態(tài)方法dispatch到這個動態(tài)類上來。這樣,你就可以在這個方法的前后嵌入自己的一些方法。
CODE清單四:
/**
* Created by IntelliJ IDEA.
* User: Ming
* Date: 2010-9-7
* Time: 8:50:35
*/
/**
* 動態(tài)代理類,實現(xiàn)InvocationHandler接口.
* 包含了業(yè)務對象綁定動態(tài)代理類的處理
*/
public class DynamicProxyHandler implements InvocationHandler {
private Object business;//被代理對象
private InterceptorClass inceptor = new InterceptorClass();//攔截器
public DynamicProxyHandler(Object business) {
this.business = business;
}
???
?// 代理要調(diào)用的方法,并在方法調(diào)用前后調(diào)用連接器的方法
?
?
/**
* @param proxy 代理類對象
* @param method 被代理的接口方法
* @param args 被代理接口方法的參數(shù)
* @return
* @throws Throwable
*/
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
Object result = null;
inceptor.before();
result = method.invoke(business, args);
inceptor.after();
return result;
}
?
OK,我們來寫個類測試一下
CODE清單五:
public static void main(String[] args) {
//生成待測試的業(yè)務組件對象
BusinessInterface business = new BusinessClass();
//生成動態(tài)代理類實例
DynamicProxyHandler handler = new DynamicProxyHandler(business);
BusinessInterface businessProxy = (BusinessInterface) Proxy.newProxyInstance(
//被代理類的ClassLoader
business.getClass().getClassLoader(),
//要被代理的接口,本方法返回對象會自動聲稱實現(xiàn)了這些接口
business.getClass().getInterfaces(),
//代理處理器對象
handler);
//用動態(tài)代理類調(diào)用方法
businessProxy.doSomething();
}
?
來看看結(jié)果:
近期struts2很流行,而且攔截器是struts2里面一個比較好的功能,下面舉個例子說明一下攔截器在struts2中的用法。
struts2對攔截器實現(xiàn)做了一個封裝,使得我們在實現(xiàn)的時候比較簡單。
首先我們要建一個攔截器類
CODE清單六:
public class AuthorizationInterceptor extends AbstractInterceptor {
@Override
public String intercept(ActionInvocation invocation) throws Exception {
Map session = invocation.getInvocationContext().getSession();
String userName = (String) session.get("userName");
if ( userName != null && userName.equals("test")) {
System.out.println("攔截器:合法用戶登錄---");
return invocation.invoke();
}
else
{
System.out.println("攔截器:用戶未登錄---");
return Action.LOGIN;
}
}
}
?
?
這個類是必須要繼承struts2包中提供的AbstractInterceptor類,這個類有一個抽象方法intercept,這個方法是必須要實現(xiàn)的。
那么經(jīng)理在這個攔截器里面寫了一個簡單的實現(xiàn),對url用戶合法性做了一個限制。
接下來比較關鍵的是過濾器在struts2中的配置,先看看代碼
CODE清單七:
?
<package name="system" extends="struts-default">
<interceptors>
<!-- 定義權(quán)限控制攔截器 -->
<interceptor name="authority"
class="com.sharesin.biz.common.intercepts.struts2.AuthorizationInterceptor"/>
<!-- 定義一個包含權(quán)限控制的攔截器棧 -->
<interceptor-stack name="mystack">
<interceptor-ref name="defaultStack"></interceptor-ref>
<interceptor-ref name="authority"></interceptor-ref>
</interceptor-stack>
</interceptors>
<!--定義默認攔截器 -->
<default-interceptor-ref name="mystack" />
<!--定義全局處理結(jié)果 -->
<global-results>
<result name="login">index.jsp</result>
</global-results>
<action name="login_*" class="com.sharesin.biz.web.system.LoginAction" method="{1}">
<result name="success">system/homepage.jsp</result>
</action>
</package>
??
在interceptors節(jié)點里,我們可以定義多個攔截器,這里的名為authority的只是其中的一個。struts2的攔截器棧我是先執(zhí)行struts2默認的攔
截器defaultStack,然后再執(zhí)行我的。然后只需要用default-interceptor-ref標簽設置好這個system包中的默認攔截器為這個攔截器就OK了。
struts2中引入了package這個概念,我覺得十分實用,當然這對struts2攔截器也是個實惠,我們可以根據(jù)不同的action來分包和不同的攔截器
ok,來運行測試一下。
?
更多文章、技術交流、商務合作、聯(lián)系博主
微信掃碼或搜索:z360901061

微信掃一掃加我為好友
QQ號聯(lián)系: 360901061
您的支持是博主寫作最大的動力,如果您喜歡我的文章,感覺我的文章對您有幫助,請用微信掃描下面二維碼支持博主2元、5元、10元、20元等您想捐的金額吧,狠狠點擊下面給點支持吧,站長非常感激您!手機微信長按不能支付解決辦法:請將微信支付二維碼保存到相冊,切換到微信,然后點擊微信右上角掃一掃功能,選擇支付二維碼完成支付。
【本文對您有幫助就好】元
