Proposal for the CXF and Camel integration

classic Classic list List threaded Threaded
7 messages Options
Reply | Threaded
Open this post in threaded view
|

Proposal for the CXF and Camel integration

Willem.Jiang
Administrator
Hi All,

I'd like to do some work of CXF and Camel integration. After talked with
James , I got two typical user scenario here:

I. Using  the Camel as a mediation, CXF endpoints and Camel router are
in the separated JVMs
*  Camel message -> CXF server
The message flow could be:
Camel consumer [Camel message] -> (processors ...) ->CXF producer (CXF
conduit) -> CXF server


*  CXF client -> Camel message -> CXF server
The message flow could be:
CXF client -> Camel consumer [Camel message] -> (processors ...) ->CXF
producer(CXF conduit) ->CXF server

II. Camel is embedded into CXF as a transport implementor, CXF and Camel
are in the same JVM
It looks like Camel will take the charge of other camel endpoints life
cycle.

* For the CXF client which use the Camel transport
The message flow could be
CXF client [CXF message]-> Camel transport [Camel message]-> Camel router
The Router part message flow could be
Camel consumer [Camel message] ->  (processors ...) ->  Camel Services
or other Camel Producer

* For the CXF Server which use the Camel transport
CXF Service (create destination message observer) -> Camel transport ->
Camel router
The Router part message flow could be
Camel consumer [Camel message] ->  (processors ...) ->  Camel producer
-> CXF message observer [CXF message]

Any thoughts?

Willem





Reply | Threaded
Open this post in threaded view
|

Re: Proposal for the CXF and Camel integration

jstrachan
On 8/7/07, Willem Jiang <[hidden email]> wrote:
> Hi All,
>
> I'd like to do some work of CXF and Camel integration.

Awesome!


> After talked with
> James , I got two typical user scenario here:
>
> I. Using  the Camel as a mediation, CXF endpoints and Camel router are
> in the separated JVMs
> *  Camel message -> CXF server
> The message flow could be:
> Camel consumer [Camel message] -> (processors ...) ->CXF producer (CXF
> conduit) -> CXF server
>
>
> *  CXF client -> Camel message -> CXF server
> The message flow could be:
> CXF client -> Camel consumer [Camel message] -> (processors ...) ->CXF
> producer(CXF conduit) ->CXF server
>
> II. Camel is embedded into CXF as a transport implementor, CXF and Camel
> are in the same JVM
> It looks like Camel will take the charge of other camel endpoints life
> cycle.
>
> * For the CXF client which use the Camel transport
> The message flow could be
> CXF client [CXF message]-> Camel transport [Camel message]-> Camel router
> The Router part message flow could be
> Camel consumer [Camel message] ->  (processors ...) ->  Camel Services
> or other Camel Producer
>
> * For the CXF Server which use the Camel transport
> CXF Service (create destination message observer) -> Camel transport ->
> Camel router
> The Router part message flow could be
> Camel consumer [Camel message] ->  (processors ...) ->  Camel producer
> -> CXF message observer [CXF message]
>
> Any thoughts?

That sounds about right to me. From a high level there are lots of
permuations for how Camel and CXF can work together;

i) CXF is the client, Camel is the server (using CXF to send messages
into some Camel component)
ii) Camel is the client, CXF is the server (i.e. binding camel
messages to CXF endpoints)
iii) Camel is inside CXF as a Transport (e.g. using Camel's XMPP, IRC
or email transport etc
iv) Camel is a mediation router inside CXF

Actually iii and iv are kinda the same; CXF client -> Camel processors
-> CXF endpoint

I think you've captured the various possible flows correctly. The next
challenge is implementing them :)

In terms of the code thats there in camel-cxf; the transport
implementation is kinda bogus; I tried basically porting the jms
transport of CXF to camel without much clue what I was doing, so you
might wanna trash that and start again :)

The other components; we kinda have 2 right now which is maybe not
ideal; one was an attempt at doing a direct POJO invocation (e.g. if
the message payload contains POJOs rather than InputStream) while the
other was trying to do a more usual InputStream/transport type
invocation. I guess Camel could work at various CXF injection points
(before marshalling, maybe during marshalling, after marshalling etc)
- so we might find we do need some flexibility in how a Camel message
binds to CXF and vice versa.

