使用Axis部署Web服務時的常見問題及其解決方法(轉)
![]() |
|
劉紅濤 (redwaveht@hotmail.com)
2003 年 11 月
本文詳細介紹了在Linux環(huán)境下以Apache Axis+ Resin作為Web服務平臺部署Web服務時的常見問題及解決方法。衷心希望本文對Web服務的開發(fā)人員或對Web服務感興趣的讀者能起到一定的幫助作用。
1 引言
隨著Web服務技術的發(fā)展和成熟,其方便性和易用性已逐漸被人們所接受,越來越多的合作伙伴之間開始利用Web服務來實現(xiàn)合作方之間的數(shù)據(jù)接口。使用Apache Axis和Linux平臺是一種低成本的Web服務解決方案,但Apache Axis文檔的FAQ對開發(fā)者來說內(nèi)容還不夠豐富,本文作者將自己使用Axis時遇到的問題和解決方法整理成文,奉獻給Web服務的開發(fā)人員和對此感興趣的讀者朋友,旨在幫助大家節(jié)約一些寶貴的時間。有關Web服務的基礎知識,讀者可以閱讀參考文獻中推薦的文檔。作者未在文中介紹Apache和Resin的安裝方法,讀者可以參考相關網(wǎng)站的說明文檔。
作者使用的軟件環(huán)境如下。
操作系統(tǒng):Red Hat Linux 7.2
Web服務器: Apache 1.3.27
應用服務器:Resin 2.1.8 ( http://www.caucho.com/ )
SOAP服務器:Apache Axis 1.1
XML解析器:Xerces 2.5.0,Xalan 2.5.1
JDK版本:JDK 1.4.1
2.1 Axis運行需要哪些jar文件
對Axis解包后,將axis-1_1/webapps/axis/WEB-INF/lib/目錄下的jar文件復制到/usr/local/apache/htdocs/WEB-INF/lib目錄下(Web應用程序的目錄)。應包括以下jar文件。
|
如果需要使用axis提供的測試頁面,還要將axis-1_1/webapps/axis/目錄下的文件復制到/usr/local/apache/htdocs/axis/目錄下。應包括以下文件。
|
2.2 應該使用哪一種XML解析器
XML解析器選用不當,經(jīng)常會導致使用Apache Axis時出現(xiàn)一些莫名其妙的問題。
由于Apache Axis 并未對Resin內(nèi)置的xml解析器進行過測試,因此推薦讀者使用已通過測試的Xerces xml解析器。可以從 http://xml.apache.org/xalan-j/index.html 處下載Xalan的Java版XSLT處理器,其中包含了Xerces的Java版XML解析器,不需要再單獨下載xml解析器。
Xalan 2.5.1解包后,將bin/目錄下的xercesImpl.jar、xml-apis.jar和xalan.jar復制到resin安裝目錄的lib/目錄下,例如/usr/local/resin/lib。
編輯/etc/目錄下的profile文件,找到設置CLASSPATH環(huán)境變量的位置,在其后加入下面的內(nèi)容(B shell)。
|
2.2.1 注意事項
如果CLASSPATH中包含其它的XML解析器設置,應將其從CLASSPATH環(huán)境變量的設置中去掉,以免發(fā)生沖突。
2.3 如何在Resin中使用Xerces的XML解析器
通過修改resin.conf將resin的XmlParser置換為Xerces的XmlParser。在resin.conf對應的Web應用程序配置中加入以下設置。
|
配置完成后重新啟動Resin。
2.4 如何排除XML解析器出現(xiàn)的異常
2.4.1 問題描述
使用http://test.com/axis查看已部署的服務時出現(xiàn)Axis內(nèi)部錯,顯示有關WSDD配置的異常信息。如果把WEB-INF目錄下的server-config.wsdd刪除,再查看就正常了,但只能看到AdminService和Version兩個系統(tǒng)缺省的服務,后來部署的服務都看不到了。
2.4.2 原因分析
Axis會在WEB應用程序的WEB-INF/目錄下自動生成一個名字為server-config.wsdd的xml文件,其中記錄了已部署的WEB服務。每部署一個新的WEB服務時,Axis都會將新服務的描述信息加入到server-config.wsdd中。
故障站點使用的XmlParser是resin內(nèi)置的XmlParser,Axis并未對其對進行過兼容性測試,查看WEB服務信息時需要從server-config.wsdd(這是一個xml文件)取得已部署的WEB服務描述信息,當server-config.wsdd的內(nèi)容較復雜時,resin內(nèi)置的XmlParser因某種原因出現(xiàn)異常,導致Axis內(nèi)部錯誤。Server-config.wsdd中記錄的Web服務描述信息較少時不會出現(xiàn)異常。
2.4.3 解決方法
修改resin.conf,將resin的XmlParser置換為Xerces的XmlParser。置換方法參見2.3節(jié)。
2.4.4 小結
如果Axis報告的錯誤中有關于xml解析器的錯誤,建議讀者參照本小節(jié)描述的方法更換應用服務器的xml解析器,將會有助于問題的解決。
2.5 如何將Axis集成到Resin或其它應用服務器
Axis是以Servlet的方式運行的,而Resin的作用相當于Servlets容器(Container),因此只要配置得當,就可以使Axis在Resin環(huán)境中運行,這一點也適用于Resin以外的其它應用服務器。在Resin中配置Axis的方法如下。
將axis-1_1/webapps/axis/WEB-INF/web.xml中的Servlet配置項復制到resin.conf中對應的Web應用程序配置中。通常應包括以下內(nèi)容。
|
2.6 Axis提供了哪些開發(fā)工具
Apache Axis提供了WSDL2Java和Java2WSDL兩個開發(fā)工具。
WSDL2Java利用已知的WSDL文件生成服務端和客戶端代碼。該WSDL文件可以是由合作伙伴提供的,也可以是利用Java2WSDL生成的。Java2WSDL根據(jù)已有的Java類文件生成WSDL文件,Java類文件可以是接口類文件,并不需要實現(xiàn)細節(jié)。
此外Axis還提供了SoapMonitorApplet和TCPMon工具,可用于監(jiān)測Web服務。
2.7 如何生成Web服務的服務端和客戶端代碼
2.7.1 生成或取得WSDL文件
Java2WSDL是Axis提供的利用Java類文件得到WSDL文件的工具。類文件可以使用接口文件編譯生成,例如下面的接口文件SoftwarePrice.java。
|
編譯SoftwarePrice.java。
|
將SoftwarePrice.class復制到正確的package路徑下。
執(zhí)行下面的命令:
|
各參數(shù)的含義如下。
|
最后面的類文件包含了Web服務的接口。
該命令執(zhí)行后,將生成sp.wsdl文件。
如果按CLASSPATH的設置找不到指定的類文件,Axis將報告異常,如下所示。
|
如果出現(xiàn)上面的問題,請檢查是否已將有關類文件復制到正確的位置或CLASSPATH設置是否正確。
生成WSDL文件以后,就可以利用Axis提供的WSDL2Java工具生成Web服務的服務端代碼和客戶端代碼了。
2.7.1.1 注意事項
WSDL文件也可以由合作伙伴提供。這種情況下合作伙伴往往是Web服務的提供者或標準接口的制定者,開發(fā)者只要按照既定的WSDL文件生成客戶端或服務端代碼就可以了。
2.7.2 生成客戶端或服務端代碼
WSDL2Java工具用于從WSDL文件生成客戶端存根(stub)代碼,服務端框架(skeleton)代碼以及WSDL中的數(shù)據(jù)類型文件(生成與之對應的Java代碼)。開發(fā)人員只需向框架代碼中補充相關的業(yè)務邏輯代碼即可得到完整的Web服務代碼,因此該工具極大地減輕了開發(fā)人員的編碼負擔。WSDL2Java的使用舉例如下。
|
執(zhí)行上述命令后將生成下列文件。
No. | 文件 | 用途 |
1. | deploy.wsdd | MyService服務的部署描述文件 |
2. | MyService.java | MyService服務的接口文件 |
3. | MyServiceService.java | 獲得MyService服務的接口文件 |
4. | MyServiceServiceLocator.java | 實現(xiàn)MyServiceService接口 |
5. | MyServiceSoapBindingImpl.java | 實現(xiàn)MyService接口,應向其中補充業(yè)務邏輯 |
6. | MyServiceSoapBindingSkeleton.java | MyService服務的服務端框架代碼,實現(xiàn)MyService, org.apache.axis.wsdl.Skeleton接口 |
7. | MyServiceSoapBindingStub.java | MyService服務的客戶端存根代碼,實現(xiàn)MyService接口 |
8. | undeploy.wsdd | 注銷MyService服務的部署描述文件 |
2.7.3 編寫Web服務客戶端代碼
Web服務的客戶端程序完成對Web服務的調(diào)用,其程序結構如下。
|
測試客戶端程序是非常簡單的,將客戶端程序編譯后,執(zhí)行"java TestClient"即可。
2.8 如何編寫服務端代碼
向MyServiceSoapBindingImpl.java添加相關的業(yè)務邏輯代碼后,將WSDL2Java生成的源程序編譯,打包成jar文件,復制到/usr/local/apache/htdocs/WEB-INF/lib/目錄下。
2.9 如何發(fā)布Web服務
有了deploy.wsdd文件并準備好類文件后,就可以發(fā)布MyService服務了。Axis在安裝后自動發(fā)布了AdminService,利用它可以發(fā)布新的Web服務。方法如下。
|
2.10 執(zhí)行WSDL2Java時報告" 類型被引用但未定義"
2.10.1 問題描述
執(zhí)行WSDL2Java時報告下面的異常:
|
2.10.2 原因分析
出現(xiàn)上述情況可能的原因有:
類型未定義就被引用。
使用了錯誤的名字空間。
WSDL文件中存在輸入錯誤。
2.10.3 解決方法
經(jīng)過仔細檢查發(fā)現(xiàn)wsdl文件中的
|
的type=" s0:ArrayOfFailedRecord"中的s0:前面有一個空格,將空格刪除后問題解決了。
2.10.4 小結
WSDL文件中出現(xiàn)的編輯錯誤有可能導致執(zhí)行WSDL2Java時出現(xiàn)"類型被引用但未定義"錯誤。
2.11 server-config.wsdd的作用是什么
server-config.wsdd記錄了axis已發(fā)布的Web服務的描述信息。
2.12 發(fā)布Web服務時報告"Exception:: (404)Not Found"
2.12.1 問題描述
|
Apache的access_log顯示如下。
|
2.12.2 原因分析
出現(xiàn)這個問題的比較簡單的原因可能是端口不對,或URL路徑不對(例如路徑中多寫了目錄),Axis的SoapMonitor服務按指定的端口或URL找不到AdminService,需要檢查正確的端口號和URL路徑。
比較深層次的原因就復雜得多了。
本文作者遇到的是下面的情況。
AdminService是一個已發(fā)布的WEB服務。
AdminClient使用soap協(xié)議同AdminService通信,需要按指定的端口和URL定位AdminService,而原來使用的resin.conf中,有兩個web-app配置項,配置A的摘要如下所示。
|
配置B的摘要如下所示。
|
Axis的有關配置在配置B中。
Httpd.conf中的DocumentRoot是/usr/local/apache/htdocs/。
使用java org.apache.axis.client.AdminClient -lhttp://localhost:80/services/AdminService deploy.wsdd發(fā)布WEB服務時,需要按http協(xié)議解析url: //localhost:80/services/AdminService。由于htdocs/目錄下并沒有services/目錄(services是Axis在resin.conf中的servlet-mapping),因此應用服務器按resin.conf中的配置去定位AdminService ,因為url的主機名為localhost,因此resin不會到<host id='test.com'>(配置B)中去定位url,而是到配置A中去定位,在配置A中并沒有Axis的配置,找不到與AdminService相關的url,因此報告了前面描述的異常情況。
2.12.3 解決方法
知道了原因后,按如下方法就可以解決了。
將配置B中全部關于Axis的配置移到配置A中,注意相應地要改變/etc/profile中的CLASSPATH變量的值。
保存resin.conf后,重新登錄服務器(使新的CLASSPATH生效),重新啟動resin。再次發(fā)布WEB服務。
|
屏幕顯示如下。
|
WEB服務終于發(fā)布成功了。
在發(fā)布成功的情況下apache的access_log中會看到如下的log:
|
2.12.4 小結
本小節(jié)描述的問題可能是讀者遇到的出現(xiàn)最多的異常,但原因并不是唯一的。遇到該問題時,建議讀者冷靜分析出現(xiàn)問題的可能原因,多實驗幾種解決方法,最終一定可以成功!
2.13 如何監(jiān)測SOAP請求和響應流
2.13.1 引言
發(fā)布了Web服務以后,如何觀察請求和響應數(shù)據(jù)呢?記錄運行日志是一種傳統(tǒng)且有效的方法,但對于調(diào)試程序來講還不夠方便和直觀。值得欣慰的是,Axis為我們提供了在客戶端觀察SOAP請求和響應流數(shù)據(jù)的工具SoapMonitor,經(jīng)過適當配置后,可以實時地觀察到Web服務的SOAP請求和響應數(shù)據(jù)。SoapMonitor是一個Java Applet程序,通過瀏覽器下載到客戶端運行。下面就介紹SoapMonitor的配置和使用方法。
2.13.2 準備SOAPMonitor 小應用程序
在Axis 1.1中,沒有為我們編譯SOAPMonitor.java程序,但我們可以在axis-1_1/webapps/axis/目錄下找到名字為SOAPMonitorApplet.java的源程序文件,自己進行編譯。該程序編譯后,會生成如下的類文件:
|
讀者需要把上述類文件復制到自己的Web應用程序目錄下,本例中是/usr/local/apache/htdocs/目錄。
在瀏覽器地址樣中輸入SOAPMonitor的地址,例如 http://test.com/SOAPMonitor ,瀏覽器會提示用戶正在下載Applet程序,下載完畢后,讀者可以在瀏覽器窗口中看到如圖4-1所示的用戶界面。如果上述類文件的位置不正確,瀏覽器會報告"找不到類"的錯誤。此時應檢查是否已將上述類文件復制到正確的目錄下。
圖 2-1 SOAPMonitor的界面
2.13.3 發(fā)布SOAPMonitor服務
圖2-1所示的SOAPMonitor界面出現(xiàn)后,并不意味著就可以觀察到Web服務的SOAP請求流與響應流了,首先需要發(fā)布SOAPMonitorService。該Web服務是由Axis提供的,但需要由用戶自己進行發(fā)布,方法如下。
獲得SOAPMonitor服務的WSDD文件deploy.wsdd,內(nèi)容如下(也可到 http://www.sosnoski.com/presents/java-xml/axis/axis-monitor.html 復制該文件):
|
發(fā)布SOAPMonitor服務:
|
2.13.4 修改deploy.wsdd
發(fā)布SOAPMonitor服務后,還要對被監(jiān)測的Web服務進行配置。方法是先注銷該Web服務,然后修改該服務對應的WSDD文件,在其中增加請求流和響應流的配置,否則是觀測不到SOAP請求和響應流的。
注銷Web服務的方法如下。
進入該Web服務的undeploy.wsdd文件所在的目錄,執(zhí)行
|
修改WSDD文件的方法如下。
以Axis提供的MyService為例,對MyService的WSDD文件做如下修改。
修改前:
|
修改后: (有下劃線的行是新加入的內(nèi)容)
|
修改WSDD文件后,重新發(fā)布MyService服務:
|
2.13.5 啟動SOAPMonitor小應用程序
按2.13.2節(jié)介紹的方法啟動SOAPMonitor小應用程序。
使用客戶端程序測試MyService服務:
|
注意,一定要先啟動SOAPMonitor小應用程序,后調(diào)用Web服務才能觀察到SOAP請求和響應流。
2.13.6 觀察SOAP請求和響應流
這時在SoapMonitorApplet的窗口中可以觀察到SOAP和請求和響應消息,如圖2-2所示。
圖2-2 MyService的Soap請求和響應流
2.14 使用客戶端程序測試Web服務時報告"Exception:: (404)Not Found"
2.14.1 問題描述
WEB服務接口編寫完成并發(fā)布后,客戶端測試程序收不到WEB服務的返回結果,Apache或Resin的log中也看不到訪問記錄。但測試程序返回結果為0(成功),在沒有部署該WEB服務的情況下,也是這個結果,因此懷疑調(diào)用的是WSDL文件的提供者自己測試用的WEB服務接口,可能與另一方提供的WSDL文件有關。
2.14.2 原因分析
合作伙伴調(diào)用WEB服務就能夠成功,從WEB服務主機自己的客戶端調(diào)用就接收不到數(shù)據(jù),估計與合作伙伴提供的WSDL文件有關,該WSDL文件影響了WSDL2Java生成的客戶端stub代碼。檢查stub代碼,發(fā)現(xiàn)其soapAction都指向了合作伙伴的測試地址。
2.14.3 解決方法
修改stub代碼中的soapAction,改為sp(Service Provider)自己的WEB服務URL。重新編譯程序并發(fā)布Web服務,問題解決。
_call.setSOAPActionURI("sp自己的Web服務地址");
2.14.4 小結
本小節(jié)描述的問題出現(xiàn)于Web服務提供方按合作伙伴統(tǒng)一提供的WSDL文件生成客戶端代碼的情況。遇到這類問題,讀者可直接檢查WSDL2Java自動生成的代碼的有關部分。
在WSDL文件中可以看到與下列內(nèi)容相似的設置。
|
其中
2.15 如何列出已發(fā)布的Web服務
使用下面的命令:
|
實際上該命令的輸出就是server-config.wsdd文件的內(nèi)容。
2.16 發(fā)布Web服務時報告"調(diào)用目標異常"
2.16.1 問題描述
在部署WEB服務時報告:java.lang.reflect.InvocationTargetException異常。
2.16.2 原因分析
在WSDL文件中自定義的名字空間與Axis的services名字空間沖突。
2.16.3 解決方法
修改WSDL文件,將services改為別的名字。
2.17 WSDL文件中的targetNamespace的作用是什么
TargetNamespace指明目標名字空間,用于驗證xml文檔。
在WSDL文件中,<definitions>中的targetNamespace與<types>中的targetNamespace應保持一致。
2.18 Web服務部署成功但檢測不到
2.19 客戶端程序找不到可用的Web服務
2.19.1 問題描述
|
時顯示<Admin>Done processing</Admin>,卻檢查不到新的服務,在WEB-INF/目錄下的server-config.wsdd文件中也看不到相應的配置項。
2.19.2 原因分析
新的WEB服務的類文件沒有重新編譯并復制到正確的位置。
2.19.3 解決方法
WEB服務的類文件可以打包為jar文件。在CLASSPATH環(huán)境變量中正確設置jar文件的路徑。例如:
|
將SPInterfaceSoap.jar復制到WEB-INF/lib/目錄下,重新發(fā)布WEB服務。
2.20 如何排除原因不明的錯誤
有時,在對WEB服務執(zhí)行客戶端測試時會出現(xiàn)慕名其妙的錯誤。為保證環(huán)境是正確的,可以按下面的步驟排除原因不明的錯誤。
1. Undeploy被測試的服務
|
2. 重新啟動resin: /usr/local/resin/bin/httpd.sh restart(如果是其它的應用服務器,請按相應的方法重新啟動)
3. 重新發(fā)布WEB服務
4. 進行測試
3 小結
目前有很多可以使用的應用服務器和Web服務平臺軟件,本文僅以Apache Axis和Resin為例介紹了在部署Web服務的過程中可能遇到的問題及其解決方法,其中并未討論Web服務的安全性問題。對于如何高效地開發(fā)和部署Web服務以及如何確保Web服務的安全性,還希望對此感興趣的讀者共同參與討論,對于文中存在的錯誤和不足之處也希望讀者朋友們能夠不吝批評指正。
posted on 2005-02-24 10:19 Victor 閱讀(2533) 評論(0) 編輯 收藏 所屬分類: web services