最近项目上要调用其他系统的WebService(Axis搭建),由于接收数据较大耗时4分钟左右,所以要设置超时时间,而且系统中已有jar包的原因,导致许多方法都不能用,最终用HttpClient。
方法一:使用JaxWsDynamicClientFactory调用WebService
public static Object call(String wsdl,String method,String requestStr){ JaxWsDynamicClientFactory factory = JaxWsDynamicClientFactory.newInstance(); Client client = factory.createClient(wsdl); HTTPConduit conduit = (HTTPConduit) client.getConduit(); HTTPClientPolicy policy = new HTTPClientPolicy(); long timeout = 10 * 60 * 1000;// policy.setConnectionTimeout(timeout); policy.setReceiveTimeout(timeout); conduit.setClient(policy); //动态invoke方法 Object[] os =client.invoke(method,requestStr); return os[0]; }
方法二:使用JaxWsProxyFactoryBean调用WebService
原理:使用JaxWsProxyFactoryBean类生成本地的代理类。
首先创建接口,然后通过JaxWsProxyFactoryBean调用。
@WebService public interface IDataService { @WebMethod @WebResult String getData(@WebParam String requestData); } public static String call(String wsdl, String requestStr) { JaxWsProxyFactoryBean factory = new JaxWsProxyFactoryBean(); factory.setServiceClass(IDataService.class); factory.setAddress(wsdl); IDataService service = (IDataService) factory.create(); // 设置超时时间 org.apache.cxf.endpoint.Client proxy = ClientProxy.getClient(service); HTTPConduit conduit = (HTTPConduit) proxy.getConduit(); HTTPClientPolicy policy = new HTTPClientPolicy(); long timeout = 10 * 60 * 1000;// policy.setConnectionTimeout(timeout); policy.setReceiveTimeout(timeout); conduit.setClient(policy); // 发出请求 return service.getData(requestStr); }
方法三:使用wsimport命令构建WebService客户端
首先使用wsimport命令构建客户端,然后用下面的方法调用。
public static String call(String requestData) { // 构建的客户端代码 IDataService_Service factory = new IDataService_Service(); IDataService service = factory.getDataSharedWebService(); long timeout = 30 * 60 * 1000;// 30分钟 // 设置超时时间 // 当前起作用的配置 ((BindingProvider) service).getRequestContext().put("javax.xml.ws.client.connectionTimeout", timeout); ((BindingProvider) service).getRequestContext().put("javax.xml.ws.client.receiveTimeout", timeout); // 网上搜到的其他设置超时的方法,当前项目没有起作用 ((BindingProvider) service).getRequestContext().put("com.sun.xml.ws.connect.timeout", timeout); ((BindingProvider) service).getRequestContext().put("com.sun.xml.ws.request.timeout", timeout); ((BindingProvider) service).getRequestContext().put("com.sun.xml.internal.ws.connect.timeout", timeout); ((BindingProvider) service).getRequestContext().put("com.sun.xml.internal.ws.request.timeout", timeout); ((BindingProvider) service).getRequestContext().put("sun.net.client.defaultConnectTimeout", timeout); ((BindingProvider) service).getRequestContext().put("sun.net.client.defaultReadTimeout", timeout); try { // 调用WebService return service.getData(requestData); } catch (Exception e) { log.error(e.getMessage()); } return null; }
也可以用cxf的wsdl2java命令构建客户端,调用方式一样,但是如何设置超时时间没有试。
方法四:使用HttpClient调用WebService
使用commons-httpclient-3.1,依赖jar包(commons-codec.jar、commons-logging.jar)。
public String call(String wsdl, String requestData) { try { // requestData可以直接用soapui中请求的数据,注意<![CDATA[]]>的使用 PostMethod postMethod = new PostMethod(wsdl); byte[] b = requestData.getBytes("UTF-8"); InputStream in = new ByteArrayInputStream(b, 0, b.length); RequestEntity re = new InputStreamRequestEntity(in, "text/xml; charset=utf-8"); postMethod.setRequestEntity(re); // 设置header SOAPAction,不设置的话,会报异常:no SOAPAction // header,但是SOAPAction的好像任意值都可以 String soapAction = "XX"; postMethod.setRequestHeader("SOAPAction", soapAction); HttpClient client = new HttpClient(); // 设置超时(不知道默认是多久,没有设置的时候,也没有报错,设置下保险些) int timeout = 10 * 60 * 1000; client.getHttpConnectionManager().getParams().setConnectionTimeout(timeout); client.getHttpConnectionManager().getParams().setSoTimeout(timeout); // int status = client.executeMethod(postMethod); if (status == 200) {// 成功 InputStream is = postMethod.getResponseBodyAsStream(); /** * 获取的结果可以参考用soapui调用时的返回值, * 如果约定的返回值是XML,并不会像soapui一样把xml用<![CDATA[]]>包含起来,要注意解析的方法, * 不知道soapui如何处理的,暂时没时间研究。 */ return getResponseXML(is); } else { log.error("调用Webservice出错;错误代码为:" + status); } } catch (Exception e) { log.error(e.getMessage()); } return null; } public String getResponseXML(InputStream response) throws Exception { // 根据具体的返回值写的解析 SAXReader reader = new SAXReader(); Document document = reader.read(response); Element root = document.getRootElement(); List<Element> childElements = root.elements(); for (Element child : childElements) { List<Element> datas = child.selectNodes("getOrgInfoResponse/getOrgInfoResponse"); for (Element node : datas) { // 返回约定的xml return node.getText(); } } return null; }
总结下这次遇到的问题:
1.异常:java.lang.NoSuchFieldError: QUALIFIED
jar包冲突,删除jar包(如果可以的话,不能删除就用HttpClient的方式)。由于项目中第三方工具需要XmlSchema-1.3.x.jar,而cxf-2.5作为客户端时需要用到xmlschema-core-2.0.1.jar导致前三种方式都不能用。
2.超时
由于接收数据较大,时间较长,必须设置超时时间。
3.异常:javax.xml.bind.UnmarshalException:unexpected element (uri:"", local:"getDataResponse").Expected elements are <{http://xxx/xx}getOrgInfoResponse>
是namespace的问题,如果用JaxWsProxyFactoryBean的方式,要修改@WebResult中targetNamespace;如果用wsimport命令的方式,需要修改类GetDataResponse中属性getDataResponse的注解中namespace的值。
4.异常:no SOAPAction header
没有设置SOAPAction,设置方式:postMethod.setRequestHeader("SOAPAction", soapAction),soapAction的值是什么好像并不影响结果。
相关推荐
本篇文章将详细介绍如何使用CXF和camel-cxf调用Web服务,以及这两个工具的核心功能和使用场景。 Apache CXF是一个全面的服务开发框架,它支持多种Web服务标准,如SOAP、WS-*协议栈、RESTful服务等。CXF提供了丰富的...
用CXF作为客户端调用webService的demo:本人亲测可用,eclipse工程项目包含完整代码和完整jar包, 只要用eclipse导入项目即可,运行控制台显示success或者false字符串,说明OK。
用camel-cxf调用webservice和发布一个webservice接口例子,首先启动QueryServiceMain主函数启动webservice接口,然后启动测试类TestWebservice。例子主要是实现java代码实现camel调用webservice接口
通过这个项目,开发者不仅可以了解SpringBoot和CXF的基本概念,还能掌握两者如何协同工作,发布和调用Web服务。同时,对于SpringBoot应用的打包、部署和测试也有了一定的认识。这个例子是一个理想的实践项目,对于...
在这个基于CXF的Web服务完整例子中,我们将深入探讨CXF的核心概念、配置、以及如何创建和调用Web服务。 1. **CXF框架介绍**:CXF,全称为"Code first eXtended Framework",最初由XFire项目发展而来,后与Apache ...
在Java开发中,Apache CXF是一个广泛使用的开源框架,它提供了创建和消费Web服务的能力。当我们需要在客户端调用Web服务时,CXF扮演着关键角色。本篇将详细讲解如何利用CXF客户端来调用Web服务以及所需的jar包。 ...
2.用cxf开发webservice 3.这个服务端和客户端的小demo 在服务端 对外开放接口服务,然后在客户端 调用服务端的方法, 实现客户端(一个javaweb项目)对服务端(javaweb项目)方法的调用, 实际上就是发送和接收消息...
- 可以通过调整CXF客户端的配置,例如设置连接超时、重试策略等,来优化性能和稳定性。 总之,使用Apache CXF,Java开发者可以方便地调用C#编写的Web服务,实现跨语言的通信。这个过程涉及到了WSDL解析、Java代理...
### 使用CXF发布和调用WebService之HelloWorld入门详解 #### 一、概述 本文将详细介绍如何使用Apache CXF框架来实现一个简单的WebService——HelloWorld示例。此示例不仅适用于初学者理解WebService的基本概念,...
C#动态调用CXF WEBSERVICE框架共通类。
"cxf超时设置"这个主题是关于如何在使用CXF框架时,对网络通信的超时时间进行配置,以优化服务的稳定性和性能。 首先,理解超时的概念至关重要。在计算机网络中,超时是指等待某个操作完成的时间限制。当这个时间...
本文将详细介绍如何使用HttpClient和XFire这两种不同的库来调用Web Service,特别是针对短信接口的调用。 首先,让我们了解Web Service的基本概念。Web Service是一种基于互联网的、平台无关的交互方式,它允许不同...
【标题】:“cxf做的webservice对外提供接口调用” 【描述】中提到的“webservice对外发布接口全部源码拿起来就能用”,这表明这是一个关于使用Apache CXF框架创建和发布的Web服务项目。Apache CXF是一个开源的Java...
Java WebService CXF客户端调用和服务端的实现是企业级应用程序中常见的通信方式,它基于标准的SOAP(Simple Object Access Protocol)协议,提供了一种在分布式环境中交换信息的方法。CXF是一个开源框架,它简化了...
【CXF和Spring搭建Web服务代码详解】 在Java开发领域,CXF和Spring框架的结合是构建高效、灵活的Web服务的常见选择。CXF是一个开源的SOAP和RESTful Web服务框架,它允许开发者轻松地创建和消费Web服务。而Spring...
【CXF:构建Web服务的全面指南】 CXF(CXF: XFire Community eXtended)是一个开源的Java框架,用于构建和部署Web服务。...通过理解并掌握CXF的基本概念和操作,你将能够充分利用它的优势,为你的项目带来便利。
在本文中,我们将深入探讨如何使用Apache CXF V3.2.4实现带有安全认证的Web服务调用。Apache CXF是一个开源框架,它允许开发者创建和消费各种Web服务,包括SOAP和RESTful API。CXF 3.2版本引入了许多增强功能,包括...
使用spring集成cxf,在两个web project里发布及调用webservice server端使用spring+springmvc+mybatis+cxf,client端使用struts2+spring+hibernate+cxf 两个工程均为myeclipse project,包含所有除myeclipse自带以外...
本项目“cxf+spring发布webservice和restservice”专注于利用Apache CXF框架与Spring框架结合,实现这两种服务的发布。Apache CXF是一个开源的、功能丰富的服务栈,它使得开发者能够轻松地构建和部署SOAP和RESTful ...
Spring框架是Java企业级应用开发的首选,而CXF是一个强大的开源服务框架,支持创建和消费Web服务。本教程将深入探讨如何利用Spring和CXF来实现基于HTTP和HTTPS的Web服务,并且将涉及到HTTPS的证书配置。 1. **...