Please do experiment and see what you think; I'm not yet sure how the
Camel-CXF stuff should look, so I'm hoping we can keep experimenting
until we find we're close to what we really need
--
James
-------
http://macstrac.blogspot.com/
Reply | Threaded
Open this post in threaded view
|

Re: Proposal for the CXF and Camel integration

William Tam
I basically agree with one comment.  I am not sure single vs seperated jvm
will be much of an implementation difference if we let CXF choose the right
transport factory based on the address.  I would change the
LocalTransportFactory in CxfComponent and let CXF to solve to a factory for
us.
For example, if the endpoint URI is cxf:http://host:28080/test, the http
transport factory will be picked (by CXF).  Or if the URI is
cxf:local://test, we will end up using the local transport factory.  I think
that can be applied to both consumer and provider.  I am doing some
experiment ...

- William


On 8/7/07, James Strachan <[hidden email]> wrote:

>
> On 8/7/07, Willem Jiang <[hidden email]> wrote:
> > Hi All,
> >
> > I'd like to do some work of CXF and Camel integration.
>
> Awesome!
>
>
> > After talked with
> > James , I got two typical user scenario here:
> >
> > I. Using  the Camel as a mediation, CXF endpoints and Camel router are
> > in the separated JVMs
> > *  Camel message -> CXF server
> > The message flow could be:
> > Camel consumer [Camel message] -> (processors ...) ->CXF producer (CXF
> > conduit) -> CXF server
> >
> >
> > *  CXF client -> Camel message -> CXF server
> > The message flow could be:
> > CXF client -> Camel consumer [Camel message] -> (processors ...) ->CXF
> > producer(CXF conduit) ->CXF server
> >
> > II. Camel is embedded into CXF as a transport implementor, CXF and Camel
> > are in the same JVM
> > It looks like Camel will take the charge of other camel endpoints life
> > cycle.
> >
> > * For the CXF client which use the Camel transport
> > The message flow could be
> > CXF client [CXF message]-> Camel transport [Camel message]-> Camel
> router
> > The Router part message flow could be
> > Camel consumer [Camel message] ->  (processors ...) ->  Camel Services
> > or other Camel Producer
> >
> > * For the CXF Server which use the Camel transport
> > CXF Service (create destination message observer) -> Camel transport ->
> > Camel router
> > The Router part message flow could be
> > Camel consumer [Camel message] ->  (processors ...) ->  Camel producer
> > -> CXF message observer [CXF message]
> >
> > Any thoughts?
>
> That sounds about right to me. From a high level there are lots of
> permuations for how Camel and CXF can work together;
>
> i) CXF is the client, Camel is the server (using CXF to send messages
> into some Camel component)
> ii) Camel is the client, CXF is the server (i.e. binding camel
> messages to CXF endpoints)
> iii) Camel is inside CXF as a Transport (e.g. using Camel's XMPP, IRC
> or email transport etc
> iv) Camel is a mediation router inside CXF
>
> Actually iii and iv are kinda the same; CXF client -> Camel processors
> -> CXF endpoint
>
> I think you've captured the various possible flows correctly. The next
> challenge is implementing them :)
>
> In terms of the code thats there in camel-cxf; the transport
> implementation is kinda bogus; I tried basically porting the jms
> transport of CXF to camel without much clue what I was doing, so you
> might wanna trash that and start again :)
>
> The other components; we kinda have 2 right now which is maybe not
> ideal; one was an attempt at doing a direct POJO invocation (e.g. if
> the message payload contains POJOs rather than InputStream) while the
> other was trying to do a more usual InputStream/transport type
> invocation. I guess Camel could work at various CXF injection points
> (before marshalling, maybe during marshalling, after marshalling etc)
> - so we might find we do need some flexibility in how a Camel message
> binds to CXF and vice versa.
>
> Please do experiment and see what you think; I'm not yet sure how the
> Camel-CXF stuff should look, so I'm hoping we can keep experimenting
> until we find we're close to what we really need
> --
> James
> -------
> http://macstrac.blogspot.com/
>
Reply | Threaded
Open this post in threaded view
|

