|
一、Axis簡介
1. 什么是SOAP
SOAP是一個基于XML的用于應(yīng)用程序之間通信數(shù)據(jù)編碼的傳輸協(xié)議。最初由微軟和Userland Software提出,隨著不斷地完善和改進,SOAP很快被業(yè)界廣泛應(yīng)用,目前完全發(fā)布版本是1.1。在其發(fā)展過程中,W3C XML標準工作小組積極促成SOAP成為一個真正的開放標準。在寫作此文檔之時,SOAP1.2草案已經(jīng)發(fā)布,1.2對1.1中相對混亂的部分做了改進。 SOAP被廣泛作為新一代跨平臺、跨語言分布計算Web Services的重要部分。
2. 什么是Axis
Axis是Apache組織推出的SOAP引擎,Axis項目是Apache組織著名的SOAP項目的后繼項目,目前最新版本是采用Java開發(fā)的1.1版本,C++的版本正在開發(fā)之中。Axis v1.1軟件包可以從http://ws./axis/dist/1_1/下載得到。 但是Axis不僅僅是一個SOAP引擎,它還包括: 一個獨立運行的SOAP服務(wù)器 一個servlet引擎的插件,這個servlet引擎可以是Tomcat 對WSDL的擴展支持 一個將WSDL的描述生成JAVA類的工具 一些示例代碼 還有一個監(jiān)控TCP/IP包的工具 二、Axis的安裝
應(yīng)用Axis開發(fā)Web Services,你需要安裝如下軟件: 1.JDK1.4.2 2.一個支持Servlet的服務(wù)器引擎,比如廣為人知的Tomcat。
當安裝好Tomcat之后,只需將下載的Axis軟件包解壓縮,將其中的“webapps”目錄下的“axis”目錄整個拷貝到Tomcat安裝目錄下的“webapps”目錄下即可。
三、Axis的配置
Axis基于Java開發(fā),可以部署于多種操作系統(tǒng),使用前需要配置一系列的系統(tǒng)變量,在此假定你已經(jīng)在本機上裝好了Tomcat 4.0以上的版本,需要配置的系統(tǒng)變量如下表所示:
CATALINA_HOME C:\Tomcat_4_1
(此處應(yīng)為Tomcat的安裝位置,注意路徑名中不要有空格)
AXIS_HOME %CATALINA_HOME%\webapps\axis
AXIS_LIB %AXIS_HOME%\lib
AXISCLASSPATH %AXIS_LIB%\axis.jar;%AXIS_LIB%\commons-discovery.jar; %AXIS_LIB%\commons-logging.jar;%AXIS_LIB%\jaxrpc.jar; %AXIS_LIB%\saaj.jar;%AXIS_LIB%\log4j-1.2.8.jar; %AXIS_LIB%\xml-apis.jar;%AXIS_LIB%\xercesImpl.jar
CLASSPATH 中加入: %AXIS_LIB%\axis.jar;%AXIS_LIB%\commons-discovery.jar; %AXIS_LIB%\commons-logging.jar;%AXIS_LIB%\jaxrpc.jar; %AXIS_LIB%\saaj.jar;%AXIS_LIB%\log4j-1.2.8.jar; %AXIS_LIB%\xml-apis.jar;%AXIS_LIB%\xercesImpl.jar
四、Axis的測試
安裝配置完畢后,應(yīng)測試一下是否Axis可以正確運行了。
啟動Tomcat服務(wù)器,在瀏覽器中訪問http://localhost:8080/axis/happyaxis.jsp,如果頁面顯示有錯誤,則需要回頭檢查一下相關(guān)配置是否正確,如果瀏覽頁面能正確顯示出系統(tǒng)組件、屬性等參數(shù)配置信息,則表示安裝成功。現(xiàn)在可以開始開發(fā)你的Web Services應(yīng)用了。
五、服務(wù)的發(fā)布 Axis提供了兩種服務(wù)發(fā)布方式,一種是即時發(fā)布(Instant Deployment),一種是定制發(fā)布(Custom Deployment)。
1. 使用即時發(fā)布 Java Web Service(JWS)
對即時發(fā)布的支持是Axis的特色之一,使用即時發(fā)布使用戶只需有提供服務(wù)的Java類的源代碼,即可將其迅速發(fā)布成Web服務(wù)。每當用戶調(diào)用這類服務(wù)的時候,Axis會自動進行編譯,即使服務(wù)器重啟了也不必對其做任何處理,使用非常簡單快捷。
使用即時發(fā)布首先需要一個實現(xiàn)服務(wù)功能的Java源文件,將其擴展名改為.jws(Java Web Service的縮寫),然后將該文件放到“……\webapps\axis”目錄下即可。 在此給出一個從英里到公里的長度單位轉(zhuǎn)換的服務(wù),其源碼如下:
文件Distance.jws
public class Distance { public double convertMile2Kilometre( double mile ) { return mile * 1.609; //實現(xiàn)英里到公里的距離轉(zhuǎn)換 } }
將其放到“……\webapps\axis”目錄,通過訪問http://localhost:8080/axis/Distance.jws?wsdl可以看到這個服務(wù)的WSDL描述文件,這說明Distance服務(wù)被成功發(fā)布了。描述的WDSL代碼如下: <?xml version="1.0" encoding="UTF-8" ?> - <wsdl:definitions targetNamespace="http://192.168.0.26:8080/axis/Distance.jws" xmlns="http://schemas./wsdl/" xmlns:apachesoap="http://xml./xml-soap" xmlns:impl="http://192.168.0.26:8080/axis/Distance.jws" xmlns:intf="http://192.168.0.26:8080/axis/Distance.jws" xmlns:soapenc="http://schemas./soap/encoding/" xmlns:wsdl="http://schemas./wsdl/" xmlns:wsdlsoap="http://schemas./wsdl/soap/" xmlns:xsd="http://www./2001/XMLSchema"> - <wsdl:message name="convertMile2KilometreRequest"> <wsdl:part name="mile" type="xsd:double" /> </wsdl:message> - <wsdl:message name="convertMile2KilometreResponse"> <wsdl:part name="convertMile2KilometreReturn" type="xsd:double" /> </wsdl:message> - <wsdl:portType name="Distance"> - <wsdl:operation name="convertMile2Kilometre" parameterOrder="mile"> <wsdl:input message="impl:convertMile2KilometreRequest" name="convertMile2KilometreRequest" /> <wsdl:output message="impl:convertMile2KilometreResponse" name="convertMile2KilometreResponse" /> </wsdl:operation> </wsdl:portType> - <wsdl:binding name="DistanceSoapBinding" type="impl:Distance"> <wsdlsoap:binding style="rpc" transport="http://schemas./soap/http" /> - <wsdl:operation name="convertMile2Kilometre"> <wsdlsoap:operation soapAction="" /> - <wsdl:input name="convertMile2KilometreRequest"> <wsdlsoap:body encodingStyle="http://schemas./soap/encoding/" namespace="http://DefaultNamespace" use="encoded" /> </wsdl:input> - <wsdl:output name="convertMile2KilometreResponse"> <wsdlsoap:body encodingStyle="http://schemas./soap/encoding/" namespace="http://192.168.0.26:8080/axis/Distance.jws" use="encoded" /> </wsdl:output> </wsdl:operation> </wsdl:binding> - <wsdl:service name="DistanceService"> - <wsdl:port binding="impl:DistanceSoapBinding" name="Distance"> <wsdlsoap:address location="http://192.168.0.26:8080/axis/Distance.jws" /> </wsdl:port> </wsdl:service> </wsdl:definitions>
需要注意的是:JWS的web服務(wù)發(fā)布是一個很簡單的Web服務(wù)發(fā)布方式,在頁面中你不能使用包,而且由于代碼是在運行期被編譯的,所以在部署之后,你也很難找到錯誤所在。
2. 使用定制發(fā)布 Web Service Deployment Descriptor(WSDD)
即時發(fā)布是一項令人激動的技術(shù),它使Web服務(wù)的開發(fā)變得如此簡單;然而即時發(fā)布并不總是最好的選擇,比如有些應(yīng)用系統(tǒng)是第三方提供的,我們沒有購買源代碼,只有.class文件,但我們又希望將這個應(yīng)用系統(tǒng)的一些功能對外發(fā)布成Web服務(wù),使其能夠在更大范圍內(nèi)產(chǎn)生作用,這個時候即時發(fā)布技術(shù)就無能為力了。此外,即時發(fā)布技術(shù)并不靈活,無法進行更多的服務(wù)配置,這使得它并不能滿足一些特定系統(tǒng)的需求。
因此,Axis提供了另一種服務(wù)發(fā)布方式,這就是定制發(fā)布。
在此給出一個從加侖到升的容積單位轉(zhuǎn)換的服務(wù),其源碼如下:
文件Capacity.java package samples.capacity; public class Capacity { public double convertGallon2Litre( double gallon ) { return gallon * 4.546;//實現(xiàn)加侖到升的容積轉(zhuǎn)換 }//convertGallon2Litre()
}/* Capacity */ 將其編譯成.class文件,放置到“……\webapps\axis\samples\capacity”目錄下,即可著手進行發(fā)布。 定制發(fā)布不需要構(gòu)建.jws文件,但必須創(chuàng)建服務(wù)發(fā)布描述文件deploy.wsdd(Web Service Deployment Descriptor的縮寫),這個文件負責(zé)描述服務(wù)的名稱、入口等信息,其內(nèi)容如下: 文件deploy.wsdd
<deployment xmlns="http://xml./axis/wsdd/" xmlns:java="http://xml./axis/wsdd/providers/java"> <service name="Capacity" provider="java:RPC"> <parameter name="className" value="samples.capacity.Capacity"/> <parameter name="allowedMethods" value="*"/> </service> </deployment>
在這里服務(wù)的提供者是“java:RPC”,它被內(nèi)建在Axis中,而且指明了一個JAVA RPC服務(wù),做這個處理的類是org.apache.axis.providers.java.RPCProvider。 我們是通過一個<parameter>標簽告訴RPC服務(wù)應(yīng)該調(diào)用的類,而另外一個<parameter>標簽則告訴引擎,它可以調(diào)用這個類中的任何的Public方法。你也可以指定通過使用名字空間或者一些可以調(diào)用的方法列表,來指明那些方法可以被調(diào)用。
將該文件也放到“……\webapps\axis\samples\capacity”目錄下,然后可以采用Axis提供的一個客戶端管理工具——AdminClient來完成服務(wù)的定制發(fā)布。 在“……\webapps\axis\samples\capacity”目錄下,運行:
java -cp %AXISCLASSPATH% org.apache.axis.client.AdminClient deploy.wsdd
如果運行時說沒有找到類,那么可能是類路徑?jīng)]有配置好,建議將所有的與axis相關(guān)的jar都寫到classpath中去。這樣只要運行:
java org.apache.axis.client.AdminClient deploy.wsdd 可以看到以下運行結(jié)果:
Processing file deploy.wsdd <Admin>Doneprocessing</Admin>
這表明Capacity服務(wù)定制發(fā)布完成。 你也可以調(diào)用: java org.apache.axis.client.AdminClient undeploy.wsdd 來取消部署。
你也可以調(diào)用: java org.apache.axis.client.AdminClient list 來獲得所有的已經(jīng)部署的服務(wù)的列表。在這里你會看到services, handlers, transports等等,注意這個調(diào)用只是列出了WEB-INF\server-config.wsdd的文件內(nèi)容。
一定要注意:編譯后的class文件要拷貝到web-inf/classes的目錄中,如果該文件中有包存在的話,別忘了還要在classes目錄下創(chuàng)建包的目錄 通過訪問http://localhost:8080/axis/services/Capacity?wsdl可以看到這個服務(wù)的WSDL描述文件,這說明Capacity服務(wù)被成功發(fā)布了。 你也可以通過訪問http://localhost:8080/axis/servlet/AxisServlet查看所有定制發(fā)布的服務(wù)。 WDSL如下: <?xml version="1.0" encoding="UTF-8" ?> - <wsdl:definitions targetNamespace="http://localhost:8080/axis/services/Capacity" xmlns="http://schemas./wsdl/" xmlns:apachesoap="http://xml./xml-soap" xmlns:impl="http://localhost:8080/axis/services/Capacity" xmlns:intf="http://localhost:8080/axis/services/Capacity" xmlns:soapenc="http://schemas./soap/encoding/" xmlns:wsdl="http://schemas./wsdl/" xmlns:wsdlsoap="http://schemas./wsdl/soap/" xmlns:xsd="http://www./2001/XMLSchema"> - <wsdl:message name="convertGallon2LitreResponse"> <wsdl:part name="convertGallon2LitreReturn" type="xsd:double" /> </wsdl:message> - <wsdl:message name="convertGallon2LitreRequest"> <wsdl:part name="in0" type="xsd:double" /> </wsdl:message> - <wsdl:portType name="Capacity"> - <wsdl:operation name="convertGallon2Litre" parameterOrder="in0"> <wsdl:input message="impl:convertGallon2LitreRequest" name="convertGallon2LitreRequest" /> <wsdl:output message="impl:convertGallon2LitreResponse" name="convertGallon2LitreResponse" /> </wsdl:operation> </wsdl:portType> - <wsdl:binding name="CapacitySoapBinding" type="impl:Capacity"> <wsdlsoap:binding style="rpc" transport="http://schemas./soap/http" /> - <wsdl:operation name="convertGallon2Litre"> <wsdlsoap:operation soapAction="" /> - <wsdl:input name="convertGallon2LitreRequest"> <wsdlsoap:body encodingStyle="http://schemas./soap/encoding/" namespace="http://mples" use="encoded" /> </wsdl:input> - <wsdl:output name="convertGallon2LitreResponse"> <wsdlsoap:body encodingStyle="http://schemas./soap/encoding/" namespace="http://localhost:8080/axis/services/Capacity" use="encoded" /> </wsdl:output> </wsdl:operation> </wsdl:binding> - <wsdl:service name="CapacityService"> - <wsdl:port binding="impl:CapacitySoapBinding" name="Capacity"> <wsdlsoap:address location="http://localhost:8080/axis/services/Capacity" /> </wsdl:port> </wsdl:service> </wsdl:definitions>
WSDD 的高級功能: (1) AXIS支持三種對象范圍: "request"范圍:這是默認的情況,每一次Soap請求的時候都將創(chuàng)建新的對象。 "application"范圍:將會為所有的請求生成一個單獨的共享的對象。 "session"范圍:為每一個session期的客戶端請求創(chuàng)建一個對象。 指定方法如下: <service name="MyService"...> <parameter name="scope" value="value"/> ... </service> (2) 更多部署內(nèi)容:Handlers and Chains 讓我們來深入挖掘一下Axis引擎的更強大的特性。如果我們想跟蹤我們的服務(wù)被調(diào)用了多少次,那么我們只需要包含一個簡單的handler,它存放在samples/log目錄下。要使用這個handler,你就首先應(yīng)該部署這個handler,然后使用在部署服務(wù)時給它指定的名字。下面是一個wsdd文件的例子: <deployment xmlns="http://xml./axis/wsdd/" xmlns:java="http://xml./axis/wsdd/providers/java"> <!-- define the logging handler configuration --> <handler name="track" type="java:samples.userguide.example4.LogHandler"> <parameter name="filename" value="MyService.log"/> </handler> <!-- define the service, using the log handler we just defined --> <service name="LogTestService" provider="java:RPC"> <requestFlow> <handler type="track"/> </requestFlow> <parameter name="className" value="samples.userguide.example4.Service"/> <parameter name="allowedMethods" value="*"/> </service> </deployment>
第一段指明了一個名為track的handler,它是samples.userguide.example4.LogHandler類的實例。另外還指定了一個參數(shù)filename,用于指定日志文件名稱。 下面的那段指明了一個RPC服務(wù),和我們在上面的例子中看到的一樣,所不同的是在service標簽中的<requestFlow>標簽,它指定了一些在調(diào)用服務(wù)前應(yīng)該被調(diào)用的handler集。也就是由于我們在部署中插入了這個"track"的引用,所以我們確定每次調(diào)用服務(wù)的時候都將被記錄到日志文件中去。 (3)遠程管理: <service name="AdminService" provider="java:MSG"> <parameter name="className" value="org.apache.axis.util.Admin"/> <parameter name="allowedMethods" value="*"/> <parameter name="enableRemoteAdmin" value="true"/> </service> WARNING: enabling remote administration may give unauthorized parties access to your machine. If you do this, please make sure to add security to your configuration! 所以遠程管理涉及到安全問題,不建議采用。
|