camel-users mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "S. Ali Tokmen" <savas-ali.tok...@bull.net>
Subject CXF consumer: fault handling
Date Wed, 04 Aug 2010 13:30:44 GMT
Hello

I use the CAMEL-CXF component to create Web Service based on a 
preexisting WSDL. The CXF codegen plugin generates for me all classes 
with everything annotated correctly, in particular WSDL fault classes 
annotated correctly.

Now, here's my issue: if I do as described in 
http://camel.apache.org/cxf.html#CXF-HowtothrowaSOAPFaultfromCamel and 
throw the exception generated by CXF codegen in a processor, CXF returns:

    <soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
    <soap:Body>
    <soap:Fault>
    <faultcode>soap:Server</faultcode>
    <faultstring>Failed searching for address: Could not send
    Message.</faultstring>
    </soap:Fault>
    </soap:Body>
    </soap:Envelope>

It therefore copies the exception message from the thrown exception, 
which is nice, but one important thing is missing: the fault detail is 
not set. Because of this, when I call my Web Service with a JAX-WS 
client, it throws me back a Fault instead of an 
AddressNotFoundFault_Exception (generated by CXF codegen).

In order to overcome this issue, I've created a CAMEL exception handler 
that ends with the following processor:

    Throwable cause = exchange.getProperty(Exchange.EXCEPTION_CAUGHT,
    Throwable.class);
    WebFault faultAnnotation =
    cause.getClass().getAnnotation(WebFault.class);
    if (faultAnnotation == null) {
         // The thrown exception is not a WebFault.
         // Let the CAMEL CXF classic error return handle this.
         return;
    }

    Fault fault = new Fault(cause);
    if (cause.getMessage() != null) {
         fault.setMessage(cause.getMessage());
    } else {
         fault.setMessage(cause.getClass().getSimpleName());
    }

    Element detail = fault.getOrCreateDetail();
    Element faultDetails = detail.getOwnerDocument().createElementNS(
         faultAnnotation.targetNamespace(), faultAnnotation.name());
    detail.appendChild(faultDetails);

    exchange.getOut().setFault(true);
    exchange.getOut().setBody(fault);

With that modification, the CAMEL CXF component returns:

    <soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
    <soap:Body>
    <soap:Fault>
    <faultcode>soap:Server</faultcode>
    <faultstring>Failed searching for address: Could not send
    Message.</faultstring>
    <detail>
    <AddressNotFoundFault xmlns="http://soap-test.camel.jonas.ow2.org/"/>
    </detail>
    </soap:Fault>
    </soap:Body>
    </soap:Envelope>

... and the JAX-WS client throws the AddressNotFoundFault_Exception. 
Marvellous.

Now, is this an expected behavior? If no, and that the patch is correct, 
could it be integrated into (I guess) 
org.apache.camel.component.cxf.CxfConsumer.java 's checkFailure method?

Cheers

-- 

S. Ali Tokmen
savas-ali.tokmen@bull.net

Office: +33 4 76 29 76 19
GSM:    +33 66 43 00 555

Bull, Architect of an Open World TM
http://www.bull.com


Mime
  • Unnamed multipart/alternative (inline, None, 0 bytes)
View raw message