1. 程式人生 > >WebService入門 - CXF與Spring整合 (maven專案)

WebService入門 - CXF與Spring整合 (maven專案)

可參考CXF官網-使用Spring編寫服務文件:http://cxf.apache.org/docs/writing-a-service-with-spring.html

1.新增依賴

        <!-- spring與cxf 整合webservice 所需 -->
        <dependency>
            <groupId>org.apache.cxf</groupId>
            <artifactId>cxf-core</artifactId>
            <version>3.1.5</version>
        </dependency>
        <dependency>
            <groupId>org.apache.cxf</groupId>
            <artifactId>cxf-rt-frontend-jaxws</artifactId>
            <version>3.1.5</version>
        </dependency>
        <dependency>
            <groupId>org.apache.cxf</groupId>
            <artifactId>cxf-rt-transports-http</artifactId>
            <version>3.1.5</version>
        </dependency>

2. 編寫提供服務的介面和類

@WebService
public interface ICustomerWSService {
    @WebMethod
    public @WebResult(name="customer") String queryCustomerByTel(@WebParam(name="tel") String tel);
}
@WebService(endpointInterface = "com.zhengqing.basic.ws.service.ICustomerWSService")
public class CustomerWSServiceImpl implements ICustomerWSService {
    @Autowired
    private CustomerMapper customerMapper;
    @WebMethod
    public String queryCustomerByTel(String tel) {
        Customer customer = customerMapper.selectByTel(tel);
        return customer.toString();
    }
}

3.配置applicationContext-ws.xml 

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:jaxws="http://cxf.apache.org/jaxws"
       xmlns:cxf="http://cxf.apache.org/core"
       xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://cxf.apache.org/jaxws http://cxf.apache.org/schemas/jaxws.xsd http://cxf.apache.org/core http://cxf.apache.org/schemas/core.xsd">

    <!-- 引入配置檔案 -->
    <import resource="classpath:META-INF/cxf/cxf.xml"/>
    <import resource="classpath:META-INF/cxf/cxf-servlet.xml"/>

    <!-- cxf攔截器獲取方法資訊和引數資訊 -->
    <cxf:bus>
        <cxf:inInterceptors>
            <ref bean="authenInterceptor"/>
        </cxf:inInterceptors>
    </cxf:bus>

    <bean name="authenInterceptor" class="com.zhengqing.basic.ws.interceptor.AuthInfoInInterceptor"></bean>

    <!-- 將服務暴露出去 -->
    <bean id="customerWSService" class="com.zhengqing.basic.ws.service.impl.CustomerWSServiceImpl"></bean>

    <jaxws:endpoint
            implementor="#customerWSService"
            address="/getCustomer">
    </jaxws:endpoint>

</beans>

4.再將 applicationContext-ws.xml 配置到spring的核心配置檔案 applicationContext.xml 中  (溫馨小提示:我這裡是多模組專案 所以是在web.xml中配置的)

5.web.xml中配置CXF的Servlet

    <!-- cxf的servlet -->
    <servlet>
        <servlet-name>CXFServlet</servlet-name>
        <servlet-class>org.apache.cxf.transport.servlet.CXFServlet</servlet-class>
    </servlet>

    <servlet-mapping>
        <servlet-name>CXFServlet</servlet-name>
        <url-pattern>/webservice/*</url-pattern>
    </servlet-mapping>

6.測試:啟動tomcat - 自動釋出服務
執行可訪問 http://localhost:8080/webservice/getCustomer?wsdl

接下來就可以編寫自己的客戶端了:

public class ClientTest {
	public static void main(String[] args) {
		// 1.建立JaxWsProxyFactoryBean的物件,用於接收服務
		JaxWsProxyFactoryBean proxyFactoryBean = new JaxWsProxyFactoryBean();
		// 2.設定服務的釋出地址,表示去哪裡過去服務
		proxyFactoryBean.setAddress("http://localhost:8080/webservice/getCustomer");
		// 3.設定服務的釋出介面,使用本地的代理介面
		proxyFactoryBean.setServiceClass(ICustomerWSService.class);
		// 4.通過create方法返回介面代理例項
		ICustomerWSService service = (ICustomerWSService) proxyFactoryBean.create();
		// 5.呼叫遠端方法
		System.out.println(service.queryCustomerByTel("10086"));
	}
}

最後即可查詢指定電話號碼的資訊  


如果做攔截器,如下  (判斷使用者是否有許可權去做事情)

public class AuthInfoInInterceptor extends AbstractPhaseInterceptor<SoapMessage>{

	@Autowired
	private EmployeeMapper employeeMapper;

	public AuthInfoInInterceptor() {
		super(Phase.PRE_INVOKE);
	}

	@Override
	public void handleMessage(SoapMessage message) throws Fault {
		String username = null;
		String password = null;

		// 獲取方法資訊
		Exchange exchange = message.getExchange();
		BindingOperationInfo bop = exchange.get(BindingOperationInfo.class);
		MethodDispatcher md = (MethodDispatcher) exchange.get(Service.class).get(MethodDispatcher.class.getName());
		Method method = md.getMethod(bop);
		//方法名
		String methodName = method.getName();
		System.out.println("方法名:"+methodName);

		// 獲取引數
		List<String> content = message.getContent(List.class);
		System.out.println("引數:"+content);

		username = content.get(1);
		password = content.get(2);

		Employee employee = employeeMapper.selectByUsername(username);
		if(!(employee!=null&&employee.getPassword().equals(password))){
			throw new Fault(new IllegalArgumentException("使用者名稱或密碼錯誤!"));
		}

	}

}

我們可以拿到從客戶端傳過來的引數然後去做自己的業務