Reputation: 119
I followed chapter 7 of Camel in Action book and implemented a CXF route.
<cxf:cxfEndpoint
id="orderEndpoint"
address="http://localhost:9000/order/"
serviceClass="test.order.OrderEndpoint"
wsdlURL="wsdl/order.wsdl" />
<camelContext xmlns="http://camel.apache.org/schema/spring">
<route>
<!-- Expose route as web service endpoint -->
<from uri="cxf:bean:orderEndpoint" />
<to uri="log:orderEndpoint_MsgIn" />
<to uri="seda:incomingOrders" />
<transform>
<constant>OK</constant>
</transform>
<to uri="log:orderEndpoint_MsgOut" />
</route>
<!-- test route -->
<route>
<from uri="seda:incomingOrders" />
<to uri="mock:end" />
</route>
</camelContext>
Then I implemented a java console class to test the route
public static void main(String[] args) throws Exception{
Main main = new Main();
AbstractApplicationContext context = new ClassPathXmlApplicationContext(
"META-INF/spring/cxfWsComponentTestContext.xml"
);
main.setApplicationContext(context);
main.start();
ProducerTemplate producer = main.getCamelTemplate();
List<Object> params = new ArrayList<Object>();
params.add("motor");
params.add(1);
params.add("honda");
String reply = producer.requestBody("cxf:bean:orderEndpoint", params, String.class);
LOG.info("Received reply from orderEndpoint = " + reply);
Thread.sleep(10000);
main.stop();
}
Expect that the console log should display
"Received reply from orderEndpoint = OK"
However, I got
"Received reply from orderEndpoint = null"
In the console log I can see that the entry
"orderEndpoint_MsgOut INFO Exchange[ExchangePattern: InOut, BodyType: String, Body: OK]"
which means that the Web service should have generated reply message "OK", but I'm not sure why this reply message was not carry over as a return value of the requestBody() method call...
I downloaded Camel in Action chapter 7's sample code and run the Junit test case, it was able to return the result as expected... I tried to compare the route definitions and source code with mine but not able to spot any difference so far...
Would like to see if anyone can give some clues on this.
--- Edit 1 ---
I have updated the route definition and remain only the route as below
<route>
<from uri="cxf:bean:orderEndpoint" />
<transform>
<constant>OK</constant>
</transform>
<to uri="seda:incomingOrders" />
</route>
And updated the main method
producer.requestBody("cxf:bean:orderEndpoint", params, String.class);
ConsumerTemplate consumer = producer.getCamelContext().createConsumerTemplate();
Exchange reply = consumer.receive("seda:incomingOrders");
LOG.info("Received reply from seda:incomingOrders = " + reply);
However, it failed with timeout exception
org.apache.camel.ExchangeTimedOutException: The OUT message was not received within: 30000 millis. Exchange[Message: OK]
at org.apache.camel.component.seda.SedaProducer.process(SedaProducer.java:144)
at org.apache.camel.processor.SendProcessor.process(SendProcessor.java:129)
at org.apache.camel.management.InstrumentationProcessor.process(InstrumentationProcessor.java:77)
at org.apache.camel.processor.RedeliveryErrorHandler.process(RedeliveryErrorHandler.java:448)
at org.apache.camel.processor.CamelInternalProcessor.process(CamelInternalProcessor.java:191)
at org.apache.camel.processor.Pipeline.process(Pipeline.java:118)
at org.apache.camel.processor.Pipeline.process(Pipeline.java:80)
at org.apache.camel.processor.CamelInternalProcessor.process(CamelInternalProcessor.java:191)
at org.apache.camel.component.cxf.CxfConsumer$1.asyncInvoke(CxfConsumer.java:95)
at org.apache.camel.component.cxf.CxfConsumer$1.invoke(CxfConsumer.java:75)
at org.apache.cxf.interceptor.ServiceInvokerInterceptor$1.run(ServiceInvokerInterceptor.java:59)
at java.util.concurrent.Executors$RunnableAdapter.call(Executors.java:471)
at java.util.concurrent.FutureTask.run(FutureTask.java:262)
at org.apache.cxf.interceptor.ServiceInvokerInterceptor$2.run(ServiceInvokerInterceptor.java:126)
at org.apache.cxf.workqueue.SynchronousExecutor.execute(SynchronousExecutor.java:37)
at org.apache.cxf.interceptor.ServiceInvokerInterceptor.handleMessage(ServiceInvokerInterceptor.java:131)
at org.apache.cxf.phase.PhaseInterceptorChain.doIntercept(PhaseInterceptorChain.java:308)
at org.apache.cxf.transport.ChainInitiationObserver.onMessage(ChainInitiationObserver.java:121)
at org.apache.cxf.transport.http.AbstractHTTPDestination.invoke(AbstractHTTPDestination.java:251)
at org.apache.cxf.transport.http_jetty.JettyHTTPDestination.doService(JettyHTTPDestination.java:234)
at org.apache.cxf.transport.http_jetty.JettyHTTPHandler.handle(JettyHTTPHandler.java:70)
at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1129)
at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1065)
at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:141)
at org.eclipse.jetty.server.handler.ContextHandlerCollection.handle(ContextHandlerCollection.java:215)
at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:97)
at org.eclipse.jetty.server.Server.handle(Server.java:497)
at org.eclipse.jetty.server.HttpChannel.handle(HttpChannel.java:310)
at org.eclipse.jetty.server.HttpConnection.onFillable(HttpConnection.java:257)
at org.eclipse.jetty.io.AbstractConnection$2.run(AbstractConnection.java:540)
at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:635)
at org.eclipse.jetty.util.thread.QueuedThreadPool$3.run(QueuedThreadPool.java:555)
at java.lang.Thread.run(Thread.java:745)
Upvotes: 3
Views: 1668
Reputation: 50
You are requesting the body of the CXF endpoint. If you look at your route, you can see that you set the content of the body in the transform tag, which comes after in the route definition. Therefore, it is logical that you don't get OK as a result of requestBody()
. The same applies to your seda endpoint. I'd bet that the Logged body for orderEndpoint_MsgIn
is different from OK.
Concerning your log at orderEndpoint_MsgOut
being correct, it is because you log the body after the transform step.
In order to receive OK, you can use this route :
<route>
<from uri="cxf:bean:orderEndpoint" />
<transform>
<constant>OK</constant>
</transform>
<wireTap uri="seda:incomingOrders" />
</route>
And use ConsumerTemplate
with the seda endpoint :
ConsumerTemplate consumer = producer.getCamelContext().createConsumerTemplate();
String reply = consumer.receive("seda:incomingOrders");
LOG.info("Received reply from seda = " + reply);
You should use this code between the requestBody()
and the main.stop()
.
For an explanation on the use of wireTap
rather than to
, see this post
Upvotes: 2