之前因为一时没找到实现JAXM服务端的教程,只能放下了对它的学习,转向了JAX-WS。但现在又必须要用到了,于是下狠心一定要从谷歌的“资料库”里找到个解决办法来。还好,谷歌没让我失望:原来实现一个服务端很简单,写个servlet即可。
这里罗列两个给我提供最大帮助的链接:《 Working with SOAP Messages 》 、《深入探索SOAP1.1--使用SAAJ1.2.1》 。
我的开发环境是JDK1.6U7、JEE5(主要用到了它的jaxm-api包)、eclipse3.4 jee版、Tomcat6。
首先建立服务器端的servlet。在eclipse里新建一个dynamic web project(可能其它类型的也可以),再新建一个servlet,我取名ReceiveServlet,继承javax.xml.messaging.JAXMServlet,实现接口javax.xml.messaging.ReqRespListener,具体代码如下:
import java.io.File; import java.io.FileOutputStream; import javax.servlet.ServletConfig; import javax.servlet.ServletException; import javax.xml.messaging.JAXMServlet; import javax.xml.messaging.ReqRespListener; import javax.xml.soap.MessageFactory; import javax.xml.soap.SOAPEnvelope; import javax.xml.soap.SOAPMessage; /** * Servlet implementation class ReceiveServlet */ public class ReceiveServlet extends JAXMServlet implements ReqRespListener { private static final long serialVersionUID = 1L; static MessageFactory mf = null; // create a messagefactory static { try { mf = MessageFactory.newInstance(); } catch (Exception e) { e.printStackTrace(); } }; /** * @see JAXMServlet#JAXMServlet() */ public ReceiveServlet() { super(); } /** * @see ReqRespListener#onMessage(SOAPMessage) */ public SOAPMessage onMessage(SOAPMessage msg) { SOAPMessage resp = null; try { System.out.println("Received message:"); msg.writeTo(new FileOutputStream(new File( "../webapps/soapmessage.xml")));// I use tomcat so set this // directory // create a response message resp = mf.createMessage(); SOAPEnvelope se = resp.getSOAPPart().getEnvelope(); se.getBody().addChildElement(se.createName("ResponseMessage")) .addTextNode("Received Message,Thanks"); return resp; } catch (Exception e) { e.printStackTrace(); } return resp; } /** * @see Servlet#init(ServletConfig) */ public void init(ServletConfig config) throws ServletException { super.init(config); } }
右击工程名,export->war,即完成了servlet的打包,我还将jaxm-api包塞到了war文件的lib目录里,也不知有没有用,没试过。发布这个war文件。这时在浏览器的地址栏里输入调用这个servlet的url会报错:
这就说明部署成功了,因为这个servlet用的不是HTTP协议,无法那样调用。
现在建立客户端,也就是SOAP发送方。随便找个工程(刚才的也行),新建一个含main方法的类,具体代码如下:
import java.io.IOException; import java.net.URL; import javax.xml.messaging.URLEndpoint; import javax.xml.soap.*; public class SOAPSender { /** * @param args * @throws SOAPException * @throws IOException */ public static void main(String[] args) throws IOException, SOAPException { SOAPSender sender = new SOAPSender(); SOAPMessage message = sender.getMessage(); sender.send(message); } public void send(SOAPMessage message) throws IOException, SOAPException { // Create SOAP connection SOAPConnectionFactory scf = SOAPConnectionFactory.newInstance(); SOAPConnection sc = scf.createConnection(); // Most article use this sentence which list below to specify the // endpoint, but I got error when I ran it. // URLEndpoint urlEndpoint = new URLEndpoint( // "http://localhost:8080/SOAP/ReceiveServlet"); // Specify the endpoint URL url = new URL("http://localhost:8080/SOAP/ReceiveServlet"); // Send the SOAP message SOAPMessage response = sc.call(message, url); if (response != null) { // Print the message to console System.out.println("Receive SOAP message from localhost:"); response.writeTo(System.out); } else { System.err.println("No response received from partner!"); } sc.close(); } public SOAPMessage getMessage() throws SOAPException { // Create a message factory MessageFactory mf = MessageFactory.newInstance(); // Create a SOAP message SOAPMessage message = mf.createMessage(); SOAPEnvelope envelope = message.getSOAPPart().getEnvelope(); // Add a namespace declaration to envelope element envelope.addNamespaceDeclaration("cwmp", "some uri"); // Create header element SOAPHeader header = envelope.getHeader(); // Create body element SOAPBody body = envelope.getBody(); SOAPBodyElement bodyElement = body.addBodyElement(envelope.createName( "Test", "cwmp", "uri")); // add content to Test element bodyElement.addTextNode("Just a test! "); try { // Print the message we have created above to console message.writeTo(System.out); } catch (IOException e) { e.printStackTrace(); } return message; } }
现在可以执行这个客户端,console会先显示我们准备发送的message,然后会显示我们从服务器接收到的回复message;在Tomcat的安装目录下的webapps目录下,会找到我们发送给服务器的message。至此,我的这个JAXM小实验就完成了!