Spring Boot+CXF搭建WebService(转)
概述
最近项目用到在 Spring boot 下搭建 WebService 服务,对 Java 语言下的 WebService 了解甚少,而今抽个时间查阅资料整理下 Spring Boot 结合 CXF 打架 WebService 一般步骤与方法;本文章结合各个博客资料整理而成,如有雷同,谨记转载;
Spring Boot WebService 开发
需要依赖 Maven 的 Pom 清单
<?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.dbgo</groupId> <artifactId>webservicedemo</artifactId> <version>0.0.1-SNAPSHOT</version> <packaging>jar</packaging> <name>webservicedemo</name> <description>Demo project for Spring Boot</description> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>1.5.8.RELEASE</version> <relativePath/> <!-- lookup parent from repository --> </parent> <properties> <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding> <java.version>1.8</java.version> </properties> <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <!--WerbService CXF 依赖--> <dependency> <groupId>org.apache.cxf</groupId> <artifactId>cxf-rt-frontend-jaxws</artifactId> <version>3.1.12</version> </dependency> <dependency> <groupId>org.apache.cxf</groupId> <artifactId>cxf-rt-transports-http</artifactId> <version>3.1.12</version> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency><dependency> <groupId>junit</groupId> <artifactId>junit</artifactId> <version><span style="color: rgba(128, 0, 128, 1)">4.12</span></version> </dependency> <dependency> <groupId>commons-io</groupId> <artifactId>commons-io</artifactId> <version><span style="color: rgba(128, 0, 128, 1)">2.5</span></version> </dependency> </dependencies> <build> <plugins> <plugin> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-maven-plugin</artifactId> </plugin> </plugins> </build>
</project>
构建并发布服务
构建 Model 对象
package com.dbgo.webservicedemo.Model;
import java.io.Serializable;
import java.util.Date;
public class User implements Serializable {
private static final long serialVersionUID = -5939599230753662529L;
private String userId;
private String username;
private String age;
private Date updateTime;
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> String getUserId() {
</span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> userId;
}
</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> setUserId(String userId) {
</span><span style="color: rgba(0, 0, 255, 1)">this</span>.userId =<span style="color: rgba(0, 0, 0, 1)"> userId;
}
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> String getUsername() {
</span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> username;
}
</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> setUsername(String username) {
</span><span style="color: rgba(0, 0, 255, 1)">this</span>.username =<span style="color: rgba(0, 0, 0, 1)"> username;
}
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> String getAge() {
</span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> age;
}
</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> setAge(String age) {
</span><span style="color: rgba(0, 0, 255, 1)">this</span>.age =<span style="color: rgba(0, 0, 0, 1)"> age;
}
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> Date getUpdateTime() {
</span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> updateTime;
}
</span><span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> setUpdateTime(Date updateTime) {
</span><span style="color: rgba(0, 0, 255, 1)">this</span>.updateTime =<span style="color: rgba(0, 0, 0, 1)"> updateTime;
}
}
构建服务接口
package com.dbgo.webservicedemo.service;
import com.dbgo.webservicedemo.Model.User;
import javax.jws.WebMethod;
import javax.jws.WebParam;
import javax.jws.WebService;
import java.util.ArrayList;
@WebService
public interface UserService {
@WebMethod
String getName(@WebParam(name = "userId")String userId);
@WebMethod
User getUser(String userI);
@WebMethod
ArrayList</span><User><span style="color: rgba(0, 0, 0, 1)"> getAlLUser();
}
构建接口实现类
package com.dbgo.webservicedemo.service;
import com.dbgo.webservicedemo.Model.User;
import javax.jws.WebService;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
@WebService(targetNamespace="http://service.webservicedemo.dbgo.com/",endpointInterface = "com.dbgo.webservicedemo.service.UserService")
public class UserServiceImpl implements UserService {
private Map<String, User> userMap = new HashMap<String, User>();
public UserServiceImpl() {
System.out.println("向实体类插入数据");
User user = new User();
user.setUserId("411001");
user.setUsername("zhansan");
user.setAge("20");
user.setUpdateTime(new Date());
userMap.put(user.getUserId(), user);
user </span>= <span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> User();
user.setUserId(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">411002</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
user.setUsername(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">lisi</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
user.setAge(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">30</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
user.setUpdateTime(</span><span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> Date());
userMap.put(user.getUserId(), user);
user </span>= <span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> User();
user.setUserId(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">411003</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
user.setUsername(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">wangwu</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
user.setAge(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">40</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
user.setUpdateTime(</span><span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> Date());
userMap.put(user.getUserId(), user);
}
@Override
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> String getName(String userId) {
</span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">liyd-</span><span style="color: rgba(128, 0, 0, 1)">"</span> +<span style="color: rgba(0, 0, 0, 1)"> userId;
}
@Override
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> User getUser(String userId) {
User user</span>= userMap.<span style="color: rgba(0, 0, 255, 1)">get</span><span style="color: rgba(0, 0, 0, 1)">(userId);
</span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> user;
}
@Override
</span><span style="color: rgba(0, 0, 255, 1)">public</span> ArrayList<User><span style="color: rgba(0, 0, 0, 1)"> getAlLUser() {
ArrayList</span><User> users=<span style="color: rgba(0, 0, 255, 1)">new</span> ArrayList<><span style="color: rgba(0, 0, 0, 1)">();
userMap.forEach((key,value)</span>-><span style="color: rgba(0, 0, 0, 1)">{users.add(value);});
</span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> users;
}
}
备注说明:接口实现类名称前的注解 targetNamespace 是当前类实现接口所在包名称的反序(PS:加上反斜线),endpointInterface 是当前需要实现接口的全称;@WebService(targetNamespace="http://service.webservicedemo.dbgo.com/",endpointInterface = "com.dbgo.webservicedemo.service.UserService")
服务发布类编写
package com.dbgo.webservicedemo;
import com.dbgo.webservicedemo.service.UserService;
import com.dbgo.webservicedemo.service.UserServiceImpl;
import org.apache.cxf.Bus;
import org.apache.cxf.bus.spring.SpringBus;
import org.apache.cxf.jaxws.EndpointImpl;
import org.apache.cxf.transport.servlet.CXFServlet;
import org.springframework.boot.web.servlet.ServletRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import javax.xml.ws.Endpoint;
@Configuration
public class WebServiceConfig {
@Bean
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> ServletRegistrationBean dispatcherServlet(){
</span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">new</span> ServletRegistrationBean(<span style="color: rgba(0, 0, 255, 1)">new</span> CXFServlet(),<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">/service/*</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);//发布服务名称
}
@Bean(name </span>=<span style="color: rgba(0, 0, 0, 1)"> Bus.DEFAULT_BUS_ID)
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> SpringBus springBus()
{
</span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> SpringBus();
}
@Bean
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> UserService userService()
{
</span><span style="color: rgba(0, 0, 255, 1)">return</span> <span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> UserServiceImpl();
}
@Bean
</span><span style="color: rgba(0, 0, 255, 1)">public</span><span style="color: rgba(0, 0, 0, 1)"> Endpoint endpoint() {
EndpointImpl endpoint</span>=<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> EndpointImpl(springBus(), userService());//绑定要发布的服务
endpoint.publish(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">/user</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">); //显示要发布的名称
</span><span style="color: rgba(0, 0, 255, 1)">return</span><span style="color: rgba(0, 0, 0, 1)"> endpoint;
}
}
运行程序,输入 http://localhost:8080/service/user?wsdl 即可查询发布出去的接口文件;
如果需要发布多个 webservice,需要配置多个 Config 实现类文件;
客户端调用服务
基于 cxf 客户端调用 WebService 可以简单概述 2 中模式:动态调用和协议调用;
package com.dbgo.webservicedemo;
import com.dbgo.webservicedemo.Model.User;
import com.dbgo.webservicedemo.service.UserService;
import org.apache.cxf.endpoint.Client;
import org.apache.cxf.frontend.ClientProxy;
import org.apache.cxf.jaxws.JaxWsProxyFactoryBean;
import org.apache.cxf.jaxws.endpoint.dynamic.JaxWsDynamicClientFactory;
import org.apache.cxf.transport.http.HTTPConduit;
import org.apache.cxf.transports.http.configuration.HTTPClientPolicy;
import java.util.ArrayList;
public class webserviceclient {
</span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">动态调用</span>
<span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">static</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> main(String[] args) throws Exception {
JaxWsDynamicClientFactory dcflient</span>=<span style="color: rgba(0, 0, 0, 1)">JaxWsDynamicClientFactory.newInstance();
Client client</span>=dcflient.createClient(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">http://localhost:8080/service/user?wsdl</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
Object[] objects</span>=client.invoke(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">getUser</span><span style="color: rgba(128, 0, 0, 1)">"</span>,<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">411001</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
System.</span><span style="color: rgba(0, 0, 255, 1)">out</span>.println(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">*******</span><span style="color: rgba(128, 0, 0, 1)">"</span>+objects[<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">].toString());
Object[] objectall</span>=client.invoke(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">getAlLUser</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
System.</span><span style="color: rgba(0, 0, 255, 1)">out</span>.println(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">*******</span><span style="color: rgba(128, 0, 0, 1)">"</span>+objectall[<span style="color: rgba(128, 0, 128, 1)">0</span><span style="color: rgba(0, 0, 0, 1)">].toString());
main3(args);
}
</span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">调用方式二,通过接口协议获取数据类型</span>
<span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">static</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> main2(String[] args) throws Exception {
JaxWsProxyFactoryBean jaxWsProxyFactoryBean</span>=<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> JaxWsProxyFactoryBean();
jaxWsProxyFactoryBean.setAddress(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">http://localhost:8080/service/user?wsdl</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
jaxWsProxyFactoryBean.setServiceClass(UserService.</span><span style="color: rgba(0, 0, 255, 1)">class</span><span style="color: rgba(0, 0, 0, 1)">);
UserService userService</span>=<span style="color: rgba(0, 0, 0, 1)">(UserService)jaxWsProxyFactoryBean.create();
User userResult</span>= userService.getUser(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">411001</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
System.</span><span style="color: rgba(0, 0, 255, 1)">out</span>.println(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">UserName:</span><span style="color: rgba(128, 0, 0, 1)">"</span>+<span style="color: rgba(0, 0, 0, 1)">userResult.getUsername());
ArrayList</span><User> users=<span style="color: rgba(0, 0, 0, 1)">userService.getAlLUser();
}
</span><span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)">调用方式三,通过接口协议获取数据类型,设置链接超时和响应时间</span>
<span style="color: rgba(0, 0, 255, 1)">public</span> <span style="color: rgba(0, 0, 255, 1)">static</span> <span style="color: rgba(0, 0, 255, 1)">void</span><span style="color: rgba(0, 0, 0, 1)"> main3(String[] args) throws Exception {
JaxWsProxyFactoryBean jaxWsProxyFactoryBean</span>=<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> JaxWsProxyFactoryBean();
jaxWsProxyFactoryBean.setAddress(</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">http://localhost:8080/service/user?wsdl</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
jaxWsProxyFactoryBean.setServiceClass(UserService.</span><span style="color: rgba(0, 0, 255, 1)">class</span><span style="color: rgba(0, 0, 0, 1)">);
UserService userService </span>= (UserService) jaxWsProxyFactoryBean.create(); <span style="color: rgba(0, 128, 0, 1)">//</span><span style="color: rgba(0, 128, 0, 1)"> 创建客户端对象</span>
Client proxy=<span style="color: rgba(0, 0, 0, 1)"> ClientProxy.getClient(userService);
HTTPConduit conduit</span>=<span style="color: rgba(0, 0, 0, 1)">(HTTPConduit)proxy.getConduit();
HTTPClientPolicy policy</span>=<span style="color: rgba(0, 0, 255, 1)">new</span><span style="color: rgba(0, 0, 0, 1)"> HTTPClientPolicy();
policy.setConnectionTimeout(</span><span style="color: rgba(128, 0, 128, 1)">1000</span><span style="color: rgba(0, 0, 0, 1)">);
policy.setReceiveTimeout(</span><span style="color: rgba(128, 0, 128, 1)">1000</span><span style="color: rgba(0, 0, 0, 1)">);
conduit.setClient(policy);
User userResult</span>= userService.getUser(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">411001</span><span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(0, 0, 0, 1)">);
System.</span><span style="color: rgba(0, 0, 255, 1)">out</span>.println(<span style="color: rgba(128, 0, 0, 1)">"</span><span style="color: rgba(128, 0, 0, 1)">UserName:</span><span style="color: rgba(128, 0, 0, 1)">"</span>+<span style="color: rgba(0, 0, 0, 1)">userResult.getUsername());
ArrayList</span><User> users=<span style="color: rgba(0, 0, 0, 1)">userService.getAlLUser();
}
}
基于 wsimport 和 JAX-WS 调用 Web Service 接口
使用 Jdk 原生态 wsimport 指令生成相应的接口文件,来调取 webservice 接口。操作如下:
1、生成接口文件:cmd->wsimport -d . -s . -p acme.client http://127.0.0.1/Services/InvoiceService.asmx?WSDL
即可通过 cmd 命令生成相应的接口文件;
参数说明:
-d 指定生成输出文件的保存路径(.class 文件,根据需要决定是否生成 class 文件)
-s 指定生成的 java 源文件的保存路径(.java 文件,根据需要决定是否生成 java 源文件)
-p 指定生成的 java 类的包(package)名称
http://127.0.0.1/Services/InvoiceService.asmx?WSDL URL 地址,URL 地址后面必须添加“?WSDL”参数。WSDL 参数也可以是小写(wsdl)。
2、配置调用相应的文件
import java.net.MalformedURLException;
import java.net.URL;
import javax.xml.namespace.QName;
import com.opertion.wsimport.HiService;
/
- 使用 Service 类进行调用
- @author Administrator
*/
public class Service {
public static void main(String[] args) throws MalformedURLException {
//wsdl 网络路径
URL url = new URL("http://127.0.0.1/Services/InvoiceService.asmx?WSDL");
//服务描述中服务端点的限定名称 两个参数分别为 命名空间 服务名
QName qName = new QName("http://tempuri.org/", "InvoiceService");
//创建服务对象
javax.xml.ws.Service service = javax.xml.ws.Service.create(url, qName);
//获得 Hiservice 的实现类对象
InvoiceService hiService = service.getPort(new QName("http://tempuri.org/","InvoiceServiceSoap"),InvoiceService.class);
//调用 WebService 方法
System.out.println(hiService.sayHi("xiaoming"));
}
}
注意事项:
命名空间 (http://tempuri.org/) 的取值,是如下内容:
服务名称 InvoiceService 和 InvoiceServiceSoap 的取值:
参考博客
Spring boot+CXF 开发 WebService Demo https://www.cnblogs.com/fuxin41/p/6289162.html
springboot1.5.4 集成 cxf 完整实例 https://www.cnblogs.com/xiaojf/p/7231529.html
JAX-WS 调用 Web Service 参考地址
通过 javax.xml.ws.Service 的方式调用 WebService https://blog.csdn.net/syy19930112/article/details/17427165
使用 wsimport 和 JAX-WS 调用 Web Service 接口 https://www.cnblogs.com/yitouniu/p/7640079.html#commentform