Re: Proposal for the CXF and Camel integration

Willem.Jiang
Administrator
Hi

In the single jvm we could use local transport to send/receive the Camel
message, but we just need other transport the send/receive the Camel
message for separate jvms communication .

I have same idea we should just wrap the transport factory in the CXF,
and Camel not need to touch it. I am also working on it to make a simple
demo work.

For the CXFEndpoint part, I don't think the orginal design of CXF
endpointInfo with adress is enough,
It should hold enough information which we need to setup a CXF server or
client, such as sei class name , wsdl url etc.
The URI could be
cxf://http://localhost:1234/test?wsdl=file://local/helloworld.wsdl&serviceName=.....

But I don't think we can hold so many information in a single URI
string. eg. we just want to pass a service implementor's reference to
the ServiceFactoryBean.
James: Is there a way to use spring to wire up the endpoint information
for CXF?
In CXF we could use a jaxws syntax to setup the CXF server and client

  <jaxws:server id="inlineSoapBinding"
    serviceClass="org.apache.cxf.jaxws.service.Hello"
    address="http://localhost:8080/test">
     <jaxws:serviceBean>
      <bean ref="#helloworld"/>
    </jaxws:serviceBean>
    <jaxws:binding>
      <soap:soapBinding mtomEnabled="true" version="1.2"/>
    </jaxws:binding>
  </jaxws:server>
   ....
 <jaxws:client id="wsdlLocation"
    serviceClass="org.apache.hello_world_soap_http.Greeter"
    serviceName="s:SOAPService"
    xmlns:s="http://apache.org/hello_world_soap_http"
    address="http://localhost:8080/simpleWithAddress"
    wsdlLocation="wsdl/hello_world.wsdl"/>

As you know CXF has two front end that we could use , one is simple
front end and the other is jaxws front end.
May be we need to do some work to auto discover which front end we need
to create the right CXF server or client.

