原文鏈接:
http://ws.apache.org/axis2/1_1_1/quickstartguide.html本指南的目的是讓你盡可能快的創建使用Axis2的服務和客戶端,我們將使用一個簡單的StockQuote服務并顯示給你一些創建和部署它
的不同的方式,以及快速的看看Axis2自帶的一些工具,然后我們將看看創建訪問這些服務的客戶端。
內容- 介紹??
- 做好準備??
- Axis2服務??
- 創建服務??
- ????部署POJOs??
- ????使用AXIOM構建服務??
- ????使用ADB生成服務??
- ????使用XMLBeans生成服務??
- ????使用JiBX生成服務??
- 生成客戶端??
- ????使用AXIOM創建一個客戶端??
- ????使用ADB生成一個客戶端??
- ????使用XMLBeans生成一個客戶端??
- ????使用JiBX生成一個客戶端??
- 總結??
- 進一步學習??
介紹
做好準備
Axis2服務
創建服務
部署POJOs
使用AXIOM構建服務
使用ADB生成服務
使用XMLBeans生成服務
使用JiBX生成服務
生成客戶端
使用AXIOM創建一個客戶端
使用ADB生成一個客戶端
使用XMLBeans生成一個客戶端
使用JiBX生成一個客戶端
總結
進一步學習
快速安裝筆記:文檔的代碼可以在解壓的標準二進制發布[/url]找到,更明確的位于其中的Axis2_HOME/samples/目錄-quickstart,quickstartdb,
quickstartaxiom,quickstartjibx和quickstartxmlbeans,如果你繼續下去它將幫你掌握它。它包含一個Ant構建文件(build.xml)
貫穿所有的例子我們將提到它來使得編譯更容易。
介紹讓我們以服務本身開始。我們將使它簡單,所以你可以看到當我們構建并部署服務時會發生什么,一個StockQuoteService例子看起來
像這個,所以讓我們使用下面的(參看Code Listing 1)。
Code Listing 1: StockQuoteService類
- package?samples.quickstart.service.pojo;??
- ??
- import?java.util.HashMap;??
- ??
- public?class?StockQuoteService?{??
- ????private?HashMap?map?=?new?HashMap();??
- ??
- ????public?double?getPrice(String?symbol)?{??
- ????????Double?price?=?(Double)?map.get(symbol);??
- ????????if(price?!=?null){??
- ????????????return?price.doubleValue();??
- ????????}??
- ????????return?42.00;??
- ????}??
- ??
- ????public?void?update(String?symbol,?double?price)?{??
- ????????map.put(symbol,?new?Double(price));??
- ????}??
- }??
package samples.quickstart.service.pojo;
import java.util.HashMap;
public class StockQuoteService {
private HashMap map = new HashMap();
public double getPrice(String symbol) {
Double price = (Double) map.get(symbol);
if(price != null){
return price.doubleValue();
}
return 42.00;
}
public void update(String symbol, double price) {
map.put(symbol, new Double(price));
}
}
它將為一個具有兩個可能的調用的簡單服務,其中一個是一個in/out消息,另一個則為一個只能in的服務,最終我們將打包服務并用
四種不同的方式部署部署它。
首先,讓我們看看這個簡單的Java類怎樣響應一個服務。
做好準備在我們使用Axis2構建任何東西之前,我們將需要關注一些家務事。現在你將需要準備好你使用Axis2的環境,幸運的是,它只包括一
些簡單的步驟:
1,下載并安裝Java(版本至少為JDK1.4)
2,下載Axis2并解壓到一個目標目錄
3,復制axis2.war文件到你的servlet引擎的webapps目錄
4,設置AXIS2_HOME環境變量來指出目標目錄,注意Axis2生成的所有腳本和構建文件依賴于這個值,所以不要遺漏了這個步驟。
大多數情況下,我們的服務也將需要一個WSDL文件,Axis2的Java2WSDL可以用來生成一個WSDL。執行以下步驟來從一個Java類生成一
個WSDL文件:
1,創建并編譯Java類
2,使用該命令生成WSDL:
%AXIS2_HOME%/bin/java2wsdl -cp . -cn samples.quickstart.service.pojo.StockQuoteService -of StockQuoteService.wsdl移動你生成WSDL文件,你可以做你需要的任何更改。例如,你可能添加自定義的過錯或者改變生成的元素名。例如,該StockQuoteSer
vice.wsdl位于%AXIS2_HOME%/samples/quickstartadb/resources/META-INF文件夾,我們將在本指南的其他部分使用它,代替生成過
程創建的一般參數。
Axis2服務在我們構建任何東西之前,理解最終產品看起來像什么是有用的。Axis2的服務器端可以被部署在任何Servlet引擎上,并且有如下的
Code Listing 2顯示的結構。
Code Listing 2: axis2.war的目錄結構
- axis2-web???
- META-INF??
- WEB-INF??
- ????classes???
- ????conf??
- ????????axis2.xml???
- ????lib??
- ????????activation.jar??
- ????????...??
- ????????xmlSchema.jar??
- ????modules??
- ????????modules.list???
- ????????addressing.mar??
- ????????...??
- ????????soapmonitor.mar??
- ????services??
- ????????services.list??
- ????????aservice.aar??
- ????????...??
- ????????version.aar??
- ????web.xml??
axis2-web
META-INF
WEB-INF
classes
conf
axis2.xml
lib
activation.jar
...
xmlSchema.jar
modules
modules.list
addressing.mar
...
soapmonitor.mar
services
services.list
aservice.aar
...
version.aar
web.xml
從最上面開始,axis2-web是組成Axis2管理程序的一些JSPs,你可以通過它來執行任何需要的動作,例如添加服務,使用模塊和禁止
模塊。WEB-INF包含了運行部署到服務目錄的任何服務的實際上的java類和其他支持文件。
這里主要的文件是axis2.xml,它控制程序怎樣與接收的消息打交道,決定Axis2是否需要使用模塊目錄里定義的任何模塊。
這里你可以看到,服務可以被部署為*.aar文件,但是它們的內容必須以一個特殊的方式安排。例如,服務的結構將為如下:
- -?StockQuoteService??
- ???-?META-INF??
- ?????-?services.xml??
- ???-?samples??
- ?????-?quickstart??
- ???????-?service??
- ?????????-?pojo??
- ???????????-?StockQuoteService.class??
- StockQuoteService
- META-INF
- services.xml
- samples
- quickstart
- service
- pojo
- StockQuoteService.class
這不是太復雜,服務的名字為StockQuoteService,它在services.xml中指定,并且根據包名把任何Java類放到合適的位置。META-INF
目錄包含關于Axis2需要來正確執行服務的額外信息。services.xml文件定義了服務本身并把Java類鏈接到它(參看Code Listing 3)。
Code Listing 3: 服務定義文件
- <service?name="StockQuoteService"?scope="application">??
- ????<description>??
- ????????Stock?Quote?Sample?Service??
- ????</description>??
- ????<messageReceivers>??
- ????????<messageReceiver???
- ????????????mep="http://www.w3.org/2004/08/wsdl/in-only"??
- ????class="org.apache.axis2.rpc.receivers.RPCInOnlyMessageReceiver"/>??
- ????????<messageReceiver??
- ????????????mep="http://www.w3.org/2004/08/wsdl/in-out"??
- ????class="org.apache.axis2.rpc.receivers.RPCMessageReceiver"/>??
- ????</messageReceivers>??
- ????<parameter?name="ServiceClass">??
- ????????samples.quickstart.service.pojo.StockQuoteService??
- ????</parameter>??
- </service>??
<service name="StockQuoteService" scope="application">
<description>
Stock Quote Sample Service
</description>
<messageReceivers>
<messageReceiver
mep="http://www.w3.org/2004/08/wsdl/in-only"
class="org.apache.axis2.rpc.receivers.RPCInOnlyMessageReceiver"/>
<messageReceiver
mep="http://www.w3.org/2004/08/wsdl/in-out"
class="org.apache.axis2.rpc.receivers.RPCMessageReceiver"/>
</messageReceivers>
<parameter name="ServiceClass">
samples.quickstart.service.pojo.StockQuoteService
</parameter>
</service>
這里你看到服務本身被定義了,以及不同的消息交換模式相關的messageReceiver類型。
META-INF目錄也是你打算包含在該程序中的自定義WSDL文件的位置。
你可以通過簡單的采用該文件目錄結構并復制到你的servlet引擎的webapps目錄來部署一個服務,這是著名的"爆發"形式,但是你也
可以壓縮你的文檔到一個*.aar文件,類似于一個*.jar文件,并直接將*.aar文件放到servlet引擎的webapps目錄。
既然你理解了我們在嘗試完成什么,我們幾乎準備好開始構建了。
首先,
下載并解壓合適版本的Axis2標準二進制發布。確認你設置了AXIS2_HOME變量的值來匹配你解壓該版本內容的位置。
讓我們看看一些創建客戶端和服務的不同方式。
創建服務在這個部分,我們將看看根據StockQuoteService類創建服務的五種方式:部署Plain Old Java Objects(POJO),使用AXIOM的OMElement
構建服務,使用Axis2 Databinding Framework(ADB)生成服務,使用XMLBeans生成服務和使用JiBX生成服務。
部署POJOs使用POJOs(Plain Old Java Objects)來部署服務,執行下面的步驟。
注意包含在<AXIS2_HOME>/samples/quickstart的目錄結構(services.xml文件來自于該指南的第一個部分):
- -?quickstart??
- ???-?README.txt??
- ???-?build.xml??
- ???-?resources??
- ?????-?META-INF??
- ???????-?services.xml??
- ???-?src??
- ?????-?samples??
- ???????-?quickstart??
- ?????????-?service??
- ???????????-?pojo??
- ?????????????-?StockQuoteService.java??
- quickstart
- README.txt
- build.xml
- resources
- META-INF
- services.xml
- src
- samples
- quickstart
- service
- pojo
- StockQuoteService.java
注意你可以通過在quickstart目錄鍵入
ant generate.wsdl來生成WSDL。
盡管如此,創建StockQuoteService.wsdl是可選的。它可以是直接從Java類生成的版本,或者該文件的一個自定義版本,并且servi
ces.xml是本文檔前面提到的同一文件。
現在通過在quickstart目錄鍵入
ant generate.service來構建工程,該目錄創建了以下目錄結構:
- -?quickstart/build/classes??
- ???-?META-INF??
- ?????-?services.xml??
- ???-?samples??
- ?????-?quickstart??
- ???????-?service??
- ?????????-?pojo??
- ???????????-?StockQuoteService.class??
- quickstart/build/classes
- META-INF
- services.xml
- samples
- quickstart
- service
- pojo
- StockQuoteService.class
如果你想以爆發形式部署服務,重命名classes目錄為StockQuoteService,并復制它到你的servlet引擎的webapps/axis2/WEB-INF/s
ervices目錄。否則,復制build/StockQuoteService.aar文件到你的servlet引擎的webapps/axis2/WEB-INF/services目錄。然后通過
視察以下服務列表來確認服務被正確部署:
http://localhost:8080/axis2/services/listServices你也可以檢驗以下WSDL:
http://localhost:8080/axis2/services/StockQuoteService?wsdl以及以下結構:
http://localhost:8080/axis2/services/StockQuoteService?xsd一旦這些urls工作,讓我們快速測試一下服務。讓你的瀏覽器訪問以下URL試試:
http://localhost:8080/axis2/rest/StockQuoteService/getPrice?symbol=IBM你將得到如下應答:
- <ns:getPriceResponse?xmlns:ns="http://pojo.service.quickstart.samples/xsd"><ns:return>42</ns:return></ns:getPriceResponse>??
<ns:getPriceResponse xmlns:ns="http://pojo.service.quickstart.samples/xsd"><ns:return>42</ns:return></ns:getPriceResponse>
如果你像這樣調用update方法:
http://localhost:8080/axis2/rest/StockQuoteService/update?symbol=IBM&price=100然后調用第一個getPrice url。你可以看到price被更新了。
使用AXIOM構建服務為了使用AXIOM"從零開始"構建一個服務,執行以下步驟。
注意包含在/samples/quickstartaxiom的目錄結構:
- -?quickstartaxiom??
- ???-?README.txt??
- ???-?build.xml??
- ???-?resources??
- ?????-?META-INF??
- ???????-?services.xml??
- ???????-?StockQuoteService.wsdl??
- ???-?src??
- ?????-?samples??
- ???????-?quickstart??
- ?????????-?service??
- ???????????-?axiom??
- ?????????????-?StockQuoteService.java??
- ?????????-?clients??
- ???????????-?AXIOMClient.java??
- quickstartaxiom
- README.txt
- build.xml
- resources
- META-INF
- services.xml
- StockQuoteService.wsdl
- src
- samples
- quickstart
- service
- axiom
- StockQuoteService.java
- clients
- AXIOMClient.java
由于AXIOM有一點不同,你將需要一個與POJO所用不同的services.xml文件,在Code Listing 4中顯示了它的定義。
Code Listing 4: 服務定義文件
- <service?name="StockQuoteService"?scope="application">??
- ????<description>??
- ????????Stock?Quote?Service??
- ????</description>??
- ????<operation?name="getPrice">??
- ????????<messageReceiver?class="org.apache.axis2.receivers.RawXMLINOutMessageReceiver"/>??
- ????</operation>??
- ????<operation?name="update">??
- ????????<messageReceiver?class="org.apache.axis2.receivers.RawXMLINOnlyMessageReceiver"/>??
- ????</operation>??
- ????<parameter?name="ServiceClass">samples.quickstart.service.axiom.StockQuoteService</parameter>??
- </service>??
<service name="StockQuoteService" scope="application">
<description>
Stock Quote Service
</description>
<operation name="getPrice">
<messageReceiver class="org.apache.axis2.receivers.RawXMLINOutMessageReceiver"/>
</operation>
<operation name="update">
<messageReceiver class="org.apache.axis2.receivers.RawXMLINOnlyMessageReceiver"/>
</operation>
<parameter name="ServiceClass">samples.quickstart.service.axiom.StockQuoteService</parameter>
</service>
注意,幾乎是一樣的,除了操作是顯示地定義在service.xml文件中,而且MessageReceiver現在是RawXML。
現在,上面提到的簡單的使用Axis2庫的類的StockQuoteService.java類,在Code Listing 5中定義。
Code Listing 5:使用AXIOM的StockQuoteService類
- package?samples.quickstart.service.axiom;??
- ??
- import?javax.xml.stream.XMLStreamException;??
- import?org.apache.axiom.om.OMAbstractFactory;??
- import?org.apache.axiom.om.OMElement;??
- import?org.apache.axiom.om.OMFactory;??
- import?org.apache.axiom.om.OMNamespace;??
- ??
- import?java.util.HashMap;??
- public?class?StockQuoteService?{??
- ????private?HashMap?map?=?new?HashMap();??
- ??
- ????public?OMElement?getPrice(OMElement?element)?throws?XMLStreamException?{??
- ????????element.build();??
- ????????element.detach();??
- ??
- ????????OMElement?symbolElement?=?element.getFirstElement();??
- ????????String?symbol?=?symbolElement.getText();??
- ??
- ????????String?returnText?=?"42";??
- ????????Double?price?=?(Double)?map.get(symbol);??
- ????????if(price?!=?null){??
- ????????????returnText??=?""?+?price.doubleValue();??
- ????????}??
- ????????OMFactory?fac?=?OMAbstractFactory.getOMFactory();??
- ????????OMNamespace?omNs?=??
- ????????????fac.createOMNamespace("http://axiom.service.quickstart.samples/xsd",?"tns");??
- ????????OMElement?method?=?fac.createOMElement("getPriceResponse",?omNs);??
- ????????OMElement?value?=?fac.createOMElement("price",?omNs);??
- ????????value.addChild(fac.createOMText(value,?returnText));??
- ????????method.addChild(value);??
- ????????return?method;??
- ????}??
- ??
- ????public?void?update(OMElement?element)?throws?XMLStreamException?{??
- ????????element.build();??
- ????????element.detach();??
- ??
- ????????OMElement?symbolElement?=?element.getFirstElement();??
- ????????String?symbol?=?symbolElement.getText();??
- ??
- ????????OMElement?priceElement?=?(OMElement)symbolElement.getNextOMSibling();??
- ????????String?price?=?priceElement.getText();??
- ??
- ????????map.put(symbol,?new?Double(price));??
- ????}??
- }??
package samples.quickstart.service.axiom;
import javax.xml.stream.XMLStreamException;
import org.apache.axiom.om.OMAbstractFactory;
import org.apache.axiom.om.OMElement;
import org.apache.axiom.om.OMFactory;
import org.apache.axiom.om.OMNamespace;
import java.util.HashMap;
public class StockQuoteService {
private HashMap map = new HashMap();
public OMElement getPrice(OMElement element) throws XMLStreamException {
element.build();
element.detach();
OMElement symbolElement = element.getFirstElement();
String symbol = symbolElement.getText();
String returnText = "42";
Double price = (Double) map.get(symbol);
if(price != null){
returnText = "" + price.doubleValue();
}
OMFactory fac = OMAbstractFactory.getOMFactory();
OMNamespace omNs =
fac.createOMNamespace("http://axiom.service.quickstart.samples/xsd", "tns");
OMElement method = fac.createOMElement("getPriceResponse", omNs);
OMElement value = fac.createOMElement("price", omNs);
value.addChild(fac.createOMText(value, returnText));
method.addChild(value);
return method;
}
public void update(OMElement element) throws XMLStreamException {
element.build();
element.detach();
OMElement symbolElement = element.getFirstElement();
String symbol = symbolElement.getText();
OMElement priceElement = (OMElement)symbolElement.getNextOMSibling();
String price = priceElement.getText();
map.put(symbol, new Double(price));
}
}
Axis2使用AXIOM,或者AXIs Object Model,一個基于StAX API(Streaming API for XML)的
DOM(Document Object Model)類似的結構
作為服務的方法必須使用OMElement作為它們的參數,OMElement表示一個XML元素,在這里它則為進來的SOAP消息的有效載荷。這里,
你提取有效載荷元素的第一個孩子,添加文本給它,并使用它作為返回的OMElement的內容。除非這是一個"只有in"的服務,這些方法
必須返回一個OMElement,因為它成為返回的SOAP消息的有效載荷。
現在通過在Axis2_HOME/samples/quickstartaxiom目錄鍵入
ant generate.service來構建工程。
把StockQuoteService.aar文件放在servlet引擎的webapps/axis2/WEB-INF/services目錄,通過視察下面的服務列表來確認服務正確
部署:
http://localhost:8080/axis2/services/listServices你也可以檢驗以下WSDL:
http://localhost:8080/axis2/services/StockQuoteService?wsdl以及以下結構:
http://localhost:8080/axis2/services/StockQuoteService?xsd使用ADB生成服務執行以下步驟來使用Axis2 Databinding Framework(ADB)生成和部署服務。
通過在Axis2_HOME/samples/quickstartadb目錄鍵入以下內容來使用WSDL2Java工具生成骨架:
%AXIS2_HOME%/bin/WSDL2Java -uri resources/META-INF/StockQuoteService.wsdl -p samples.quickstart.adb -d adb -s -ss
-sd -ssi -o build/service或者在Axis2_HOME/samples/quickstartadb目錄簡單的鍵入
ant generate.service選項-d adb指定了Axis Data Binding(ADB)。-s轉換指定同步或者只模塊化調用。-ss轉換創建服務器端代碼(骨架和相關文件)。-sd
轉換創建一個服務描述符(services.xml文件)。-ssi轉換為服務骨架創建一個接口。服務文件現在應該定位于build/service。
如果你通過使用WSDL2Java直接生成代碼,下一步你需要修改生成的骨架來實現服務(如果你使用"ant generate.service",一個完全
的骨架會自動復制并覆蓋生成的那個)。
打開build/service/src/samples/quickstart/adb/service/StockQuoteServiceSkeleton.java文件并修改它來添加你的服務的功能性
到生成的方法,下面的Code Listing 6顯示了。
Code Listing 6:定義服務骨架文件
- package?samples.quickstart.service.adb;??
- ??
- import?samples.quickstart.service.adb.xsd.GetPriceResponse;??
- import?samples.quickstart.service.adb.xsd.Update;??
- import?samples.quickstart.service.adb.xsd.GetPrice;??
- ??
- import?java.util.HashMap;??
- ??
- public?class?StockQuoteServiceSkeleton?{??
- ??
- ????private?static?HashMap?map;??
- ??
- ????static{?map?=?new?HashMap();?}??
- ??
- ????public?void?update(Update?param0)?{??
- ????????map.put(param0.getSymbol(),?new?Double(param0.getPrice()));??
- ????}??
- ??
- ????public?GetPriceResponse?getPrice(GetPrice?param1)?{??
- ????????Double?price?=?(Double)?map.get(param1.getSymbol());??
- ????????double?ret?=?42;??
- ????????if(price?!=?null){??
- ????????????ret?=?price.doubleValue();??
- ????????}??
- ????????GetPriceResponse?res?=??
- ????????????????new?GetPriceResponse();??
- ????????res.set_return(ret);??
- ????????return?res;??
- ????}??
- }??
package samples.quickstart.service.adb;
import samples.quickstart.service.adb.xsd.GetPriceResponse;
import samples.quickstart.service.adb.xsd.Update;
import samples.quickstart.service.adb.xsd.GetPrice;
import java.util.HashMap;
public class StockQuoteServiceSkeleton {
private static HashMap map;
static{ map = new HashMap(); }
public void update(Update param0) {
map.put(param0.getSymbol(), new Double(param0.getPrice()));
}
public GetPriceResponse getPrice(GetPrice param1) {
Double price = (Double) map.get(param1.getSymbol());
double ret = 42;
if(price != null){
ret = price.doubleValue();
}
GetPriceResponse res =
new GetPriceResponse();
res.set_return(ret);
return res;
}
}
現在你可以通過在build/service目錄鍵入以下命令構建工程:
ant jar.server如果一切進展順利,你應該在你的窗口看到BUILD SUCCESSFUL消息,而且StockQuoteService.aar文件在build/service/build/lib
目錄中。復制該文件到servlet引擎的webapps/axis2/WEB-INF/services目錄。
你可以通過視察下面的服務列表來確認服務正確部署:
http://localhost:8080/axis2/services/listServices你也可以檢驗以下WSDL:
http://localhost:8080/axis2/services/StockQuoteService?wsdl以及以下結構:
http://localhost:8080/axis2/services/StockQuoteService?xsd使用XMLBeans生成服務執行以下步驟來使用XMLBeans生成服務。
通過在Axis2_HOME/samples/quickstartxmlbeans目錄鍵入以下命令來使用WSDL2Java工具生成骨架:
%AXIS2_HOME%/bin/WSDL2Java -uri resources/META-INF/StockQuoteService.wsdl -p samples.quickstart.service.xmlbeans
-d xmlbeans -s -ss -sd -ssi -o build/service或者在Axis2_HOME/sampels/quickstartxmlbeans目錄簡單的鍵入
ant generate.service選項-d xmlbeans指定XMLBeans數據綁定。-s轉換指定同步或者只是模塊化調用。-ss轉換創建服務器端代碼(骨架和相關文件)。-sd
轉換創建一個服務描述符(services.xml文件)。-ssi轉換創建一個服務骨架的接口。現在服務文件應該位于build/service。
如果你通過使用WSDL2Java直接生成代碼,下一步你需要修改生成的骨架來實現服務(如果你使用"ant generate.service",一個完全
的骨架將被自動復制并覆蓋生成的那個)。
下一步打開build/service/src/samples/quickstart/service/xmlbeans/StockQuoteServiceSkeleton.java文件并修改它來添加你的
服務的功能性到生成的方法(參看Code Listing 7)。
Code Listing 7:定義服務骨架
- package?samples.quickstart.service.xmlbeans;??
- ??
- import?samples.quickstart.service.xmlbeans.xsd.GetPriceDocument;??
- import?samples.quickstart.service.xmlbeans.xsd.GetPriceResponseDocument;??
- import?samples.quickstart.service.xmlbeans.xsd.UpdateDocument;??
- ??
- import?java.util.HashMap;??
- ??
- public?class?StockQuoteServiceSkeleton?implements?StockQuoteServiceSkeletonInterface?{??
- ??
- ????private?static?HashMap?map;??
- ??
- ????static{?map?=?new?HashMap();?}??
- ??
- ????public?void?update(UpdateDocument?param0)?{??
- ????}??
- ??
- ????public?GetPriceResponseDocument?getPrice(GetPriceDocument?param1)?{??
- ????}??
- }??
package samples.quickstart.service.xmlbeans;
import samples.quickstart.service.xmlbeans.xsd.GetPriceDocument;
import samples.quickstart.service.xmlbeans.xsd.GetPriceResponseDocument;
import samples.quickstart.service.xmlbeans.xsd.UpdateDocument;
import java.util.HashMap;
public class StockQuoteServiceSkeleton implements StockQuoteServiceSkeletonInterface {
private static HashMap map;
static{ map = new HashMap(); }
public void update(UpdateDocument param0) {
}
public GetPriceResponseDocument getPrice(GetPriceDocument param1) {
}
}
通過在build/service目錄鍵入命令
ant jar.server構建項目,該目錄包含build.xml文件。
如果一切進展順利,你應該在你的窗口看到BUILD SUCCESSFUL消息,而且StockQuoteService.aar文件位于新創建的build/service/
build/lib目錄。復制該文件到servlet引擎的webapps/axis2/WEB-INF/services目錄。
你可以通過視察下面的服務列表來確認服務正確部署:
http://localhost:8080/axis2/services/listServices你也可以檢驗以下WSDL:
http://localhost:8080/axis2/services/StockQuoteService?wsdl以及以下結構:
http://localhost:8080/axis2/services/StockQuoteService?xsd使用JiBX生成服務執行以下步驟來使用
JiBX數據綁定生成和部署服務。
通過在Axis2_HOME/samples/quickstartjibx目錄的控制臺鍵入以下內容來使用WSDL2Java工具生成骨架:
%AXIS2_HOME%/bin/wsdl2java -uri resources/META-INF/StockQuoteService.wsdl -p samples.quickstart.service.jibx -d jibx
-s -ss -sd -ssi -uw -o build/service或者在Axis2_HOME/samples/quickstartjibx目錄簡單的鍵入"
ant generate.service"
選項-d jibx指定了JiBX數據綁定。-s轉換指定同步或者只是模塊化調用。-ss轉換創建服務器端代碼(骨架和相關文件)。-sd轉換創建
一個服務描述符(services.xml文件)。-ssi轉換創建服務骨架的接口。-uw轉換解開傳遞給服務操作和從服務操作傳遞出去的參數,來
創建一個更自然的編程接口。
在運行WSDL2Java后,服務文件應該位于build/service。如果你通過使用WSDL2Java直接生成代碼,下一步你需要修改生成的骨架來
實現服務(如果你使用"ant generate.service"則一個完全的骨架將自動被復制并覆蓋生成的那個)。打開build/service/src/samples
/quickstart/service/jibx/StockQuoteServiceSkeleton.java文件并修改它來添加你的服務的功能性到生成的方法,在Code Listing
8中顯示了。
Code Listing 8:定義服務骨架文件
- package?samples.quickstart.service.jibx;??
- ??
- import?java.util.HashMap;??
- ??
- public?class?StockQuoteServiceSkeleton?implements?StockQuoteServiceSkeletonInterface?{??
- ????private?HashMap?map?=?new?HashMap();??
- ??
- ????public?void?update(String?symbol,?Double?price)?{??
- ????????map.put(symbol,?price);??
- ????}??
- ??
- ????public?Double?getPrice(String?symbol)?{??
- ????????Double?ret?=?(Double)?map.get(symbol);??
- ????????if?(ret?==?null)?{??
- ????????????ret?=?new?Double(42.0);??
- ????????}??
- ????????return?ret;??
- ????}??
- }??
package samples.quickstart.service.jibx;
import java.util.HashMap;
public class StockQuoteServiceSkeleton implements StockQuoteServiceSkeletonInterface {
private HashMap map = new HashMap();
public void update(String symbol, Double price) {
map.put(symbol, price);
}
public Double getPrice(String symbol) {
Double ret = (Double) map.get(symbol);
if (ret == null) {
ret = new Double(42.0);
}
return ret;
}
}
現在你可以通過在build/service目錄鍵入命令
ant jar.server構建工程
如果一切進展順利,你應該在你的窗口看到BUILD SUCCESSFUL消息,并且StockQuoteService.aar文件位于build/service/build/lib
目錄。復制該文件到servlet引擎的webapps/axis2/WEB-INF/services目錄。
你可以通過視察下面的服務列表來確認服務正確部署:
http://localhost:8080/axis2/services/listServices你也可以檢驗以下WSDL:
http://localhost:8080/axis2/services/StockQuoteService?wsdl以及以下結構:
http://localhost:8080/axis2/services/StockQuoteService?xsd對于和Axis2使用JiBX的更多信息,參考[urlhttp://ws.apache.org/axis2/1_1_1/jibx/jibx-quotegen-integration.html]JiBX代碼生成集成[/url]。你也可以檢查
JiBX Axis2 Wiki頁面得到更多同Axis2使用
JiBX的更新信息。
創建客戶端在這個部分,我們將看看基于StockQuoteService類創建客戶端的四種方式:構建基于AXIOM的客戶端,使用Axis2 Databinding Frame
work(ADB)生成客戶端,使用XMLBeans生成客戶端,使用JiBX生成客戶端。
使用AXIOM創建一個客戶端執行以下步驟來使用AXIOM構建一個客戶端。
也注意在使用AXIOM創建服務部分顯示的目錄結構,為了完整性下面的重復了。
- -?quickstartaxiom??
- ???-?README.txt??
- ???-?build.xml??
- ???-?resources??
- ?????-?META-INF??
- ???????-?services.xml??
- ???????-?StockQuoteService.wsdl??
- ???-?src??
- ?????-?samples??
- ???????-?quickstart??
- ?????????-?service??
- ???????????-?axiom??
- ?????????????-?StockQuoteService.java??
- ?????????-?clients??
- ???????????-?AXIOMClient.java??
- quickstartaxiom
- README.txt
- build.xml
- resources
- META-INF
- services.xml
- StockQuoteService.wsdl
- src
- samples
- quickstart
- service
- axiom
- StockQuoteService.java
- clients
- AXIOMClient.java
上面提到的AXIOMClient.java類的定義顯示在下面的Code Listing 9。
Code Listing 9:使用AXIOM的AXIOMClient類
- package?samples.quickstart.clients;??
- ??
- import?org.apache.axiom.om.OMAbstractFactory;??
- import?org.apache.axiom.om.OMElement;??
- import?org.apache.axiom.om.OMFactory;??
- import?org.apache.axiom.om.OMNamespace;??
- import?org.apache.axis2.Constants;??
- import?org.apache.axis2.addressing.EndpointReference;??
- import?org.apache.axis2.client.Options;??
- import?org.apache.axis2.client.ServiceClient;??
- ??
- public?class?AXIOMClient?{??
- ??
- ????private?static?EndpointReference?targetEPR?=???
- ????????new?EndpointReference("http://localhost:8080/axis2/services/StockQuoteService");??
- ??
- ????public?static?OMElement?getPricePayload(String?symbol)?{??
- ????????OMFactory?fac?=?OMAbstractFactory.getOMFactory();??
- ????????OMNamespace?omNs?=?fac.createOMNamespace("http://axiom.service.quickstart.samples/xsd",?"tns");??
- ??
- ????????OMElement?method?=?fac.createOMElement("getPrice",?omNs);??
- ????????OMElement?value?=?fac.createOMElement("symbol",?omNs);??
- ????????value.addChild(fac.createOMText(value,?symbol));??
- ????????method.addChild(value);??
- ????????return?method;??
- ????}??
- ??
- ????public?static?OMElement?updatePayload(String?symbol,?double?price)?{??
- ????????OMFactory?fac?=?OMAbstractFactory.getOMFactory();??
- ????????OMNamespace?omNs?=?fac.createOMNamespace("http://axiom.service.quickstart.samples/xsd",?"tns");??
- ??
- ????????OMElement?method?=?fac.createOMElement("update",?omNs);??
- ??
- ????????OMElement?value1?=?fac.createOMElement("symbol",?omNs);??
- ????????value1.addChild(fac.createOMText(value1,?symbol));??
- ????????method.addChild(value1);??
- ??
- ????????OMElement?value2?=?fac.createOMElement("price",?omNs);??
- ????????value2.addChild(fac.createOMText(value2,??
- ?????????????????????????????????????????Double.toString(price)));??
- ????????method.addChild(value2);??
- ????????return?method;??
- ????}??
- ??
- ????public?static?void?main(String[]?args)?{??
- ????????try?{??
- ????????????OMElement?getPricePayload?=?getPricePayload("WSO");??
- ????????????OMElement?updatePayload?=?updatePayload("WSO",?123.42);??
- ????????????Options?options?=?new?Options();??
- ????????????options.setTo(targetEPR);??
- ????????????options.setTransportInProtocol(Constants.TRANSPORT_HTTP);??
- ??
- ????????????ServiceClient?sender?=?new?ServiceClient();??
- ????????????sender.setOptions(options);??
- ??
- ????????????sender.fireAndForget(updatePayload);??
- ????????????System.err.println("done");??
- ????????????OMElement?result?=?sender.sendReceive(getPricePayload);??
- ??
- ????????????String?response?=?result.getFirstElement().getText();??
- ????????????System.err.println("Current?price?of?WSO:?"?+?response);??
- ??
- ????????}?catch?(Exception?e)?{??
- ????????????e.printStackTrace();??
- ????????}??
- ????}??
- ??????
- }??
package samples.quickstart.clients;
import org.apache.axiom.om.OMAbstractFactory;
import org.apache.axiom.om.OMElement;
import org.apache.axiom.om.OMFactory;
import org.apache.axiom.om.OMNamespace;
import org.apache.axis2.Constants;
import org.apache.axis2.addressing.EndpointReference;
import org.apache.axis2.client.Options;
import org.apache.axis2.client.ServiceClient;
public class AXIOMClient {
private static EndpointReference targetEPR =
new EndpointReference("http://localhost:8080/axis2/services/StockQuoteService");
public static OMElement getPricePayload(String symbol) {
OMFactory fac = OMAbstractFactory.getOMFactory();
OMNamespace omNs = fac.createOMNamespace("http://axiom.service.quickstart.samples/xsd", "tns");
OMElement method = fac.createOMElement("getPrice", omNs);
OMElement value = fac.createOMElement("symbol", omNs);
value.addChild(fac.createOMText(value, symbol));
method.addChild(value);
return method;
}
public static OMElement updatePayload(String symbol, double price) {
OMFactory fac = OMAbstractFactory.getOMFactory();
OMNamespace omNs = fac.createOMNamespace("http://axiom.service.quickstart.samples/xsd", "tns");
OMElement method = fac.createOMElement("update", omNs);
OMElement value1 = fac.createOMElement("symbol", omNs);
value1.addChild(fac.createOMText(value1, symbol));
method.addChild(value1);
OMElement value2 = fac.createOMElement("price", omNs);
value2.addChild(fac.createOMText(value2,
Double.toString(price)));
method.addChild(value2);
return method;
}
public static void main(String[] args) {
try {
OMElement getPricePayload = getPricePayload("WSO");
OMElement updatePayload = updatePayload("WSO", 123.42);
Options options = new Options();
options.setTo(targetEPR);
options.setTransportInProtocol(Constants.TRANSPORT_HTTP);
ServiceClient sender = new ServiceClient();
sender.setOptions(options);
sender.fireAndForget(updatePayload);
System.err.println("done");
OMElement result = sender.sendReceive(getPricePayload);
String response = result.getFirstElement().getText();
System.err.println("Current price of WSO: " + response);
} catch (Exception e) {
e.printStackTrace();
}
}
}
Axis2使用AXIOM,或者AXIs Object Model,一個基于StAX API(Streaming API for XML)的DOM(Document Object Model)類似的結構
這里你為服務的update和getPrice方法建立有效載荷。有效載荷的創建類似于你為AXIOM服務創建getPriceResponse有效載荷。然后
你創建Options類,并創建用來與服務交流的ServiceClient。首先你調用update方法,一個什么也不返回的fireAndForget方法。最后
你調用getPrice方法,并從服務得到當前價格并顯示它。
現在你可以通過在Axis2_HOME/samples/quickstartaxiom目錄鍵入
ant run.client構建并運行AXIOM客戶端。
你應該得到以下輸出:
- done??
- Current?price?of?WSO:?123.42??
done
Current price of WSO: 123.42
使用ADB生成一個客戶端執行以下步驟來使用Axis Data Binding(ADB)構建一個客戶端。
通過在Axis2_HOME/samples/quickstartadb目錄鍵入以下命令來生成客戶端數據綁定:
%AXIS2_HOME%/bin/WSDL2Java -uri resources/META-INF/StockQuoteService.wsdl -p samples.quickstart.clients -d adb -s
-o build/client或者在Axis2_HOME/samples/quickstartadb目錄簡單的鍵入
ant generate.client。
下一步看看quickstartadb/src/samples/quickstart/clients/ADBClient.java,并看看它在Code Listing 10中是怎樣定義的。
Code Listing 10:ADBClient類
- package?samples.quickstart.clients;??
- ??
- import?samples.quickstart.service.adb.StockQuoteServiceStub;??
- ??
- public?class?ADBClient{??
- ????public?static?void?main(java.lang.String?args[]){??
- ????????try{??
- ????????????StockQuoteServiceStub?stub?=??
- ????????????????new?StockQuoteServiceStub??
- ????????????????("http://localhost:8080/axis2/services/StockQuoteService");??
- ??
- ????????????getPrice(stub);??
- ????????????update(stub);??
- ??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- ??
- ??????
- ????public?static?void?update(StockQuoteServiceStub?stub){??
- ????????try{??
- ????????????StockQuoteServiceStub.Update?req?=?new?StockQuoteServiceStub.Update();??
- ????????????req.setSymbol?("ABC");??
- ????????????req.setPrice?(42.35);??
- ??
- ????????????stub.update(req);??
- ????????????System.err.println("done");??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- ??
- ??????
- ????public?static?void?getPrice(StockQuoteServiceStub?stub){??
- ????????try{??
- ????????????StockQuoteServiceStub.GetPrice?req?=?new?StockQuoteServiceStub.GetPrice();??
- ??
- ????????????req.setSymbol("ABC");??
- ??
- ????????????StockQuoteServiceStub.GetPriceResponse?res?=??
- ????????????????stub.getPrice(req);??
- ??
- ????????????System.err.println(res.get_return());??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- ??
- }??
package samples.quickstart.clients;
import samples.quickstart.service.adb.StockQuoteServiceStub;
public class ADBClient{
public static void main(java.lang.String args[]){
try{
StockQuoteServiceStub stub =
new StockQuoteServiceStub
("http://localhost:8080/axis2/services/StockQuoteService");
getPrice(stub);
update(stub);
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
/* fire and forget */
public static void update(StockQuoteServiceStub stub){
try{
StockQuoteServiceStub.Update req = new StockQuoteServiceStub.Update();
req.setSymbol ("ABC");
req.setPrice (42.35);
stub.update(req);
System.err.println("done");
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
/* two way call/receive */
public static void getPrice(StockQuoteServiceStub stub){
try{
StockQuoteServiceStub.GetPrice req = new StockQuoteServiceStub.GetPrice();
req.setSymbol("ABC");
StockQuoteServiceStub.GetPriceResponse res =
stub.getPrice(req);
System.err.println(res.get_return());
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
}
該類使用你創建的Axis Data Bindings創建一個客戶端存根。然后它在Web服務上調用getPrice和update操作。getPrice方法操作創建
GetPrice有效載荷并設置symbol為ABC。然后它發送請求并顯示當前價格。update方法創建一個Update有效載荷,設置symbol為ABC及
price為42.35。
現在通過在Axis2_HOME/samples/quickstartadb目錄鍵入
ant run.client來構建并運行客戶端。
你應該得到以下輸出:
42
done
使用XMLBeans生成一個客戶端執行以下步驟來使用XMLBeans數據綁定來構建一個客戶端。
通過在xmlbeansClient目錄鍵入以下命令來生成數據綁定:
%AXIS2_HOME%/bin/WSDL2Java -uri resources/META-INF/StockQuoteService.wsdl -p samples.quickstart.service.xmlbeans -d
xmlbeans -s -o build/client或者簡單的在Axis2_HOME/samples/quickstartxmlbeans目錄下鍵入
ant generate.client。
注意這只會創建客戶端存根代碼而不會創建服務器端代碼。
下一步看看quickstartxmlbeans/src/samples/quickstart/clients/XMLBEANSClient.java,并在Code Listing 11看看它怎樣定義的
Code Listing 11:XMLBEANSClient類
- package?samples.quickstart.clients;??
- ??
- import?samples.quickstart.service.xmlbeans.StockQuoteServiceStub;??
- import?samples.quickstart.service.xmlbeans.xsd.GetPriceDocument;??
- import?samples.quickstart.service.xmlbeans.xsd.GetPriceResponseDocument;??
- import?samples.quickstart.service.xmlbeans.xsd.UpdateDocument;??
- ??
- public?class?XMLBEANSClient{??
- ??
- ????public?static?void?main(java.lang.String?args[]){??
- ????????try{??
- ????????????StockQuoteServiceStub?stub?=??
- ????????????????new?StockQuoteServiceStub??
- ????????????????("http://localhost:8080/axis2/services/StockQuoteService");??
- ??
- ????????????getPrice(stub);??
- ????????????update(stub);??
- ??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- ??
- ??????
- ????public?static?void?update(StockQuoteServiceStub?stub){??
- ????????try{??
- ????????????UpdateDocument?reqDoc?=?UpdateDocument.Factory.newInstance();??
- ????????????UpdateDocument.Update?req?=?reqDoc.addNewUpdate();??
- ????????????req.setSymbol?("ABC");??
- ????????????req.setPrice?(42.32);??
- ??
- ????????????stub.update(reqDoc);??
- ????????????System.err.println("done");??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- ??
- ??????
- ????public?static?void?getPrice(StockQuoteServiceStub?stub){??
- ????????try{??
- ????????????GetPriceDocument?reqDoc?=?GetPriceDocument.Factory.newInstance();??
- ????????????GetPriceDocument.GetPrice?req?=?reqDoc.addNewGetPrice();??
- ????????????req.setSymbol("ABC");??
- ??
- ????????????GetPriceResponseDocument?res?=??
- ????????????????stub.getPrice(reqDoc);??
- ??
- ????????????System.err.println(res.getGetPriceResponse().getReturn());??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- }??
package samples.quickstart.clients;
import samples.quickstart.service.xmlbeans.StockQuoteServiceStub;
import samples.quickstart.service.xmlbeans.xsd.GetPriceDocument;
import samples.quickstart.service.xmlbeans.xsd.GetPriceResponseDocument;
import samples.quickstart.service.xmlbeans.xsd.UpdateDocument;
public class XMLBEANSClient{
public static void main(java.lang.String args[]){
try{
StockQuoteServiceStub stub =
new StockQuoteServiceStub
("http://localhost:8080/axis2/services/StockQuoteService");
getPrice(stub);
update(stub);
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
/* fire and forget */
public static void update(StockQuoteServiceStub stub){
try{
UpdateDocument reqDoc = UpdateDocument.Factory.newInstance();
UpdateDocument.Update req = reqDoc.addNewUpdate();
req.setSymbol ("ABC");
req.setPrice (42.32);
stub.update(reqDoc);
System.err.println("done");
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
/* two way call/receive */
public static void getPrice(StockQuoteServiceStub stub){
try{
GetPriceDocument reqDoc = GetPriceDocument.Factory.newInstance();
GetPriceDocument.GetPrice req = reqDoc.addNewGetPrice();
req.setSymbol("ABC");
GetPriceResponseDocument res =
stub.getPrice(reqDoc);
System.err.println(res.getGetPriceResponse().getReturn());
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
}
該類使用你創建的XMLBeans數據綁定創建一個客戶端存根,然后它在Web服務上調用getPrice和update操作。getPrice方法操作創建
GetPriceDocument,它內部的GetPrice類,并設置symbol為ABC。然后它發送請求并得到GetPriceResponseDocument并顯示當前price
update方法創建一個UpdateDocument和Update并設置symbol為ABC及price為42.32,當完成時顯示done。
現在通過在Axis2_HOME/samples/quickstartxmlbeans目錄鍵入
ant run.client構建并運行工程。
你應該得到下列輸出:
42
done
使用JiBX生成一個客戶端執行以下步驟來使用JiBX構建一個客戶端。
通過在Axis2_HOME/samples/quickstartjibx目錄的控制臺鍵入以下命令來生成客戶端存根:
- %AXIS2_HOME%/bin/wsdl2java?-uri?resources/META-INF/StockQuoteService.wsdl?-p?samples.quickstart.clients?-d?jibx?-s??
- -uw?-o?build/client??
%AXIS2_HOME%/bin/wsdl2java -uri resources/META-INF/StockQuoteService.wsdl -p samples.quickstart.clients -d jibx -s
-uw -o build/client
或者簡單的鍵入"
ant generate.client"。
下一步看看quickstartjibx/src/samples/quickstart/clients/JiBXClient.java,在Code Listing 12顯示了。
Code Listing 12:JiBXClient類
- package?samples.quickstart.clients;??
- ??
- import?samples.quickstart.service.jibx.StockQuoteServiceStub;??
- ??
- public?class?JiBXClient{??
- ????public?static?void?main(java.lang.String?args[]){??
- ????????try{??
- ????????????StockQuoteServiceStub?stub?=??
- ????????????????new?StockQuoteServiceStub??
- ????????????????("http://localhost:8080/axis2/services/StockQuoteService");??
- ??
- ????????????getPrice(stub);??
- ????????????update(stub);??
- ??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- ??
- ??????
- ????public?static?void?update(StockQuoteServiceStub?stub){??
- ????????try{??
- ????????????stub.update("ABC",?new?Double(42.35));??
- ????????????System.err.println("done");??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- ??
- ??????
- ????public?static?void?getPrice(StockQuoteServiceStub?stub){??
- ????????try{??
- ????????????System.err.println(stub.getPrice("ABC"));??
- ????????}?catch(Exception?e){??
- ????????????e.printStackTrace();??
- ????????????System.err.println("\n\n\n");??
- ????????}??
- ????}??
- ??
- }??
package samples.quickstart.clients;
import samples.quickstart.service.jibx.StockQuoteServiceStub;
public class JiBXClient{
public static void main(java.lang.String args[]){
try{
StockQuoteServiceStub stub =
new StockQuoteServiceStub
("http://localhost:8080/axis2/services/StockQuoteService");
getPrice(stub);
update(stub);
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
/* fire and forget */
public static void update(StockQuoteServiceStub stub){
try{
stub.update("ABC", new Double(42.35));
System.err.println("done");
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
/* two way call/receive */
public static void getPrice(StockQuoteServiceStub stub){
try{
System.err.println(stub.getPrice("ABC"));
} catch(Exception e){
e.printStackTrace();
System.err.println("\n\n\n");
}
}
}
該類使用創建的JiBX客戶端存根在Web服務上訪問getPrice和update操作。getPrice方法為股票"ABC"發送請求并顯示當前price。
update方法為股票"ABC"設置價格為42.35。
現在通過在Axis2_HOME/samples/quickstartjibx目錄的控制臺鍵入"[b]ant run.client[b]"來構建并運行客戶端。
你應該得到以下輸出:
42
done
參考
JiBX代碼生成集成來得到更多關于同Axis2使用JiBX的信息細節。
總結Axis2是一個立刻讓web服務運行起來的靈活和健壯的方式。本指南呈現了創建一個可以在Axis2上部署的服務的五種方法。現在你擁有
了使用多種不同技術來創建Web服務的靈活性。
進一步學習Apache Axis2-
http://ws.apache.org/axis2/Axis2 Architecture-
http://ws.apache.org/axis2/1_0/Axis2ArchitectureGuide.htmlIntroduction to Apache Axis2-
http://www.redhat.com/magazine/021jul06/features/apache_axis2/Working With Apache Axis2-
http://www.wso2.net/articles/axis2/java/2006/09/13/working-with-axis2