本文為原創(chuàng),如需轉(zhuǎn)載,請注明作者和出處,謝謝!
WebService 給人最直觀的感覺就是由一個個方法組成,并在客戶端通過 SOAP 協(xié)議調(diào)用這些方法。這些方法可能有返回值,也可能沒有返回值。雖然這樣可以完成一些工具,但這些被調(diào)用的方法是孤立的,當(dāng)一個方法被調(diào)用后,在其他的方法中無法獲得這個方法調(diào)用后的狀態(tài),也就是說無法保留狀態(tài)。
讀者可以想象,這對于一個完整的應(yīng)用程序,無法保留狀態(tài),就意味著只依靠 WebService 很難完成全部的工作。例如,一個完整的應(yīng)用系統(tǒng)都需要進行登錄,這在 Web 應(yīng)用中使用 Session 來保存用戶登錄狀態(tài),而如果用 WebService 的方法來進行登錄處理,無法保存登錄狀態(tài)是非常令人尷尬的。當(dāng)然,這也可以通過其他的方法來解決,如在服務(wù)端使用 static 變量來保存用戶狀態(tài),并發(fā)送一個 id 到客戶端,通過在服務(wù)端和客戶端傳遞這個 id 來取得相應(yīng)的用戶狀態(tài)。這非常類似于 Web 應(yīng)用中通過 Session 和 Cookie 來管理用戶狀態(tài)。但這就需要由開發(fā)人員做很多工作,不過幸好 Axis2 為我們提供了 WebService 狀態(tài)管理的功能。
使用 Axis2 來管理 WebService 的狀態(tài)基本上對于開發(fā)人員是透明的。在 WebService 類需要使用 org.apache.axis2.context.MessageContext 和 org.apache.axis2.context.ServiceContext 類來保存與獲得保存在服務(wù)端的狀態(tài)信息,這有些象使用 HttpSession 接口的 getAttribute 和 setAttribute 方法獲得與設(shè)置 Session 域?qū)傩浴?
除此之外,還需要修改 services.xml 文件的內(nèi)容,為 <service> 元素加一個 scope 屬性,該屬性有四個可取的值: Application, SOAPSession, TransportSession, Request ,不過要注意一下,雖然 Axis2 的官方文檔將這四個值的單詞首字母和縮寫字母都寫成了大寫,但經(jīng)筆者測試,必須全部小寫才有效,也就是這四個值應(yīng)為: application 、 soapsession 、 transportsession 、 request ,其中 request 為 scope 屬性的默認值。讀者可以選擇使用 transportsession 和 application 分別實現(xiàn)同一個 WebService 類和跨 WebService 類的會話管理。
在客戶端需要使用 setManageSession(true) 打開 Session 管理功能。
綜上所述,實現(xiàn)同一個 WebService 的 Session 管理需要如下三步:
1. 使用 MessageContext 和 ServiceContext 獲得與設(shè)置 key-value 對。
2. 為要進行 Session 管理的 WebService 類所對應(yīng)的 <service> 元素添加一個 scope 屬性,并將該屬性值設(shè)為 transportsession 。
3. 在客戶端使用 setManageSession(true) 打開 Session 管理功能。
下面是一個在同一個
WebService
類中管理
Session
的例子。
先建立一個WebService類,代碼如下:
import org.apache.axis2.context.ServiceContext;
import org.apache.axis2.context.MessageContext;
public class LoginService
{
public boolean login(Stringusername,Stringpassword)
{
if ( " bill " .equals(username) && " 1234 " .equals(password))
{
// 第1步:設(shè)置key-value對
MessageContextmc = MessageContext.getCurrentMessageContext();
ServiceContextsc = mc.getServiceContext();
sc.setProperty( " login " , " 成功登錄 " );
return true ;
}
else
{
return false ;
}
}
public StringgetLoginMsg()
{
// 第1步:獲得key-value對中的value
MessageContextmc = MessageContext.getCurrentMessageContext();
ServiceContextsc = mc.getServiceContext();
return (String)sc.getProperty( " login " );
}
}
在 LoginService 類中有兩個方法: login 和 getLoginMsg ,如果 login 方法登錄成功,會將“成功登錄”字符串保存在 ServiceContext 對象中。如果在 login 方法返回 true 后調(diào)用 getLoginMsg 方法,就會返回“成功登錄”。
下面是
LoginService
類的配置代碼(
services.xml
):
< service name ="loginService" scope ="transportsession" >
< description >
登錄服務(wù)
</ description >
< parameter name ="ServiceClass" >
service.LoginService
</ parameter >
< messageReceivers >
< messageReceiver mep ="http://www.w3.org/2004/08/wsdl/in-out"
class ="org.apache.axis2.rpc.receivers.RPCMessageReceiver" />
</ messageReceivers >
</ service >
<!--[if gte mso 9]><xml> Normal 0 7.8 磅 0 2 false false false MicrosoftInternetExplorer4 </xml><![endif]--><!--[if gte mso 9]><![endif]--> <!--[if gte mso 10]> <mce:style><! /* Style Definitions */ table.MsoNormalTable { mso-style-parent:""; font-size:10.0pt; font-family:"Times New Roman"; mso-fareast-font-family:"Times New Roman";} --> <!--[endif]-->
使用如下的命令生成客戶端使用的
stub
類:
<!--[if gte mso 9]><xml> Normal 0 7.8 磅 0 2 false false false MicrosoftInternetExplorer4 </xml><![endif]--><!--[if gte mso 9]><![endif]--> <!--[if gte mso 10]> <mce:style><! /* Style Definitions */ table.MsoNormalTable { mso-style-parent:""; font-size:10.0pt; font-family:"Times New Roman"; mso-fareast-font-family:"Times New Roman";} --> <!--[endif]-->
在
stub\src\client
目錄中生成了一個
LoginServiceStub.java
類,在該類中找到如下的構(gòu)造句方法:
java.lang.StringtargetEndpoint, boolean useSeparateListener)
throws org.apache.axis2.AxisFault
{


_serviceClient.getOptions().setSoapVersionURI(org.apache.axiom.soap.SOAP12Constants.SOAP_ENVELOPE_NAMESPACE_URI);
}
<!--[if gte mso 10]> <mce:style><! /* Style Definitions */ table.MsoNormalTable { mso-style-parent:""; font-size:10.0pt; font-family:"Times New Roman"; mso-fareast-font-family:"Times New Roman";} --> <!--[endif]-->
在該方法中最后添加如下的代碼:
_serviceClient.getOptions().setManageSession( true );
下面的客戶端代碼使用
LoginServiceStub
對象訪問了剛才建立的
WebService
:
LoginServiceStub.Loginlogin = new LoginServiceStub.Login();
login.setUsername( " bill " );
login.setPassword( " 1234 " );
if (stub.login(login).local_return)
{
System.out.println(stub.getLoginMsg().local_return);
}
<!--[if gte mso 9]><xml> Normal 0 7.8 磅 0 2 false false false MicrosoftInternetExplorer4 </xml><![endif]--><!--[if gte mso 9]><![endif]--> <!--[if gte mso 10]> <mce:style><! /* Style Definitions */ table.MsoNormalTable { mso-style-parent:""; font-size:10.0pt; font-family:"Times New Roman"; mso-fareast-font-family:"Times New Roman";} --> <!--[endif]-->
運行上面的代碼后,會輸出“成功登錄”信息。
更多文章、技術(shù)交流、商務(wù)合作、聯(lián)系博主
微信掃碼或搜索:z360901061

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