BTW , we still need to set up the CXF interceptors for the CXF consumer
and CXF producer, which we can handler different message mode such as
POJO mode, Payload mode and Message mode :)
Now I am not clear about howto configure it :( and I don't think we can
do it in endpoint's URL.


Willem.


William Tam wrote:

> I basically agree with one comment.  I am not sure single vs seperated jvm
> will be much of an implementation difference if we let CXF choose the right
> transport factory based on the address.  I would change the
> LocalTransportFactory in CxfComponent and let CXF to solve to a factory for
> us.
> For example, if the endpoint URI is cxf:http://host:28080/test, the http
> transport factory will be picked (by CXF).  Or if the URI is
> cxf:local://test, we will end up using the local transport factory.  I think
> that can be applied to both consumer and provider.  I am doing some
> experiment ...
>
> - William
>
>
> On 8/7/07, James Strachan <[hidden email]> wrote:
>  
>> On 8/7/07, Willem Jiang <[hidden email]> wrote:
>>    
>>> Hi All,
>>>
>>> I'd like to do some work of CXF and Camel integration.
>>>      
>> Awesome!
>>
>>
>>    
>>> After talked with
>>> James , I got two typical user scenario here:
>>>
>>> I. Using  the Camel as a mediation, CXF endpoints and Camel router are
>>> in the separated JVMs
>>> *  Camel message -> CXF server
>>> The message flow could be:
>>> Camel consumer [Camel message] -> (processors ...) ->CXF producer (CXF
>>> conduit) -> CXF server
>>>
>>>
>>> *  CXF client -> Camel message -> CXF server
>>> The message flow could be:
>>> CXF client -> Camel consumer [Camel message] -> (processors ...) ->CXF
>>> producer(CXF conduit) ->CXF server
>>>
>>> II. Camel is embedded into CXF as a transport implementor, CXF and Camel
>>> are in the same JVM
>>> It looks like Camel will take the charge of other camel endpoints life
>>> cycle.
>>>
>>> * For the CXF client which use the Camel transport
>>> The message flow could be
>>> CXF client [CXF message]-> Camel transport [Camel message]-> Camel
>>>      
>> router
>>    
>>> The Router part message flow could be
>>> Camel consumer [Camel message] ->  (processors ...) ->  Camel Services
>>> or other Camel Producer
>>>
>>> * For the CXF Server which use the Camel transport
>>> CXF Service (create destination message observer) -> Camel transport ->
>>> Camel router
>>> The Router part message flow could be
>>> Camel consumer [Camel message] ->  (processors ...) ->  Camel producer
>>> -> CXF message observer [CXF message]
>>>
>>> Any thoughts?
>>>      
>> That sounds about right to me. From a high level there are lots of
>> permuations for how Camel and CXF can work together;
>>
>> i) CXF is the client, Camel is the server (using CXF to send messages
>> into some Camel component)
>> ii) Camel is the client, CXF is the server (i.e. binding camel
>> messages to CXF endpoints)
>> iii) Camel is inside CXF as a Transport (e.g. using Camel's XMPP, IRC
>> or email transport etc
>> iv) Camel is a mediation router inside CXF
>>
>> Actually iii and iv are kinda the same; CXF client -> Camel processors
>> -> CXF endpoint
>>
>> I think you've captured the various possible flows correctly. The next
>> challenge is implementing them :)
>>
>> In terms of the code thats there in camel-cxf; the transport
>> implementation is kinda bogus; I tried basically porting the jms
>> transport of CXF to camel without much clue what I was doing, so you
>> might wanna trash that and start again :)
>>
>> The other components; we kinda have 2 right now which is maybe not
>> ideal; one was an attempt at doing a direct POJO invocation (e.g. if
>> the message payload contains POJOs rather than InputStream) while the
>> other was trying to do a more usual InputStream/transport type
>> invocation. I guess Camel could work at various CXF injection points
>> (before marshalling, maybe during marshalling, after marshalling etc)
>> - so we might find we do need some flexibility in how a Camel message
>> binds to CXF and vice versa.
>>
>> Please do experiment and see what you think; I'm not yet sure how the
>> Camel-CXF stuff should look, so I'm hoping we can keep experimenting
>> until we find we're close to what we really need
>> --
>> James
>> -------
>> http://macstrac.blogspot.com/
>>
>>    
>
>  

Reply | Threaded
Open this post in threaded view
|

Re: Proposal for the CXF and Camel integration

jstrachan
On 8/8/07, Willem Jiang <[hidden email]> wrote:

> Hi
>
> In the single jvm we could use local transport to send/receive the Camel
> message, but we just need other transport the send/receive the Camel
> message for separate jvms communication .
>
> I have same idea we should just wrap the transport factory in the CXF,
> and Camel not need to touch it. I am also working on it to make a simple
> demo work.
>
> For the CXFEndpoint part, I don't think the orginal design of CXF
> endpointInfo with adress is enough,
> It should hold enough information which we need to setup a CXF server or
> client, such as sei class name , wsdl url etc.
> The URI could be
> cxf://http://localhost:1234/test?wsdl=file://local/helloworld.wsdl&serviceName=.....
>
> But I don't think we can hold so many information in a single URI
> string. eg. we just want to pass a service implementor's reference to
> the ServiceFactoryBean.
> James: Is there a way to use spring to wire up the endpoint information
> for CXF?
> In CXF we could use a jaxws syntax to setup the CXF server and client
>
>   <jaxws:server id="inlineSoapBinding"
>     serviceClass="org.apache.cxf.jaxws.service.Hello"
>     address="http://localhost:8080/test">
>      <jaxws:serviceBean>
>       <bean ref="#helloworld"/>
>     </jaxws:serviceBean>
>     <jaxws:binding>
>       <soap:soapBinding mtomEnabled="true" version="1.2"/>
>     </jaxws:binding>
>   </jaxws:server>
>    ....
>  <jaxws:client id="wsdlLocation"
>     serviceClass="org.apache.hello_world_soap_http.Greeter"
>     serviceName="s:SOAPService"
>     xmlns:s="http://apache.org/hello_world_soap_http"
>     address="http://localhost:8080/simpleWithAddress"
>     wsdlLocation="wsdl/hello_world.wsdl"/>

