先写服务端代码:
CallBackAction
package org.hd.axis2.device; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpSession; import org.apache.struts2.ServletActionContext; import org.hd.business.service.BusinessService; import org.hd.business.summary.model.CallSummaryVo; import org.rd.framework.common.container.ContainerManager; import com.opensymphony.xwork2.ActionContext; import org.apache.axis2.rpc.receivers.RPCMessageReceiver; import org.apache.axis2.rpc.receivers.RPCInOutAsyncMessageReceiver; import org.apache.axis2.rpc.receivers.RPCInOnlyMessageReceiver; public class CallBackAction{ private BusinessService businessService = (BusinessService)ContainerManager.getComponent(BusinessService.BEAN_ID); public String updateCallInfo(String callid,String billNumber){ String resultMessage=""; CallSummaryVo call=new CallSummaryVo(); if(callid==null||callid.trim().equals("")){ resultMessage="未获取到参数通话callid,操作失败!"; }else if(billNumber==null||billNumber.trim().equals("")){ resultMessage="未获取到参数工单号billNumber,操作失败!"; }else{ call.setVoiceid(callid); call.setBill_number(billNumber); businessService.updateSummaryByWebservice(call);//这个方法就是更新数据库的2个字段 resultMessage="收到信息:callid="+callid+",billNumber="+billNumber+"。根据参数已经完成更新数据库数据。"; } System.out.println("调用webservice的返回结果信息:\r\n"+resultMessage); return resultMessage; } public String queryCallInfo(String comeUserjobNumber){ String resultMessage=""; if(comeUserjobNumber==null||comeUserjobNumber.trim().equals("")){ resultMessage="未获取到参数comeUserjobNumber,操作失败!"; }else{ String userInfo=businessService.getAgentNameFromHdUser(comeUserjobNumber);//这个方法就是从数据库查询一个字段 resultMessage="收到参数信息comeUserjobNumber="+comeUserjobNumber+"。根据此参数查询到的信息是:"+userInfo; } System.out.println("调用webservice的返回结果信息:\r\n"+resultMessage); return resultMessage; } //没有参数的方法 public String getUserNameFromSession(){ String resultMessage=""; String userName=(String)businessService.getInfoFromSession("current_user_id"); if(userName!=null){ resultMessage="获取到当前登录用户的账号:"+userName; }else{ resultMessage="当前登录用户的账号为null"; } System.out.println("调用webservice的返回结果信息:\r\n"+resultMessage); return resultMessage; } //没有返回值得方法 public void writeLog(String info){ String resultMessage=""; if(info==null||info.trim().equals("")){ resultMessage="未获取到参数info,操作失败!"; }else{ resultMessage="收到参数信息info="+info; } System.out.println("调用webservice的返回结果信息:\r\n"+resultMessage); } }
service.xml文件配置:
<service name="callInfoService"> <description> This service is about deal with call info </description> <parameter name="ServiceClass">org.hd.axis2.device.CallBackAction</parameter> <operation name="updateCallInfo"> <messageReceiver class="org.apache.axis2.rpc.receivers.RPCMessageReceiver" /> </operation> <operation name="queryCallInfo"> <messageReceiver class="org.apache.axis2.rpc.receivers.RPCMessageReceiver" /> </operation> <operation name="getUserNameFromSession"> <messageReceiver class="org.apache.axis2.rpc.receivers.RPCMessageReceiver" /> </operation> <operation name="writeLog"> <messageReceiver class="org.apache.axis2.rpc.receivers.RPCMessageReceiver" /> </operation> </service>
客户端的访问方式1:rpc
CallBackClient
package org.hd.axis2.client; import javax.xml.namespace.QName; import org.apache.axis2.AxisFault; import org.apache.axis2.addressing.EndpointReference; import org.apache.axis2.client.Options; import org.apache.axis2.rpc.client.RPCServiceClient; public class CallBackClient { public static void main(String args[]) throws AxisFault { // CallBackClient.revokeMethodUpdateCallInfo(); CallBackClient.revokeMethodQueryCallInfo(); // CallBackClient.revokeMethodWriteLog(); } public static void revokeMethodUpdateCallInfo() throws AxisFault { // 使用RPC方式调用WebService RPCServiceClient serviceClient = new RPCServiceClient(); Options options = serviceClient.getOptions(); // 指定调用WebService的UR // http://helpdesk.citicsinfo.com:80/services/callInfoService/queryCallInfo?comeUserjobNumber=T001890 EndpointReference targetEPR = new EndpointReference( "http://helpdesk.citicsinfo.com:80/services/callInfoService"); options.setTo(targetEPR); // 指定hadAddBillForTheCall方法的参数值 Object[] opAddEntryArgs = new Object[] { "B4848F35FFFF827601ED4054D35238FC","ceshi-SDF22" }; // 指定返回值的数据类型 Class[] classes = new Class[] { String.class }; // 指定要调用的方法及WSDL文件的命名空间 QName opAddEntry = new QName("http://device.axis2.hd.org", "updateCallInfo"); // 调用sayHelloToPerson方法并输出该方法的返回值 Object[] resObj=serviceClient.invokeBlocking(opAddEntry, opAddEntryArgs, classes); //打印结果 System.out.println("调用方法 updateCallInfo"); if(resObj!=null&&resObj.length>0){ for(int i=0;i<resObj.length;i++){ System.out.println(resObj[i].toString()); } } } public static void revokeMethodQueryCallInfo() throws AxisFault { // 使用RPC方式调用WebService RPCServiceClient serviceClient = new RPCServiceClient(); Options options = serviceClient.getOptions(); // 指定调用WebService的UR // http://helpdesk.citicsinfo.com:80/services/callInfoService/queryCallInfo?comeUserjobNumber=T001890 EndpointReference targetEPR = new EndpointReference( "http://helpdesk.citicsinfo.com:80/services/callInfoService"); options.setTo(targetEPR); // 指定hadAddBillForTheCall方法的参数值 Object[] opAddEntryArgs = new Object[] { "T001890"}; // 指定返回值的数据类型 Class[] classes = new Class[] { String.class }; // 指定要调用的方法及WSDL文件的命名空间 QName opAddEntry = new QName("http://device.axis2.hd.org", "queryCallInfo"); // 调用sayHelloToPerson方法并输出该方法的返回值 Object[] resObj=serviceClient.invokeBlocking(opAddEntry, opAddEntryArgs, classes); //打印结果 System.out.println("调用方法 queryCallInfo"); if(resObj!=null&&resObj.length>0){ for(int i=0;i<resObj.length;i++){ System.out.println(resObj[i].toString()); } } } public static void revokeMethodWriteLog() throws AxisFault { // 使用RPC方式调用WebService RPCServiceClient serviceClient = new RPCServiceClient(); Options options = serviceClient.getOptions(); // 指定调用WebService的UR // http://helpdesk.citicsinfo.com:80/services/callInfoService/queryCallInfo?comeUserjobNumber=T001890 EndpointReference targetEPR = new EndpointReference( "http://helpdesk.citicsinfo.com:80/services/callInfoService"); options.setTo(targetEPR); // 指定hadAddBillForTheCall方法的参数值 Object[] opAddEntryArgs = new Object[] { "写日志test" }; // 指定返回值的数据类型 Class[] classes = new Class[] { String.class }; // 指定要调用的方法及WSDL文件的命名空间 QName opAddEntry = new QName("http://device.axis2.hd.org", "writeLog"); // 调用sayHelloToPerson方法并输出该方法的返回值 Object[] resObj=serviceClient.invokeBlocking(opAddEntry, opAddEntryArgs, classes); //打印结果 System.out.println("调用方法 writeLog"); if(resObj!=null&&resObj.length>0){ for(int i=0;i<resObj.length;i++){ System.out.println(resObj[i].toString()); } } } }
这中访问方式,在前篇博客已经做过测试,本篇主要讲axiom方式。
客户端的访问方式2:axiom
CallBackClientAxiom
package org.hd.axis2.client.axiom; import java.util.Iterator; import javax.xml.namespace.QName; 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.AxisFault; import org.apache.axis2.Constants; import org.apache.axis2.addressing.EndpointReference; import org.apache.axis2.client.Options; import org.apache.axis2.client.ServiceClient; import org.apache.axis2.rpc.client.RPCServiceClient; public class CallBackClientAxiom { public static void main(String args[]) throws AxisFault { CallBackClientAxiom.revokeMethodUpdateCallInfoAxiom(); CallBackClientAxiom.revokeMethodQueryCallInfoAxiom(); CallBackClientAxiom.revokeMethodWriteLogAxiom(); } public static void revokeMethodUpdateCallInfoAxiom() throws AxisFault { System.out.println("方法revokeMethodUpdateCallInfoAxiom被调用---------"); EndpointReference targetEPR = new EndpointReference("http://helpdesk.citicsinfo.com:80/services/callInfoService"); //使用axiom方式访问 OMFactory fac = OMAbstractFactory.getOMFactory(); OMNamespace omNs = fac.createOMNamespace("http://device.axis2.hd.org", "tns"); OMElement method = fac.createOMElement("updateCallInfo", omNs);//方法名 OMElement param1 = fac.createOMElement("callid", omNs);//参数名 OMElement param2 = fac.createOMElement("billNumber", omNs);//参数名 String param1value="B4848F35FFFF827601ED4054D35238FC";String param2value="ceshihaha"; param1.addChild(fac.createOMText(param1, param1value)); param2.addChild(fac.createOMText(param2, param2value)); method.addChild(param1); method.addChild(param2); Options options = new Options(); options.setTo(targetEPR); options.setTransportInProtocol(Constants.TRANSPORT_HTTP); ServiceClient axiomClient = new ServiceClient(); axiomClient.setOptions(options); //开始访问 // axiomClient.fireAndForget(method);//访问无返回的方法void //1 OMElement result = axiomClient.sendReceive(method); System.out.println("1:axiom客户端方式访问结果第一个element:"+result.getFirstElement().getText()); //2或者用下面遍历的方式获取访问结果 Iterator<OMElement> it=result.getChildElements(); while(it.hasNext()){ OMElement ome=(OMElement)it.next(); if(ome!=null){ String omevalue=ome.getText(); if (omevalue != null) { System.out.println("2:axiom客户端方式访问结果:"+omevalue); } } } //3使用QName参数 QName qname = new QName("http://device.axis2.hd.org", "queryCallInfo"); result.getFirstChildWithName(qname); System.out.println("3:axiom客户端方式QName访问结果第一个element:"+result.getFirstElement().getText()); } public static void revokeMethodQueryCallInfoAxiom() throws AxisFault { System.out.println("方法revokeMethodQueryCallInfoAxiom被调用---------"); EndpointReference targetEPR = new EndpointReference("http://helpdesk.citicsinfo.com:80/services/callInfoService"); //使用axiom方式访问 OMFactory fac = OMAbstractFactory.getOMFactory(); OMNamespace omNs = fac.createOMNamespace("http://device.axis2.hd.org", "tns"); OMElement method = fac.createOMElement("queryCallInfo", omNs);//方法名 OMElement param1 = fac.createOMElement("comeUserjobNumber", omNs);//参数名 String param1value="T001890"; param1.addChild(fac.createOMText(param1, param1value)); method.addChild(param1); Options options = new Options(); options.setTo(targetEPR); options.setTransportInProtocol(Constants.TRANSPORT_HTTP); ServiceClient axiomClient = new ServiceClient(); axiomClient.setOptions(options); //开始访问 // axiomClient.fireAndForget(method);//访问无返回的方法void //1 OMElement result = axiomClient.sendReceive(method); System.out.println("1:axiom客户端方式访问结果第一个element:"+result.getFirstElement().getText()); //2或者用下面遍历的方式获取访问结果 Iterator<OMElement> it=result.getChildElements(); while(it.hasNext()){ OMElement ome=(OMElement)it.next(); if(ome!=null){ String omevalue=ome.getText(); if (omevalue != null) { System.out.println("2:axiom客户端方式访问结果:"+omevalue); } } } //3使用QName参数 QName qname = new QName("http://device.axis2.hd.org", "queryCallInfo"); result.getFirstChildWithName(qname); System.out.println("3:axiom客户端方式QName访问结果第一个element:"+result.getFirstElement().getText()); } public static void revokeMethodWriteLogAxiom() throws AxisFault { System.out.println("方法revokeMethodWriteLogAxiom被调用---------"); EndpointReference targetEPR = new EndpointReference("http://helpdesk.citicsinfo.com:80/services/callInfoService"); //使用axiom方式访问 OMFactory fac = OMAbstractFactory.getOMFactory(); OMNamespace omNs = fac.createOMNamespace("http://device.axis2.hd.org", "tns"); OMElement method = fac.createOMElement("writeLog", omNs);//方法名 OMElement param1 = fac.createOMElement("info", omNs);//参数名 String param1value="哈哈,写日志"; param1.addChild(fac.createOMText(param1, param1value)); method.addChild(param1); Options options = new Options(); options.setTo(targetEPR); options.setTransportInProtocol(Constants.TRANSPORT_HTTP); ServiceClient axiomClient = new ServiceClient(); axiomClient.setOptions(options); //开始访问 axiomClient.fireAndForget(method);//访问无返回的方法void //下面注释掉的部分也可以使用。因为访问的方法返回void,所以结果肯定是空, //我们只需要调用就可以了,没必要在查看返回结果。 // //1 // OMElement result = axiomClient.sendReceive(method); // System.out.println("1:axiom客户端方式访问结果第一个element:"+result.getFirstElement().getText()); // // //2或者用下面遍历的方式获取访问结果 // Iterator<OMElement> it=result.getChildElements(); // while(it.hasNext()){ // OMElement ome=(OMElement)it.next(); // if(ome!=null){ // String omevalue=ome.getText(); // if (omevalue != null) { // System.out.println("2:axiom客户端方式访问结果:"+omevalue); // } // } // // } // // //3使用QName参数 // QName qname = new QName("http://device.axis2.hd.org", // "writeLog"); // result.getFirstChildWithName(qname); // System.out.println("3:axiom客户端方式QName访问结果第一个element:"+result.getFirstElement().getText()); // } }
运行main方法,
服务端打印:
调用webservice的返回结果信息:
收到信息:callid=B4848F35FFFF827601ED4054D35238FC,billNumber=ceshihaha。根据参数已经完成更新数据库数据。
调用webservice的返回结果信息:
收到参数信息comeUserjobNumber=T001890。根据此参数查询到的信息是:王x
调用webservice的返回结果信息:
收到参数信息info=哈哈,写日志
客户端打印:
方法revokeMethodUpdateCallInfoAxiom被调用---------
1:axiom客户端方式访问结果第一个element:收到信息:callid=B4848F35FFFF827601ED4054D35238FC,billNumber=ceshihaha。根据参数已经完成更新数据库数据。
2:axiom客户端方式访问结果:收到信息:callid=B4848F35FFFF827601ED4054D35238FC,billNumber=ceshihaha。根据参数已经完成更新数据库数据。
3:axiom客户端方式QName访问结果第一个element:收到信息:callid=B4848F35FFFF827601ED4054D35238FC,billNumber=ceshihaha。根据参数已经完成更新数据库数据。
方法revokeMethodQueryCallInfoAxiom被调用---------
1:axiom客户端方式访问结果第一个element:收到参数信息comeUserjobNumber=T001890。根据此参数查询到的信息是:王x
2:axiom客户端方式访问结果:收到参数信息comeUserjobNumber=T001890。根据此参数查询到的信息是:王x
3:axiom客户端方式QName访问结果第一个element:收到参数信息comeUserjobNumber=T001890。根据此参数查询到的信息是:王x
方法revokeMethodWriteLogAxiom被调用---------
-------------------------------------------------------------------------------
--------------------------------------------------------------------------------
看看axis2开发文档中介绍的客户端访问方式:
Axis2中为您提供了几种方式完成到WSDL到对象的映射,生成客户端。
这三个选项是Axis2的数据绑定框架Axis2 DataBinding Framework(即ADB),XMLBeans,和JiBX数据绑定。
所有这些方法包括使用数据绑定创建Java对象的服务所使用的XML结构,每一种都有其优点和缺点。
您还可以生成XML的in-out存根,不是基于数据绑定。
Axis2的数据绑定框架(ADB):
ADB可能是最简单的方法生成Axis2客户端。
在大多数情况下,所有的相关的类作为内部类的主要存根类创建。
ADB是非常容易使用,但它也有局限性。这并不意味着是一个完整的架构绑定的应用程序,
和有困难的结构,如XML Schema元素扩展和限制。
XMLBeans:
与ADB不同,XMLBeans是一个全功能的模式编译器,所以它没有ADB的限制问题。
但是,代价是使用要比ADB更复杂。它会产生一个数量庞大的文件和编程模型,
同时当然是可用的,不像ADB那么简单。
JiBX:
JiBX是一个完整的数据绑定框架,不仅提供WSDL到Java的转换,
同时提供Java-to-XML转换。在某些方面,JiBX在这两方面做的最好。
JiBX是非常灵活,使您能够选择代表你的实体类,但它可以进行复杂的设置。
另一方面,一旦完成,使用生成的代码和使用ADB一样容易。
如果是简单的结构,ADB就足够了。如果你需要更高性能和更多灵活性,推荐选择使用XMLBeans或JiBX。
---------------------------------------------------------------------------------------------
在快速开发向导中有这样的内容:
•Generating Clients
◦Creating a client using AXIOM
◦Generating a client using ADB
◦Generating a client using XML Beans
◦Generating a client using JiBX
也就是说客户端其实有多钟方式,在生命客户端时,可以这样:
1: ServiceClient axiomClient = new ServiceClient();
2: RPCServiceClient serviceClient = new RPCServiceClient();
org.apache.axis2.client.ServiceClient 这个类在axis2-kernel-1.6.2.jar中。
而org.apache.axis2.rpc.client.RPCServiceClient这个类在axis2-adb-1.6.2.jar中,并且继承了ServiceClient。
源代码中:
public class RPCServiceClient extends ServiceClient
所以客户端的访问方式rpc也算是一种。
我比较喜欢rpc和axiom方式(网上有说是ome方式,不知这个名字怎么来的,官方的文档就没说过)。
这两种方式是类似的,我们只要编写好代码就可以访问webservice了,只是代码的内容有些区别而已。
而后面的其他三种方式(ADB,XMLBeans,JiBX)是需要使用java2wsdl工具把你想做成webservice的类先编译成wsdl文件,然后
在生成客户端的过程中,需要使用wsdl2java工具生成客户端代码(供后面的使用),并需要你再写客户端代码(和上面的客户端代码不同,是另外的方式)。
这3个方式比较灵活对效率有可控性,就是麻烦些,如果你的webservice处理的问题比较简单,数据量少,这样做其实
很麻烦,使用rpc或者axiom方式,我们只需要写代码就可以了。