Spring Boot项目如何向SOAP WebService发送数据完成对接?
基于wsdl2java生成代码调用SOAP服务实操指南
第一步:先明确请求、响应结构
你不需要手动逐行读WSDL梳理结构,wsdl2java已经帮你把所有定义映射成了Java类:
- 类名后缀为
*Service的是服务入口类,后缀为*PortType(部分版本生成的是*Port)的是请求代理接口 - 类名后缀为
*Request的是请求实体类,里面的所有setter方法对应你需要传入的请求字段 - 类名后缀为
*Response的是响应实体类,里面的所有getter方法对应服务返回的字段
直接在IDE里点开这些类看属性和方法,就能完全明确请求、响应的结构要求。
第二步:编写服务调用代码
目前Java生态下最常用的wsdl2java是Apache CXF提供的实现,以下是通用实现逻辑:
- 先在项目中引入对应依赖(如果是Maven项目,引入
cxf-rt-frontend-jaxws、cxf-rt-transports-http两个核心依赖即可,版本选择和你生成代码时用的CXF版本一致避免冲突) - 初始化客户端、构造请求、调用服务的核心代码示例:
import javax.xml.namespace.QName; import java.net.URL; // 初始化服务实例 URL wsdlAddress = new URL("Project B提供的服务WSDL地址"); // QName的两个参数分别对应WSDL根节点的targetNamespace属性、服务名,你可以在生成的Service类的静态代码块里直接找到这两个值,不用自己去WSDL里翻 QName serviceQName = new QName("http://service.projectb.com/", "UserQueryService"); UserQueryService userQueryService = new UserQueryService(wsdlAddress, serviceQName); // 获取请求代理对象 UserQueryPortType port = userQueryService.getUserQueryPort(); // 构造请求对象,把你JSON接口收到的参数映射赋值进去 UserQueryRequest request = new UserQueryRequest(); request.setUserId(/* 从你自己的JSON API入参里取对应值 */); request.setQueryCondition(/* 从你自己的JSON API入参里取对应值 */); // 直接调用接口方法,框架会自动完成SOAP报文序列化、发送、响应解析全流程 UserQueryResponse response = port.queryUser(request); // 从response对象中通过getter方法取返回值,做后续业务处理即可
第三步:常见配置与问题排查
- 超时配置:默认客户端超时时间可能不符合业务要求,可以通过以下代码设置:
import org.apache.cxf.endpoint.Client; import org.apache.cxf.frontend.ClientProxy; import org.apache.cxf.transport.http.HTTPConduit; import org.apache.cxf.transports.http.configuration.HTTPClientPolicy; Client client = ClientProxy.getClient(port); HTTPConduit httpConduit = (HTTPConduit) client.getConduit(); HTTPClientPolicy clientPolicy = new HTTPClientPolicy(); clientPolicy.setConnectionTimeout(5000); // 连接超时5秒 clientPolicy.setReceiveTimeout(10000); // 响应超时10秒 httpConduit.setClient(clientPolicy);
- 连通性排查:写代码前可以先用接口测试工具直接测Project B的服务地址,确认网络连通、IP白名单、鉴权要求都没问题,避免写完代码才发现是网络层面的问题
- 报文格式错误:如果调用时报字段不匹配、命名空间错误,先确认你生成Java类用的WSDL文件和Project B当前线上运行的服务版本完全一致,不要用过期的WSDL生成代码
- 鉴权处理:如果Project B的服务需要加请求头、token鉴权,可以通过CXF的拦截器在请求发出前统一添加报文头即可
内容的提问来源于stack exchange,提问作者Abhishikth
相关产品推荐
相关产品推荐

