一、Webservice可以使用的框架很多。
AXIS、CXF 、JAX、XFIRE,这些框架都可以根据wsdl文件生成ws的服务器和客户端代码。
二、Ws的调用方式有三种,http post、http get、soap post。
本人建议使用http post,他访问远程ws接口的速度比使用soap post要快些。
象使用axis框架实现soap post方式来说,简单的接口还好,对于使用了大量代理类及带有soaphead的ws,且还要在本地生成一大堆JAVA类来和服务端对应。
特别如下这种情况,axis好像无法实现。
Soaphead如下<soapHead><appId>0039434454</appId><pwd>67677</pwd></soapHead>象这种只能根据org.apache.axis.client.Call.addHead(ElementSoapHead)来增加报头。
但这个报头没有根元素,无法创建一个这种Element。
下面就如何书写客户端代码详细讲解下。
1.通过发送http post请求来调用ws。
SOAPUI是个不错的工具,他可以根据wsdl文件生成测试例子。
另外重要的是,它可以生成wsdl对应的请求报文和响应报文。
这样我们在调用别人写的ws时,不管多复杂的ws都可以简单的调用。
首先按照SOAPUI显示的请求报文格式拼装我们的请求报文,使用.HttpURLConnection对象来发送http post请求。
然后使用输出流、输出流获得响应报文,再用Element解析报文得到要取的数据。
示例代码如下:JAVA类SoapInvoke:package test;import java.io.InputStream;import java.io.OutputStream;import .HttpURLConnection;import .URL;public class SoapInvoke {public static void main(String[] args) {try {soapSpecialConnection();} catch (Exception e) {e.printStackTrace();}}public static void soapSpecialConnection() throws Exception{//拼装soap请求报文StringBuilder sb = new StringBuilder();StringBuilder soapHeader = new StringBuilder();soapHeader.append("<soapenv:Envelopexmlns:soapenv=\"/soap/envelope/\"xmlns:test=\"http://test/\">");soapHeader.append("<soapenv:Header>");soapHeader.append("<spId>zhouyun</spId>");soapHeader.append("<spPassword>123</spPassword>");soapHeader.append("</soapenv:Header>");soapHeader.append("<soapenv:Body>");soapHeader.append("<test:sayHelloMiss>");soapHeader.append("<arg0>");soapHeader.append("<name>zhouyun</name>");soapHeader.append("</arg0>");soapHeader.append("</test:sayHelloMiss>");soapHeader.append("</soapenv:Body>");soapHeader.append("</soapenv:Envelope>");//设置soap请求报文的相关属性String url="http://localhost:8080/CXFServer/SayHelloService";URL u = new URL(url);HttpURLConnection conn = (HttpURLConnection) u.openConnection(); conn.setDoInput(true);conn.setDoOutput(true);conn.setUseCaches(false);conn.setDefaultUseCaches(false);conn.setRequestProperty("Host", "localhost:8080");conn.setRequestProperty("Content-Type", "text/xml;charset=utf-8");conn.setRequestProperty("Content-Length",String.valueOf(soapHeader.length()));conn.setRequestProperty("SOAPAction", "");conn.setRequestMethod("POST");//定义输出流OutputStream output = conn.getOutputStream();if (null != soapHeader) {byte[] b = soapHeader.toString().getBytes("utf-8");//发送soap请求报文output.write(b, 0, b.length);}output.flush();output.close();//定义输入流,获取soap响应报文InputStream input = conn.getInputStream();int c = -1;//sb为返回的soap响应报文字符串while (-1 != (c = input.read())) {sb.append((char)c);}input.close();}}2.通过axis来调用ws。
对于使用了复杂代理类的ws,我们在调用时可以使用AXIS、CXF、xfire架包来自动生成ws客户端JA V A代码。
下面以axis为例,来展示。
服务器端主要JAV A代码package test;import javax.jws.WebService;@WebServicepublic class SayHelloImpl implements SayHelloService {public wsResult sayHelloMr(String name) {wsResult retObj = new wsResult();retObj.setResultVal("Hello,mr " + name);return retObj;}public wsResult sayHelloMiss(InputClass input) {wsResult retObj = new wsResult();retObj.setResultVal("Hello,Miss " + input.getName());return retObj;}}客户端:1)新建wsdltojava.bat文件,放到C盘,文件内容如下:set Axis_Lib=E:\axis-bin-1_4\axis-1_4\libset Java_Cmd=java -Djava.ext.dirs=%Axis_Lib%set Axis_Servlet=http://localhost:8080/CXFServer/SayHelloService?wsdl%Java_Cmd% org.apache.axis.wsdl.WSDL2Java -u %Axis_Servlet%其中Axis_Lib为本地axis架包的路径;Axis_Servlet为本地ws的URL,这里也可以设置为此ws服务器对应的wsdl文件的路径。
2)在DOS里,执行wsdltojava.bat。
在C盘根目录下就会生成JA V A客户端的代码了3)新建一个java类Invoke,代码如下:package test;public class invoke {public static void main(String[] args) throws Exception { getResult();}public static void getResult() {try {SayHelloImplServiceLocator svc = new SayHelloImplServiceLocator();SayHelloService stub = svc.getSayHelloImplPort();//调用//WsResult wsResult = stub.sayHelloMr("zhouyun");InputClass inputClass=new InputClass();inputClass.setName("zhouyun");WsResult wsResult = stub.sayHelloMiss(inputClass);System.out.println("结果是:" + wsResult.getResultVal());} catch (Exception e) {System.out.println(e);}}}Ps:1.通过命令生成的java客户端代码里SayHelloImplServiceLocator类是调用ws的入口。