If there's a ton of configuration then we could always configure this
stuff using the normal CXF way in spring.xml - then just refer to it
by name (spring id/name) from Camel.


> As you know CXF has two front end that we could use , one is simple
> front end and the other is jaxws front end.
> May be we need to do some work to auto discover which front end we need
> to create the right CXF server or client.
>
> BTW , we still need to set up the CXF interceptors for the CXF consumer
> and CXF producer, which we can handler different message mode such as
> POJO mode, Payload mode and Message mode :)
> Now I am not clear about howto configure it :( and I don't think we can
> do it in endpoint's URL.

OK. Lets start with the easy stuff and gradually get more complex.

So how about for now we assume CXF client or servers are configured in
spring outside of camel; then we try write a camel
endpoint/producer/consumer so we can consume camel messages and send
them to the CXF service, or we can get a CXF client to send to a camel
producer?

(We can worry about things like POJO v Payload v Message mode later on)

--
James
-------
http://macstrac.blogspot.com/
Reply | Threaded
Open this post in threaded view
|

Re: Proposal for the CXF and Camel integration

Willem.Jiang
Administrator
Hi James,

I agree, let's implement a simple demo first.
I am just trying to create CxfConumser(holds a reference of CXF server)
and CxfProducer (holds a reference of CXF client) with the CXF simple
front endpoint , it is much close now .

Now I have a question about the spring configuration file. Can we put
the Spring context into the endpoint ? So I can easily get the server
and client from the spring context.

Here is  my other question:
When the CXFProducer get the response message, how can this response
message can be process by Camel ?
I just saw the CxfBinding storeCxfResponse. I guess there need a process
somewhere.

BTW, I saw a note in the CxfBinding.createCxfMessage(CxfExchange
exchange), there a note 'Is InputStream the best type to give to CXF?'
in the code.

Here is my answer for that.
CXF uses the stax which is based on the stream API to parser the XML, so
the CXF transport is also based on the stream API.
And the interceptors are also based on the stream API, so we still need
to use the InputStream to hold the CXF on wire message.


Willem.

James Strachan wrote:

> On 8/8/07, Willem Jiang <[hidden email]> wrote:
>  
>> Hi
>>
>> In the single jvm we could use local transport to send/receive the Camel
>> message, but we just need other transport the send/receive the Camel
>> message for separate jvms communication .
>>
>> I have same idea we should just wrap the transport factory in the CXF,
>> and Camel not need to touch it. I am also working on it to make a simple
>> demo work.
>>
>> For the CXFEndpoint part, I don't think the orginal design of CXF
>> endpointInfo with adress is enough,
>> It should hold enough information which we need to setup a CXF server or
>> client, such as sei class name , wsdl url etc.
>> The URI could be
>> cxf://http://localhost:1234/test?wsdl=file://local/helloworld.wsdl&serviceName=.....
>>
>> But I don't think we can hold so many information in a single URI
>> string. eg. we just want to pass a service implementor's reference to
>> the ServiceFactoryBean.
>> James: Is there a way to use spring to wire up the endpoint information
>> for CXF?
>> In CXF we could use a jaxws syntax to setup the CXF server and client
>>
>>   <jaxws:server id="inlineSoapBinding"
>>     serviceClass="org.apache.cxf.jaxws.service.Hello"
>>     address="http://localhost:8080/test">
>>      <jaxws:serviceBean>
>>       <bean ref="#helloworld"/>
>>     </jaxws:serviceBean>
>>     <jaxws:binding>
>>       <soap:soapBinding mtomEnabled="true" version="1.2"/>
>>     </jaxws:binding>
>>   </jaxws:server>
>>    ....
>>  <jaxws:client id="wsdlLocation"
>>     serviceClass="org.apache.hello_world_soap_http.Greeter"
>>     serviceName="s:SOAPService"
>>     xmlns:s="http://apache.org/hello_world_soap_http"
>>     address="http://localhost:8080/simpleWithAddress"
>>     wsdlLocation="wsdl/hello_world.wsdl"/>
>>    
>
> If there's a ton of configuration then we could always configure this
> stuff using the normal CXF way in spring.xml - then just refer to it
> by name (spring id/name) from Camel.
>
>
>  
>> As you know CXF has two front end that we could use , one is simple
>> front end and the other is jaxws front end.
>> May be we need to do some work to auto discover which front end we need
>> to create the right CXF server or client.
>>
>> BTW , we still need to set up the CXF interceptors for the CXF consumer
>> and CXF producer, which we can handler different message mode such as
>> POJO mode, Payload mode and Message mode :)
>> Now I am not clear about howto configure it :( and I don't think we can
>> do it in endpoint's URL.
>>    
>
> OK. Lets start with the easy stuff and gradually get more complex.
>
> So how about for now we assume CXF client or servers are configured in
> spring outside of camel; then we try write a camel
> endpoint/producer/consumer so we can consume camel messages and send
> them to the CXF service, or we can get a CXF client to send to a camel
> producer?
>
> (We can worry about things like POJO v Payload v Message mode later on)
>
>  

Reply | Threaded
Open this post in threaded view
|

Re: Proposal for the CXF and Camel integration

jstrachan
On 8/8/07, Willem Jiang <[hidden email]> wrote:
> Hi James,
>
> I agree, let's implement a simple demo first.
> I am just trying to create CxfConumser(holds a reference of CXF server)
> and CxfProducer (holds a reference of CXF client) with the CXF simple
> front endpoint , it is much close now .

Awesome! :). Am looking forward to it!


