基于SpringBoot使用CXF框架

前面章节中我们介绍了如何基于标准JavaEE和Wildfly应用服务器使用CXF框架实现JAX-WS和JAX-RS服务,这篇笔记我们继续介绍如何在SpringBoot中集成CXF进行JAX-WS开发。对于JAX-RS,实际上我们可能更倾向于使用SpringMVC框架,因此我们这里仅介绍如何使用CXF实现JAX-WS服务。

这篇笔记我们使用SpringBoot2.7.18和JDK8为例进行介绍。

引入Maven依赖

CXF提供了SpringBoot的起步依赖,我们直接引入即可。

<dependency>
    <groupId>org.apache.cxf</groupId>
    <artifactId>cxf-spring-boot-starter-jaxws</artifactId>
    <version>3.2.1</version>
</dependency>

注意CXF框架额外依赖Hibernate Validation,目前实测3.2.1版本如果不引入会在启动阶段报错,因此我们还需要保证工程中存在如下依赖。

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-validation</artifactId>
</dependency>

开发JAX-WS服务端

我们的SpringBoot工程目录结构如下。

|_ src/main
    |_ java
        |_ com.gacfox.demo.demows
            |_ config
                |_ WsConfig.java
            |_ model
                |_ Weather.java
            |_ service
                |_ WeatherService.java
                |_ impl
                    |_ WeatherServiceImpl.java
            |_ DemowsApplication.java
    |_ resources
        |_ application.properties

首先我们创建实体类、SEI接口类和实现类,这些代码和之前JAX-WS章节中的完全一致,唯一的区别是对于WebService实现类我们使用了Spring的@Component注解将其托管到Spring的IoC容器。

package com.gacfox.demo.demows.model;

import lombok.Data;

import java.util.Date;

@Data
public class Weather {
    private String city;
    private String weather;
    private int temperature;
    private Date date;
}
package com.gacfox.demo.demows.service;

import com.gacfox.demo.demows.model.Weather;

import javax.jws.WebMethod;
import javax.jws.WebParam;
import javax.jws.WebResult;
import javax.jws.WebService;
import javax.jws.soap.SOAPBinding;

@WebService(name = "WeatherServicePortType",
        targetNamespace = "http://service.demows.demo.gacfox.com/")
@SOAPBinding(style = SOAPBinding.Style.RPC, use = SOAPBinding.Use.LITERAL)
public interface WeatherService {
    @WebMethod(operationName = "queryWeather")
    @WebResult(name = "weather")
    Weather queryWeather(@WebParam(name = "city") String city);
}
package com.gacfox.demo.demows.service.impl;

import com.gacfox.demo.demows.model.Weather;
import org.springframework.stereotype.Component;
import com.gacfox.demo.demows.service.WeatherService;

import javax.jws.WebService;
import java.util.Date;

@Component("weatherService")
@WebService(endpointInterface = "com.gacfox.demo.demows.service.WeatherService",
        targetNamespace = "http://service.demows.demo.gacfox.com/",
        serviceName = "WeatherService",
        portName = "WeatherServicePort")
public class WeatherServiceImpl implements WeatherService {
    @Override
    public Weather queryWeather(String city) {
        // ... 具体业务逻辑
        return weather;
    }
}

然后我们在配置类WsConfig中手动注册JAX-WS接口。

package com.gacfox.demo.demows.config;

import org.apache.cxf.Bus;
import org.apache.cxf.jaxws.EndpointImpl;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import com.gacfox.demo.demows.service.WeatherService;

import javax.xml.ws.Endpoint;

@Configuration
public class WsConfig {
    @Bean
    public Endpoint endpoint(Bus bus, WeatherService weatherService) {
        Endpoint endpoint = new EndpointImpl(bus, weatherService);
        endpoint.publish("/WeatherService");
        return endpoint;
    }
}

代码中,我们依赖注入了WebService实例和一个Bus实例,这个Bus是CXF框架的核心类,其中包含了CXF的运行时环境等信息,我们在EndPointImpl的构造函数参数中传入这些对象并将这个接口注册到/WeatherService路径上。

最后,我们在SpringBoot工程的application.properties配置文件中添加如下配置。

cxf.path=/ws

该配置用于指定CXF框架处理的基础路径。我们前面介绍过CXF框架本身也是基于Servlet实现的,其实这个配置就是用在CXF的核心Servlet上。

访问WSDL文档

正常启动工程后,按照我们之前注册的CXF基础路径和WebService接口路径,我们使用浏览器访问http://localhost:8080/ws/WeatherService?wsdl即可看到WSDL文档。

作者:Gacfox
版权声明:本网站为非盈利性质,文章如非特殊说明均为原创,版权遵循知识共享协议CC BY-NC-ND 4.0进行授权,转载必须署名,禁止用于商业目的或演绎修改后转载。
Copyright © 2017-2024 Gacfox All Rights Reserved.
Build with NextJS | Sitemap