2013-03-04 46 views
0

所以,我有一个公开Web服务端点的路由。在收到请求后,我会向某些队列发送一些信息,并且我想返回原始呼叫者的回复。 响应是一个枚举,可以有4个值(OK,NULL,RPT,NOK)骆驼:如何在处理CXF请求后返回有效的SOAP响应

我可以在soapUI中获得响应,但它不在有效的SOAP Envelope中。这意味着当在Java或.Net中处理响应时,会抛出异常,表示没有有效的Envelope名称空间。

如何保证发送的响应是SOAPMessage?

要生成我responde消息我有这样的方法:

public OnClientEventResponse process(Message message){ 
    if(message.getBody().toString().contains("OnClientEventResponse")){ 
     return (OnClientEventResponse) message.getBody(); 
    } 
    OnClientEventResponse resp = new OnClientEventResponse(); 
    resp.setReturn(Response.OK); 
    return resp; 
} 

在SOAPUI我得到这个:

<onClientEventResponse> 
    <Response>OK</Response> 
</onClientEventResponse> 

,但我需要的东西是这样的:

<soap:Envelope xmlns:soap="blabla/soap/envelope"> 
<soap:Headers/> 
<soap:Body> 
    <onClientEventResponse> 
     <Response>OK</Response> 
    </onClientEventResponse> 
<soap:Body> 
<soap:Envelope> 

我的web服务接口类是:

@WebService(name = "ClientEventNotifierEndpoint") 
public interface ClientEventNotifierEndpoint { 

@WebMethod(operationName = "onClientEvent", action = "urn:OnClientEvent") 
@WebResult(name = "return") 
public Response onClientEvent(@WebParam(name = "readerCode") String readerCode, @WebParam(name = "clientRfid") String clientRfid, 
     @WebParam(name = "eventType") String eventType, @WebParam(name = "dateTime") Date dateTime); 

}

回答

0

我不确定它是否适用于骆驼,但尝试将此注释添加到您的界面。

@WebService(name = "ClientEventNotifierEndpoint") 
@SOAPBinding(style = SOAPBinding.Style.RPC) 

公共接口ClientEventNotifierEndpoint {

4

我相信你不再等待这个答案,但因为我刚刚完成了去寻找同样在这里是你必须做的:

package com.xxxxx.esb.invoice.processors; 

import java.io.StringWriter; 
import java.util.ArrayList; 
import java.util.List; 

import javax.xml.bind.JAXBContext; 
import javax.xml.bind.JAXBElement; 
import javax.xml.bind.Marshaller; 
import javax.xml.namespace.QName; 
import javax.xml.transform.Source; 
import javax.xml.transform.dom.DOMSource; 

import org.apache.camel.Exchange; 
import org.apache.camel.Processor; 
import org.apache.camel.component.cxf.CxfPayload; 
import org.apache.camel.converter.jaxp.XmlConverter; 
import org.apache.cxf.binding.soap.SoapHeader; 
import org.apache.log4j.Logger; 
import org.w3c.dom.Document; 

import com.xxxxx.esb.invoice_service_spec.ProcessFileResponse; 

/** 
* @author pantinor 
* 
* 
* 
*/ 
public class SoapResponseProcessor implements Processor { 
    private static final String ROOT_NODE = "processFileResponse"; 
    private static final String NAMESPACE = "http://www.xxxxx.com/Esb/invoice-service -spec"; 
    private static final String OK = "OK"; 
    protected static final Logger LOG = Logger 
      .getLogger(SoapResponseProcessor.class); 

    @Override 
    public void process(Exchange exchange) throws Exception { 
     //lots a support classes to serialize my answer 
     List<Source> outElements = new ArrayList<Source>(); 
     XmlConverter converter = new XmlConverter(); 
     StringWriter writer = new StringWriter(); 
     JAXBContext context = JAXBContext 
       .newInstance(ProcessFileResponse.class); 
     Marshaller m = context.createMarshaller(); 

     //build my business answer 
     ProcessFileResponse result = new ProcessFileResponse(); 
     result.setReturn(OK); 

     //serialize the answer 

     //the following is required since the JAXB annotated class does not include  the XMLRoot annotation 
     m.marshal(new JAXBElement<ProcessFileResponse>(new QName(NAMESPACE, 
       ROOT_NODE), ProcessFileResponse.class, result), writer); 

     Document outDocument = converter.toDOMDocument(writer.toString()); 
     outElements.add(new DOMSource(outDocument.getDocumentElement())); 

     //use camel class cxf class to produce a payload that the cxf component can  consume for the answer 
     CxfPayload<SoapHeader> responsePayload = new CxfPayload<SoapHeader>(
       null, outElements, null); 

     //write the anwer 
     exchange.getIn().setBody(responsePayload); 


    } 

}  
+0

非常感谢你,我确实不再需要这个,但当我回家后我会尝试它,并会回复你。如果有效,我会选择它作为答案。感谢分享。 当时我解决它的方法是自己添加Envelope,非常粗糙,但是在当时做了诀窍。 – 2013-07-17 15:15:46