> Now I have a question about the spring configuration file. Can we put
> the Spring context into the endpoint ? So I can easily get the server
> and client from the spring context.

We've done this kinda thing before, sure.

Generally how we've done it up to now is that we've added the
ApplicationContext into the component class, which is the factory of
the endpoints; endpoints typically have a reference to the component
which created it, so the endpoint can ask the component for it; or the
lookup could be done by the component at endpoint creation time.

So just implement ApplicationContextAware on the component and it
should just work I think.


As an aside; we've an abstraction called Registry which is accessible
on the CamelContext which allows you to lookup a bean by name, or by
name and type.
http://activemq.apache.org/camel/maven/camel-core/apidocs/org/apache/camel/spi/Registry.html


We've a JNDI and Spring ApplicationContext based implementation. (We
could add an OSGi / OSGi-DS / iPOJO / Guice implementation too etc).

By default if you are using camel-spring and the SpringCamelContext
(which is used when using the spring XML) then the Registry will use
the current ApplicationContext.

So maybe you could just perform your lookups in the Registry instead;
then your code would work when folks are not using Spring etc?


> Here is  my other question:
> When the CXFProducer get the response message, how can this response
> message can be process by Camel ?

You could set the response message on the Exchange.getOut() maybe?
Then the code invoking the producer can extract the output etc?


> I just saw the CxfBinding storeCxfResponse. I guess there need a process
> somewhere.
>
> BTW, I saw a note in the CxfBinding.createCxfMessage(CxfExchange
> exchange), there a note 'Is InputStream the best type to give to CXF?'
> in the code.
>
> Here is my answer for that.
> CXF uses the stax which is based on the stream API to parser the XML, so
> the CXF transport is also based on the stream API.
> And the interceptors are also based on the stream API, so we still need
> to use the InputStream to hold the CXF on wire message.

OK thanks for the clarification!

I guess further down the line - when we look at alternative places to
integrate with CXF at different points in the processing/interceptor
chain (POJO v Payload v Message etc) we could experiment with some
alternatives maybe. e.g. let CXF parse the message via StaX/streams
into some kinda POJO - then put this in the message for Camel to
process. Or vice versa, pass the POJOs to CXF and let it figure out
how to marshall it onto the wire etc.

Keep up the good work Willem!

--
James
-------
http://macstrac.blogspot.com/