Java與.NET 的Web Services相互調(diào)用
Posted on 2005-12-29 09:59 月亮的太陽(yáng) 閱讀(369) 評(píng)論(0) 編輯 收藏 所屬分類(lèi): 編程本文介紹了Java與.NET開(kāi)發(fā)的Web Services相互調(diào)用的技術(shù)。本文包括兩個(gè)部分,第一部分介紹了如何用.NET做客戶(hù)端調(diào)用Java寫(xiě)的Web Services,第二部分介紹了如何用Java做客戶(hù)端調(diào)用.NET開(kāi)發(fā)的Web Services。
二:項(xiàng)目需要的工具
Windows2000 Server(IIS)
Jbuilder9.0( 含有Tomcat , axis)
JDK1.4+Java Web Services Develop
VS.Net 2003
備注:如果沒(méi)有JBuilder的話(huà)就需要自己下載安裝Tomcat4.1 以及 Axis的開(kāi)發(fā)包,并做相應(yīng)配置。由于網(wǎng)上有很多這樣的文章,這里就不一一說(shuō)明了。
三:用.NET做客戶(hù)端調(diào)用Java寫(xiě)的Web Services
1. 生成一個(gè)Java Web Services
使用JBuilder 生成一個(gè)Web Services是非常簡(jiǎn)單的,我完全是按照它的幫助做的,只要一步步做下去就可以了。具體路徑是Developing Web Services -> tutorials : Web Services(Axis) -> Creating a simple Web Services
2. 發(fā)布這個(gè)Web Services并得到它的WSDL
Web Services生成好之后,F(xiàn)9運(yùn)行這個(gè)項(xiàng)目。然后,單擊View瀏覽現(xiàn)有的Web 服務(wù),單擊Bean1的WSDL連接,我們可以在瀏覽器中察看它的WSDL描述。在瀏覽器地址欄復(fù)制WSDL地址,為下一步使用.NET開(kāi)發(fā)客戶(hù)端調(diào)用程序做準(zhǔn)備。
3. 用VS.NET生成一個(gè).NET的客戶(hù)端
新建一個(gè)項(xiàng)目(WinForm,ASP.net都可以),我在這里使用的是一個(gè)Asp.Net項(xiàng)目。在起始頁(yè)面上放置一個(gè)文本輸入框用來(lái)顯示調(diào)用Web Services的結(jié)果,放置一個(gè)按鈕,用來(lái)單擊調(diào)用Web Services。然后,選擇添加Web 引用,在WSDL一欄中把剛才得到的WSDL地址復(fù)制過(guò)來(lái),Web 引用的名稱(chēng)輸入JavaService,單擊添加引用按鈕就可以了。此時(shí),我們可以在VS.net 的Solution Explore中看到這個(gè)Web 引用。
在按鈕的單擊事件中輸入下列代碼:
JavaService.Bean1 bean = new JavaService.Bean1();
TextBox1.Text = bean.getSample.ToString ();
這樣,一個(gè).NET客戶(hù)端就完成了,測(cè)試一下,工作正常,OK.
四:用Java做客戶(hù)端調(diào)用.NET寫(xiě)的 Web Services
有了上面的成功,使我以為用Java做客戶(hù)端調(diào)用也是一件十分容易的事情,可實(shí)際情況卻耗費(fèi)了我兩天時(shí)間才得以實(shí)現(xiàn)。
1. 用VS.NET新建一個(gè)Asp Web Services工程,添加一個(gè)web 服務(wù),命名為SumService.asmx。新增一個(gè)web method,代碼如下:
[WebMethod]
public int IntAdd(int a,int b)
{
return a+b ;
}
然后運(yùn)行它,并利用IE進(jìn)行測(cè)試成功。
2. 打開(kāi)jbuilder9.0,新建一個(gè)項(xiàng)目,添加一個(gè)java class ,命名為T(mén)estNetService,輸入下列代碼:
package MyWebServiceJavaClient;
import java.util.Date;
import java.text.DateFormat;
import java.util.Date;
import java.text.DateFormat;
import org.apache.axis.client.Call;
import org.apache.axis.client.Service;
import javax.xml.namespace.QName;
import java.lang.Integer;
import javax.xml.rpc.ParameterMode;
/**
* <p>Title: </p>
* <p>Description: </p>
* <p>Copyright: Copyright (c) 2004</p>
* <p>Company: </p>
* @author not attributable
* @version 1.0
*/
public class TestNetService {
public TestNetService() {
}
public static void main(String[] args) {
try {
Integer i = new Integer(1);
Integer j = new Integer(2);
String endpoint="http://localhost/MyServices/WebServiceTest/SumService.asmx";
Service service = new Service();
Call call = (Call)service.createCall();
call.setTargetEndpointAddress(new java.net.URL(endpoint));
call.setOperationName(new QName("http://www.my.com/SU","IntAdd"));
call.addParameter("a",org.apache.axis.encoding.XMLType.XSD_DATE,javax.xml.rpc.ParameterMode.IN);
call.addParameter("b",org.apache.axis.encoding.XMLType.XSD_DATE,javax.xml.rpc.ParameterMode.IN);
call.setReturnType(org.apache.axis.encoding.XMLType.XSD_INT);
call.setUseSOAPAction(true);
call.setSOAPActionURI("http://www.my.com/Rpc");
Integer k = (Integer)call.invoke(new Object[]{i,j});
System.out.println( "result is " + k.toString() + ".");
}
catch (Exception e) {System.err.println(e.toString());}
}
}
運(yùn)行上面的java客戶(hù)端程序,你會(huì)發(fā)現(xiàn)系統(tǒng)會(huì)拋出一個(gè)SoapAction異常。奇怪,怎么會(huì)錯(cuò)誤呢?想到了我開(kāi)發(fā)的asp web services沒(méi)有指定SoapAction,于是在SumService.asmx中的 [web method] 的上一行添加下列代碼:
[SoapRpcMethod(Action="http://www.my.com/Rpc",
RequestNamespace="http://www.my.com/SU",
ResponseNamespace="http://www.my.com/SU")]
重新編譯運(yùn)行asp web services后,在執(zhí)行java程序,這時(shí)會(huì)發(fā)現(xiàn)輸出了正確的結(jié)果3。
這樣,用java調(diào)用.net生成的web services也算初步完成了,好像也不是很復(fù)雜是吧。其實(shí),在實(shí)際工作中,我一開(kāi)始并沒(méi)有在網(wǎng)上找到一個(gè)很好的代碼例子,全部是依靠jbuilder 和 axis的幫助完成的, 可總是提示什么找不到相應(yīng)的SoapAction。而實(shí)際上,我在運(yùn)行了asp web services后是可以在IE瀏覽器中看到那個(gè)SoapAction的。我試驗(yàn)過(guò)將默認(rèn)的SoapAction拷貝到j(luò)ava代碼中,但是java客戶(hù)端依然拋出同樣的異常,這要我也很迷惑。
五:總結(jié)
經(jīng)過(guò)兩天的試驗(yàn),終于從技術(shù)上明確了通過(guò)Web Services實(shí)現(xiàn).net 與 java的互通是可能的。當(dāng)然有幾點(diǎn)是需要注意的:
1. 在提供Web Services的時(shí)候,盡量使用xml schema中支持的變量類(lèi)型做參數(shù)。如果使用.net 中的dataset這種類(lèi)型,對(duì)于java來(lái)說(shuō)解析起來(lái)將是一個(gè)災(zāi)難,當(dāng)然,理論上是可以解析的。但是從效率角度來(lái)說(shuō),在Web Services與客戶(hù)端交換信息的過(guò)程中,始終有一個(gè)序列化和反序列化的問(wèn)題。如果使用dataset這種類(lèi)型,系統(tǒng)還需要對(duì)它進(jìn)行序列化操作,這將是一個(gè)很耗費(fèi)資源的過(guò)程。而使用string類(lèi)型將簡(jiǎn)單很多。
2. 如果使用了soap header等擴(kuò)展功能,例如使用了微軟提供的WSE技術(shù),它們之間的相互通信需要作特殊處理。