1. 环境说明
jdk 1.6.0-29
apache cxf 2.7.7
2. 新建web project,并添加apache cxf/lib目录下所需jar,软件目录如下:
3. 程序代码
Book.java
package com.unei.bean; import javax.xml.bind.annotation.XmlRootElement; @XmlRootElement(name = "Book") public class Book { private int bookId; private String bookISBNnumber; private String bookName; private double price; private String author; public double getPrice() { return price; } public void setPrice(double price) { this.price = price; } public int getBookId() { return bookId; } public void setBookId(int bookId) { this.bookId = bookId; } public String getBookISBNnumber() { return bookISBNnumber; } public void setBookISBNnumber(String bookISBNnumber) { this.bookISBNnumber = bookISBNnumber; } public String getBookName() { return bookName; } public void setBookName(String bookName) { this.bookName = bookName; } public String getAuthor() { return author; } public void setAuthor(String author) { this.author = author; } }
IBookService.java
package com.unei.service; import javax.jws.WebMethod; import javax.jws.WebService; import com.unei.bean.Book; @WebService public interface IBookService { @WebMethod public void addBook(Book book); @WebMethod public void deleteBook(int bookId); @WebMethod public void updateBook(Book book); @WebMethod public Book getBook(int bookId); }BookService.java
package com.unei.service.impl; import com.unei.bean.Book; import com.unei.service.IBookService; public class BookService implements IBookService{ @Override public void addBook(Book book) { System.out.println("addBook:"+book.getBookName()); } @Override public void deleteBook(int bookId) { System.out.println("deleteBook:"+bookId); } @Override public void updateBook(Book book) { System.out.println("updateBook:"+book.getBookName()); } @Override public Book getBook(int bookId) { Book book=new Book(); book.setBookId(4); book.setBookName("getBook"); book.setBookISBNnumber("ABCDEFG"); book.setPrice(20.00); return book; } }CheckHandler.java
package com.unei.handler; import java.util.Iterator; import java.util.Set; import javax.xml.namespace.QName; import javax.xml.soap.Node; import javax.xml.soap.SOAPBody; import javax.xml.soap.SOAPConstants; import javax.xml.soap.SOAPEnvelope; import javax.xml.soap.SOAPException; import javax.xml.soap.SOAPFault; import javax.xml.soap.SOAPHeader; import javax.xml.soap.SOAPMessage; import javax.xml.ws.handler.MessageContext; import javax.xml.ws.handler.soap.SOAPHandler; import javax.xml.ws.handler.soap.SOAPMessageContext; import javax.xml.ws.soap.SOAPFaultException; public class CheckHandler implements SOAPHandler<SOAPMessageContext>{ @Override public boolean handleMessage(SOAPMessageContext context) { System.out.println("Server:handleMessage...."); Boolean isResponse=(Boolean)context.get(MessageContext.MESSAGE_OUTBOUND_PROPERTY); if(!isResponse){ System.out.println("request...."); try { SOAPMessage soapMsg=context.getMessage(); SOAPEnvelope soapEnv=soapMsg.getSOAPPart().getEnvelope(); SOAPHeader soapHeader=soapEnv.getHeader(); //if no header,add one,throw exception if(soapHeader==null){ soapHeader=soapEnv.addHeader(); generateSoapErrMessage(soapMsg, "No SOAP header."); } //Get Iterator it=soapHeader.extractHeaderElements(SOAPConstants.URI_SOAP_ACTOR_NEXT); if(it==null||!it.hasNext()){ generateSoapErrMessage(soapMsg, "No header block for next"); } Node a=(Node)it.next(); System.out.println(a.getValue()); } catch (SOAPException e) { e.printStackTrace(); } }else{ System.out.println("response...."); } return true; } @Override public boolean handleFault(SOAPMessageContext context) { return false; } @Override public void close(MessageContext context) { } @Override public Set<QName> getHeaders() { return null; } private void generateSoapErrMessage(SOAPMessage msg,String reason){ try { SOAPBody soapBody=msg.getSOAPPart().getEnvelope().getBody(); SOAPFault soapFault=soapBody.addFault(); soapFault.setFaultString(reason); throw new SOAPFaultException(soapFault); } catch (SOAPException e) { e.printStackTrace(); } } }
web.xml
<web-app xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd" version="2.4"> <!-- 指明spring配置文件在何处 --> <context-param> <param-name>contextConfigLocation</param-name> <param-value>classpath*:applicationContext.xml</param-value> </context-param> <!-- 加载spring配置文件applicationContext.xml --> <listener> <listener-class> org.springframework.web.context.ContextLoaderListener </listener-class> </listener> <servlet> <servlet-name>cxf</servlet-name> <servlet-class>org.apache.cxf.transport.servlet.CXFServlet </servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>cxf</servlet-name> <url-pattern>/services/*</url-pattern> </servlet-mapping> </web-app>
applicationContext.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:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:context="http://www.springframework.org/schema/context" xmlns:jaxws="http://cxf.apache.org/jaxws" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd http://cxf.apache.org/jaxws http://cxf.apache.org/schemas/jaxws.xsd "> <import resource="classpath:META-INF/cxf/cxf.xml" /> <import resource="classpath:META-INF/cxf/cxf-extension-soap.xml" /> <import resource="classpath:META-INF/cxf/cxf.xml" /> <aop:aspectj-autoproxy proxy-target-class="true" /> <bean id="bsServiceBean" class="com.unei.service.impl.BookService" /> <bean id="inLog" class="org.apache.cxf.interceptor.LoggingInInterceptor" /> <bean id="outLog" class="org.apache.cxf.interceptor.LoggingOutInterceptor"/> <jaxws:server id="bookService" serviceClass="com.unei.service.IBookService" address="/bs"> <jaxws:serviceBean> <ref bean="bsServiceBean" /> </jaxws:serviceBean> <jaxws:inInterceptors> <ref bean="inLog" /> </jaxws:inInterceptors> <jaxws:outInterceptors> <ref bean="outLog"/> </jaxws:outInterceptors> <jaxws:handlers> <bean class="com.unei.handler.CheckHandler"/> </jaxws:handlers> </jaxws:server> </beans>在<jaxws:server>标签中添加<jaxws:handlers>标签,声明handler
4. 客户端,新建java project,添加apache cxf/lib目录下所需jar,项目结构如下
5. 项目代码
CheckHandler.java
package com.unei.handler; import java.net.InetAddress; import java.net.NetworkInterface; import java.util.Set; import javax.xml.namespace.QName; import javax.xml.soap.SOAPConstants; import javax.xml.soap.SOAPEnvelope; import javax.xml.soap.SOAPHeader; import javax.xml.soap.SOAPHeaderElement; import javax.xml.soap.SOAPMessage; import javax.xml.ws.handler.MessageContext; import javax.xml.ws.handler.soap.SOAPHandler; import javax.xml.ws.handler.soap.SOAPMessageContext; public class CheckHandler implements SOAPHandler<SOAPMessageContext>{ @Override public void close(MessageContext arg0) { } @Override public boolean handleFault(SOAPMessageContext arg0) { return false; } @Override public boolean handleMessage(SOAPMessageContext context) { Boolean isRequest=(Boolean)context.get(SOAPMessageContext.MESSAGE_OUTBOUND_PROPERTY); if(isRequest){ System.out.println("request..."); SOAPMessage soapMsg=context.getMessage(); SOAPEnvelope soapEnv; try { soapEnv = soapMsg.getSOAPPart().getEnvelope(); SOAPHeader soapHeader=soapEnv.getHeader(); if(soapHeader==null){ soapHeader=soapEnv.addHeader(); } String mac=getMACAddress(); QName qname=new QName("http://localhost","macAddress"); SOAPHeaderElement soapHeaderElement=soapHeader.addHeaderElement(qname); soapHeaderElement.setActor(SOAPConstants.URI_SOAP_ACTOR_NEXT); soapHeaderElement.addTextNode(mac); soapMsg.saveChanges(); soapMsg.writeTo(System.out); } catch (Exception e) { e.printStackTrace(); } }else{ System.out.println("response..."); } return true; } @Override public Set<QName> getHeaders() { return null; } private String getMACAddress() throws Exception{ InetAddress ip; StringBuilder sb=new StringBuilder(); ip=InetAddress.getLocalHost(); System.out.println("Current IP address:"+ip.getHostAddress()); NetworkInterface network=NetworkInterface.getByInetAddress(ip); byte[] mac=network.getHardwareAddress(); System.out.println("Current MAC address:"); for(int i=0;i<mac.length;i++){ sb.append(String.format("%02X%s",mac[i],(i<mac.length-1)?"-":"")); } System.out.println(sb.toString()); return sb.toString(); } }
Client.java
package com.unei.app; import org.springframework.context.support.ClassPathXmlApplicationContext; import com.unei.soap.client.Book; import com.unei.soap.client.IBookService; public class Client { public static void main(String[] args) { ClassPathXmlApplicationContext context=new ClassPathXmlApplicationContext("classpath:applicationContext.xml"); IBookService client=(IBookService)context.getBean("client"); Book b=new Book(); b.setBookId(1); b.setBookName("new book"); client.addBook(b); } }
applicationContext.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:aop="http://www.springframework.org/schema/aop" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:context="http://www.springframework.org/schema/context" xmlns:jaxws="http://cxf.apache.org/jaxws" xsi:schemaLocation=" http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.0.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx-3.0.xsd http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.0.xsd http://cxf.apache.org/jaxws http://cxf.apache.org/schemas/jaxws.xsd "> <import resource="classpath:META-INF/cxf/cxf.xml" /> <import resource="classpath:META-INF/cxf/cxf-extension-soap.xml" /> <import resource="classpath:META-INF/cxf/cxf.xml" /> <aop:aspectj-autoproxy proxy-target-class="true" /> <!-- <bean id="client" class="com.unei.soap.client.IBookService" factory-bean="clientFactory" factory-method="create"/> <bean id="clientFactory" class="org.apache.cxf.jaxws.JaxWsProxyFactoryBean"> <property name="serviceClass" value="com.unei.soap.client.IBookService"/> <property name="address" value="http://localhost:8080/soap/services/bs"/> </bean> --> <jaxws:client id="client" serviceClass="com.unei.soap.client.IBookService" address="http://localhost:8080/soap/services/bs"> <jaxws:handlers> <bean class="com.unei.handler.CheckHandler"/> </jaxws:handlers> </jaxws:client> </beans>
6.程序测试
客户端输出:
request... Current IP address:192.168.1.101 Current MAC address: 00-1F-C6-D6-DC-E8 <soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"><SOAP-ENV:Header xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"><macAddress xmlns="http://localhost" SOAP-ENV:actor="http://schemas.xmlsoap.org/soap/actor/next">00-1F-C6-D6-DC-E8</macAddress></SOAP-ENV:Header><soap:Body><ns2:addBook xmlns:ns2="http://service.unei.com/"><arg0><bookId>1</bookId><bookName>new book</bookName><price>0.0</price></arg0></ns2:addBook></soap:Body></soap:Envelope>response...
服务器端输出:
2013-10-4 21:26:17 org.apache.cxf.services.IBookServiceService.IBookServicePort.IBookService 信息: Inbound Message ---------------------------- ID: 1 Address: http://localhost:8080/soap/services/bs Encoding: UTF-8 Http-Method: POST Content-Type: text/xml; charset=UTF-8 Headers: {Accept=[*/*], cache-control=[no-cache], connection=[keep-alive], Content-Length=[531], content-type=[text/xml; charset=UTF-8], host=[localhost:8080], pragma=[no-cache], SOAPAction=[""], user-agent=[Apache CXF 2.7.7]} Payload: <soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"><SOAP-ENV:Header xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"><macAddress xmlns="http://localhost" xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" SOAP-ENV:actor="http://schemas.xmlsoap.org/soap/actor/next">00-1F-C6-D6-DC-E8</macAddress></SOAP-ENV:Header><soap:Body><ns2:addBook xmlns:ns2="http://service.unei.com/"><arg0><bookId>1</bookId><bookName>new book</bookName><price>0.0</price></arg0></ns2:addBook></soap:Body></soap:Envelope> -------------------------------------- Server:handleMessage.... request.... 00-1F-C6-D6-DC-E8 addBook:new book Server:handleMessage.... response.... 2013-10-4 21:26:17 org.apache.cxf.services.IBookServiceService.IBookServicePort.IBookService 信息: Outbound Message --------------------------- ID: 1 Encoding: UTF-8 Content-Type: text/xml Headers: {} Payload: <soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"><SOAP-ENV:Header xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/"/><soap:Body><ns2:addBookResponse xmlns:ns2="http://service.unei.com/"/></soap:Body></soap:Envelope> --------------------------------------