You are viewing a plain text version of this content. The canonical link for it is here.
Posted to users@camel.apache.org by snowbug <la...@gmail.com> on 2009/09/02 01:25:25 UTC

Why does ExchangeHelper.prepareAggregation modify the in body?

When doing aggregation, this code is executed before the actual aggregation:
    /**
     * Prepares the exchanges for aggregation.
     * <p/>
     * This implementation will copy the OUT body to the IN body so when you
do
     * aggregation the body is only in the IN body to avoid confusing end
users.
     *
     * @param oldExchange  the old exchange
     * @param newExchange  the new exchange
     */
    public static void prepareAggregation(Exchange oldExchange, Exchange
newExchange) {
        // copy body/header from OUT to IN
        if (oldExchange != null) {
            if (oldExchange.hasOut()) {
                oldExchange.getIn().copyFrom(oldExchange.getOut());
                oldExchange.setOut(null);
            }
        }

        if (newExchange != null) {
            if (newExchange.hasOut()) {
                newExchange.getIn().copyFrom(newExchange.getOut());
                newExchange.setOut(null);
            }
        }
    }


I have hard time to understand why the IN is overwritten automatically. IN
is the message that comes in and should only be overwritten if I choose to
based on my business logic, not have the framework code to assume this
behavior. 

To make the matter worse, the DefaultExchange.getOut() will automatically
create an empty Message when it is invoked. In other words, if
DefaultExchange.getOut() is called somewhere either in your code or Camel's
code, the OUT message is automatically created, and the hasOut() method will
then be true, and this default empty OUT message is then automatically
copied to the IN. 

If there is a compelling reason shows this behavior is absolutely necessary,
I'd like to create a bug ticket to have it fixed.

Thanks,
-- 
View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25249162.html
Sent from the Camel - Users mailing list archive at Nabble.com.


Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by Claus Ibsen <cl...@gmail.com>.
On Thu, Sep 3, 2009 at 7:52 AM, snowbug<la...@gmail.com> wrote:
>
> Thanks for the reply.
>
> After digging into EIP and Camel for a couple of hours, I come to understand
> your point and it's probably necessary to be this way.
>

Yeah the IN and OUT and lazy creating OUT is a bit of a pain.
However what works on paper may not work when applied in practice :)


> I ended up solve my problem by wrapping my original message class in a new
> wrapper class, which has methods to keep properties just like Exchange. I
> couldn't use Exchange class for that purpose because the properties I set
> are lost once a message is dropped into a queue. But properties set on my
> wrapper class are kept as they are part of the payload.
>

Ah yeah not all transports can transfer entire exchanges safely.
Usually body and headers are supported.
But some only body, such as a file :)

As said we want to overhaul the aggregator later in Camel 2.2 so any
feedback there is valuable.
Maybe we should offer the end users an API to have access to
- original exchange (the input)
- reply exchange
- merged exchange

In a consistent manner.

And with a pojo option as well to avoid working on low level Camel
Exchange when using parameter binding is sufficient.




> Thanks for the help! BTW, I'm reading your interview at
> http://soa.dzone.com/articles/interview-claus-ibsen-about
> http://soa.dzone.com/articles/interview-claus-ibsen-about  right now :)
>

Happy reading it is a bit long :)

We should get a bit more advertise for Camel now that 2.0 is out of the door.
But as always to busy :(


>
> Alan
>
>
> Claus Ibsen-2 wrote:
>>
>> 1 + 2)
>> No as IN is not the original input, when you do an aggregation. Its
>> the result. However depending on how the route in the aggregation
>> Camel could let the reply be in either IN or OUT so end users was
>> confused.
>>
>> You can not assume that IN is always the payload before aggregation.
>>
>>
>> The aggregator EIP is slated for an overhaul in Camel 2.2, as it have
>> some other areas as well needed to be improved.
>>
>>
>> --
>> Claus Ibsen
>> Apache Camel Committer
>>
>> Open Source Integration: http://fusesource.com
>> Blog: http://davsclaus.blogspot.com/
>> Twitter: http://twitter.com/davsclaus
>>
>>
>
> --
> View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25270209.html
> Sent from the Camel - Users mailing list archive at Nabble.com.
>
>



-- 
Claus Ibsen
Apache Camel Committer

Open Source Integration: http://fusesource.com
Blog: http://davsclaus.blogspot.com/
Twitter: http://twitter.com/davsclaus

Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by snowbug <la...@gmail.com>.
Thanks for the reply. 

After digging into EIP and Camel for a couple of hours, I come to understand
your point and it's probably necessary to be this way. 

I ended up solve my problem by wrapping my original message class in a new
wrapper class, which has methods to keep properties just like Exchange. I
couldn't use Exchange class for that purpose because the properties I set
are lost once a message is dropped into a queue. But properties set on my
wrapper class are kept as they are part of the payload.

Thanks for the help! BTW, I'm reading your interview at 
http://soa.dzone.com/articles/interview-claus-ibsen-about
http://soa.dzone.com/articles/interview-claus-ibsen-about  right now :)


Alan


Claus Ibsen-2 wrote:
> 
> 1 + 2)
> No as IN is not the original input, when you do an aggregation. Its
> the result. However depending on how the route in the aggregation
> Camel could let the reply be in either IN or OUT so end users was
> confused.
> 
> You can not assume that IN is always the payload before aggregation.
> 
> 
> The aggregator EIP is slated for an overhaul in Camel 2.2, as it have
> some other areas as well needed to be improved.
> 
> 
> -- 
> Claus Ibsen
> Apache Camel Committer
> 
> Open Source Integration: http://fusesource.com
> Blog: http://davsclaus.blogspot.com/
> Twitter: http://twitter.com/davsclaus
> 
> 

-- 
View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25270209.html
Sent from the Camel - Users mailing list archive at Nabble.com.


Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by Claus Ibsen <cl...@gmail.com>.
On Wed, Sep 2, 2009 at 11:35 PM, snowbug<la...@gmail.com> wrote:
>
> Another thing I also want to point out is:
>
> the IN is only overwritten if the OUT is not null, so in my aggreator, I do
> not know if the content in IN is the original IN or the new OUT content. In
> other words, it is not consistency.
>
>
> I see the argument of setting the IN automatically, but I feel the
> implementation is still flawed. Leaving both IN and OUT untouched in this
> aggreation case seems is a better alternative as the user at least:
> 1. have control over what IN and OUT should be
> 2. no ambiguous on what the content in IN is.
>
>

1 + 2)
No as IN is not the original input, when you do an aggregation. Its
the result. However depending on how the route in the aggregation
Camel could let the reply be in either IN or OUT so end users was confused.

You can not assume that IN is always the payload before aggregation.


The aggregator EIP is slated for an overhaul in Camel 2.2, as it have
some other areas as well needed to be improved.



> --
> View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25266159.html
> Sent from the Camel - Users mailing list archive at Nabble.com.
>
>



-- 
Claus Ibsen
Apache Camel Committer

Open Source Integration: http://fusesource.com
Blog: http://davsclaus.blogspot.com/
Twitter: http://twitter.com/davsclaus

Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by snowbug <la...@gmail.com>.
Another thing I also want to point out is: 

the IN is only overwritten if the OUT is not null, so in my aggreator, I do
not know if the content in IN is the original IN or the new OUT content. In
other words, it is not consistency.


I see the argument of setting the IN automatically, but I feel the
implementation is still flawed. Leaving both IN and OUT untouched in this
aggreation case seems is a better alternative as the user at least: 
1. have control over what IN and OUT should be
2. no ambiguous on what the content in IN is.


-- 
View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25266159.html
Sent from the Camel - Users mailing list archive at Nabble.com.


Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by snowbug <la...@gmail.com>.
I just started to apply Camel to our project and I like it very much. Don't
have much feedback at this time but will definitely post here if we have any
in the future as we use more and more of Camel's feature.

I think the key to make Camel easy to use are flexibility and consistency.
You've mentioned that there is lots of discussion regarding OUT overwrite
IN. Apparently there is no clear cut answer and we certainly don't need to
repeat the discussion here. It's more of a confusion from me as a new user
of Camel. And I think have a "hasIn()" and "hasOut()" is fine, once I get
know the API better. 

However, like I posted in the last reply above, I think what is not good is
hurting the flexibility in the case of splitter implementation. There is
virtually no way to set the exchange property in the splitter as we are
given only a copy of the object, not the original one.

Thanks,

Alan


Claus Ibsen-2 wrote:
> 
> Hi
> 
> BTW: We do have on the roadmap an overhaul of the aggreagator. So any
> feedback of it is much valuable.
> And combined with the copy on write stuff for the exchanges to avoid
> the pitfalls of OUT overwriting IN etc.
> then it will be better in the future when its implemented.
> 
> The IN and OUT stuff has been debated countless on the camel dev forum.
> James created James to resemble JBI stuff and thus that is why the
> Camel API have this.
> 
> And we all agree the lazy creation of getOut is unfortunate and hence
> why we added the hasOut.
> Changing it to be not lazy would break to much at current time.
> 
> Anyway discussing this is a bit "tired" and it should be done on dev
> forum.
> 
> Just wanted to share a bit hints on background.
> 
> 
> 
> 
> 
> -- 
> Claus Ibsen
> Apache Camel Committer
> 
> Open Source Integration: http://fusesource.com
> Blog: http://davsclaus.blogspot.com/
> Twitter: http://twitter.com/davsclaus
> 
> 

-- 
View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25261523.html
Sent from the Camel - Users mailing list archive at Nabble.com.


Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by Claus Ibsen <cl...@gmail.com>.
Hi

BTW: We do have on the roadmap an overhaul of the aggreagator. So any
feedback of it is much valuable.
And combined with the copy on write stuff for the exchanges to avoid
the pitfalls of OUT overwriting IN etc.
then it will be better in the future when its implemented.

The IN and OUT stuff has been debated countless on the camel dev forum.
James created James to resemble JBI stuff and thus that is why the
Camel API have this.

And we all agree the lazy creation of getOut is unfortunate and hence
why we added the hasOut.
Changing it to be not lazy would break to much at current time.

Anyway discussing this is a bit "tired" and it should be done on dev forum.

Just wanted to share a bit hints on background.



On Wed, Sep 2, 2009 at 8:02 AM, snowbug<la...@gmail.com> wrote:
>
> Thanks for the explanation, it makes sense, especially for the pipeline
> pattern.
>
> Based on your recommendation, looking into setting the exchange property for
> storing information that I'd like to persist, I encountered some problem. In
> my splitter bean, the split method looks like this (modified for this post
> to make the discussion easier):
>    @Handler
>    public List<MyMessage> split(Exchange exchange) throws Exception {
>        MyMessage msg = (MyMessage) exchange.getIn().getBody();
>        exchange.setProperty("myheader", msg.getHeader());
>
>        List<MyMessage> splitted = new ArrayList<MyMessage>();
>        for (int i=0; i<5; i++) {
>            // create a new message
>            MyMessage part = messageUtil.newMsg(msg);
>            part.getBody().setId(i);
>            splitted.add(part);
>        }
>
>        return splitted;
>    }
>
> What I found is that the property I set "myheader" is not preserved in the
> next endpoint where the splitted method is processed. It seems that the
> splitter used a copy of the exchange when invoking this method, thus any
> header I set to the exchange is lost when the copy is discarded.
>
>
> So any workaround for me to preserve some information? What I can think of
> is to add a bean processing after the previous step to create the "myheader"
> property before hitting split (haven't tried but should work), but I'd like
> to know if there is any easier approach, or if I am doing anything wrong -
> I'm quite new to Camel.
>
> BTW, I think it's shouldn't be rare to have the need to preserve the
> original message during the processing of generating the response. One often
> need to correlate the response with the original message.
> Thanks, Alan
> --
> View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25252082.html
> Sent from the Camel - Users mailing list archive at Nabble.com.
>
>



-- 
Claus Ibsen
Apache Camel Committer

Open Source Integration: http://fusesource.com
Blog: http://davsclaus.blogspot.com/
Twitter: http://twitter.com/davsclaus

Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by snowbug <la...@gmail.com>.
In the splitter, I was setting the exchange property to preserve the data
(see my posted code), but it is not working and I believe it's because the
exchange passed into the splitter is a copy, not the actual. I dumped the
object identity of the exchange objects passed into my splitter and my next
processor and they are different object.

What this mean is that the in the splitter, there is no way to set the
exchange property and preserve it. I think this could be revised to pass in
the original exchange instead of a copy, but of course, I don't know the
reason to use a copy in the first place.


Claus Ibsen-2 wrote:
> 
> Use Exchange properties to preserve data!
> 
> On Wed, Sep 2, 2009 at 8:02 AM, snowbug<la...@gmail.com> wrote:
>>
>> Thanks for the explanation, it makes sense, especially for the pipeline
>> pattern.
>>
>> Based on your recommendation, looking into setting the exchange property
>> for
>> storing information that I'd like to persist, I encountered some problem.
>> In
>> my splitter bean, the split method looks like this (modified for this
>> post
>> to make the discussion easier):
>>    @Handler
>>    public List<MyMessage> split(Exchange exchange) throws Exception {
>>        MyMessage msg = (MyMessage) exchange.getIn().getBody();
>>        exchange.setProperty("myheader", msg.getHeader());
>>
>>        List<MyMessage> splitted = new ArrayList<MyMessage>();
>>        for (int i=0; i<5; i++) {
>>            // create a new message
>>            MyMessage part = messageUtil.newMsg(msg);
>>            part.getBody().setId(i);
>>            splitted.add(part);
>>        }
>>
>>        return splitted;
>>    }
>>
>> What I found is that the property I set "myheader" is not preserved in
>> the
>> next endpoint where the splitted method is processed. It seems that the
>> splitter used a copy of the exchange when invoking this method, thus any
>> header I set to the exchange is lost when the copy is discarded.
>>
>>
>> So any workaround for me to preserve some information? What I can think
>> of
>> is to add a bean processing after the previous step to create the
>> "myheader"
>> property before hitting split (haven't tried but should work), but I'd
>> like
>> to know if there is any easier approach, or if I am doing anything wrong
>> -
>> I'm quite new to Camel.
>>
>> BTW, I think it's shouldn't be rare to have the need to preserve the
>> original message during the processing of generating the response. One
>> often
>> need to correlate the response with the original message.
>> Thanks, Alan
>> --
>> View this message in context:
>> http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25252082.html
>> Sent from the Camel - Users mailing list archive at Nabble.com.
>>
>>
> 
> 
> 
> -- 
> Claus Ibsen
> Apache Camel Committer
> 
> Open Source Integration: http://fusesource.com
> Blog: http://davsclaus.blogspot.com/
> Twitter: http://twitter.com/davsclaus
> 
> 

-- 
View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25261336.html
Sent from the Camel - Users mailing list archive at Nabble.com.


Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by Claus Ibsen <cl...@gmail.com>.
Use Exchange properties to preserve data!

On Wed, Sep 2, 2009 at 8:02 AM, snowbug<la...@gmail.com> wrote:
>
> Thanks for the explanation, it makes sense, especially for the pipeline
> pattern.
>
> Based on your recommendation, looking into setting the exchange property for
> storing information that I'd like to persist, I encountered some problem. In
> my splitter bean, the split method looks like this (modified for this post
> to make the discussion easier):
>    @Handler
>    public List<MyMessage> split(Exchange exchange) throws Exception {
>        MyMessage msg = (MyMessage) exchange.getIn().getBody();
>        exchange.setProperty("myheader", msg.getHeader());
>
>        List<MyMessage> splitted = new ArrayList<MyMessage>();
>        for (int i=0; i<5; i++) {
>            // create a new message
>            MyMessage part = messageUtil.newMsg(msg);
>            part.getBody().setId(i);
>            splitted.add(part);
>        }
>
>        return splitted;
>    }
>
> What I found is that the property I set "myheader" is not preserved in the
> next endpoint where the splitted method is processed. It seems that the
> splitter used a copy of the exchange when invoking this method, thus any
> header I set to the exchange is lost when the copy is discarded.
>
>
> So any workaround for me to preserve some information? What I can think of
> is to add a bean processing after the previous step to create the "myheader"
> property before hitting split (haven't tried but should work), but I'd like
> to know if there is any easier approach, or if I am doing anything wrong -
> I'm quite new to Camel.
>
> BTW, I think it's shouldn't be rare to have the need to preserve the
> original message during the processing of generating the response. One often
> need to correlate the response with the original message.
> Thanks, Alan
> --
> View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25252082.html
> Sent from the Camel - Users mailing list archive at Nabble.com.
>
>



-- 
Claus Ibsen
Apache Camel Committer

Open Source Integration: http://fusesource.com
Blog: http://davsclaus.blogspot.com/
Twitter: http://twitter.com/davsclaus

Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by snowbug <la...@gmail.com>.
Thanks for the explanation, it makes sense, especially for the pipeline
pattern.

Based on your recommendation, looking into setting the exchange property for
storing information that I'd like to persist, I encountered some problem. In
my splitter bean, the split method looks like this (modified for this post
to make the discussion easier):
    @Handler
    public List<MyMessage> split(Exchange exchange) throws Exception {
        MyMessage msg = (MyMessage) exchange.getIn().getBody();
        exchange.setProperty("myheader", msg.getHeader());

        List<MyMessage> splitted = new ArrayList<MyMessage>();
        for (int i=0; i<5; i++) {
            // create a new message 
            MyMessage part = messageUtil.newMsg(msg);
            part.getBody().setId(i);
            splitted.add(part);
        }

        return splitted;
    }

What I found is that the property I set "myheader" is not preserved in the
next endpoint where the splitted method is processed. It seems that the
splitter used a copy of the exchange when invoking this method, thus any
header I set to the exchange is lost when the copy is discarded.


So any workaround for me to preserve some information? What I can think of
is to add a bean processing after the previous step to create the "myheader"
property before hitting split (haven't tried but should work), but I'd like
to know if there is any easier approach, or if I am doing anything wrong -
I'm quite new to Camel.

BTW, I think it's shouldn't be rare to have the need to preserve the
original message during the processing of generating the response. One often
need to correlate the response with the original message.
Thanks, Alan
-- 
View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25252082.html
Sent from the Camel - Users mailing list archive at Nabble.com.


Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by Claus Ibsen <cl...@gmail.com>.
>
> I think it does not make sense because after this operation, I have no way to
> get back my original IN message which might be critical for processing.
>

You can copy you IN message to an exchange property and get it from
there, if its "so critical". The EIP pattern pipes and filters that
Camel uses by the Pipeline will also affect this as it will copy OUT
-> IN and therefore your "original input" may already be "lost"
because of this EIP pattern.
Hence why you need to preserve this yourself!

We do have some experiments with Camel 2.x where we work with a copy
on write approach that would allow us to retrieve original inputs.
But at current time this code is in a sandbox repo.


The reason for the OUT -> IN is that AggregationStrategy is cumbersome
to use for Camel users and they get confused with where their result
message is in either IN or OUT etc. Now it works consistent and your
"result" message is *always* in the IN.

In the future I would like to provide a bean based aggregator that
does not use Exchange objects. And thus is less confusing to use.




On Wed, Sep 2, 2009 at 5:22 AM, snowbug<la...@gmail.com> wrote:
>
> I think it does not make sense because after this operation, I have no way to
> get back my original IN message which might be critical for processing.
>
> Say I have a exchange that I splitted, did some processing on each of the
> splitted exchange (which is in the IN message of the exchange), and set the
> OUT message after each of the processing on the splitted exchange. Now in my
> aggregation, I want to merge the OUT messages based on the content of the
> original IN message. With this implementation, you simply can't do it
> because the you don' t have the original IN message anymore.
>
> I understand you can check hasOut(). But the real problem here is that the
> implementation clears the original IN message and it is a destructive
> operation that can not be reversed!
>
> At least it should provide a way to disable this behavior.
>
> Alan
>
>
>
> willem.jiang wrote:
>>
>> Please use hasOut() to check if the out message is there.
>> As the comments said, the prepareAggregation is make the user
>> aggregation strategy more easy, it just need to check the in message and
>> do not care about the out message.
>>
>> Willem
>>
>> snowbug wrote:
>>> When doing aggregation, this code is executed before the actual
>>> aggregation:
>>>     /**
>>>      * Prepares the exchanges for aggregation.
>>>      * <p/>
>>>      * This implementation will copy the OUT body to the IN body so when
>>> you
>>> do
>>>      * aggregation the body is only in the IN body to avoid confusing end
>>> users.
>>>      *
>>>      * @param oldExchange  the old exchange
>>>      * @param newExchange  the new exchange
>>>      */
>>>     public static void prepareAggregation(Exchange oldExchange, Exchange
>>> newExchange) {
>>>         // copy body/header from OUT to IN
>>>         if (oldExchange != null) {
>>>             if (oldExchange.hasOut()) {
>>>                 oldExchange.getIn().copyFrom(oldExchange.getOut());
>>>                 oldExchange.setOut(null);
>>>             }
>>>         }
>>>
>>>         if (newExchange != null) {
>>>             if (newExchange.hasOut()) {
>>>                 newExchange.getIn().copyFrom(newExchange.getOut());
>>>                 newExchange.setOut(null);
>>>             }
>>>         }
>>>     }
>>>
>>>
>>> I have hard time to understand why the IN is overwritten automatically.
>>> IN
>>> is the message that comes in and should only be overwritten if I choose
>>> to
>>> based on my business logic, not have the framework code to assume this
>>> behavior.
>>>
>>> To make the matter worse, the DefaultExchange.getOut() will automatically
>>> create an empty Message when it is invoked. In other words, if
>>> DefaultExchange.getOut() is called somewhere either in your code or
>>> Camel's
>>> code, the OUT message is automatically created, and the hasOut() method
>>> will
>>> then be true, and this default empty OUT message is then automatically
>>> copied to the IN.
>>>
>>> If there is a compelling reason shows this behavior is absolutely
>>> necessary,
>>> I'd like to create a bug ticket to have it fixed.
>>>
>>> Thanks,
>>
>>
>>
>
> --
> View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25251098.html
> Sent from the Camel - Users mailing list archive at Nabble.com.
>
>



-- 
Claus Ibsen
Apache Camel Committer

Open Source Integration: http://fusesource.com
Blog: http://davsclaus.blogspot.com/
Twitter: http://twitter.com/davsclaus

Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by snowbug <la...@gmail.com>.
I think it does not make sense because after this operation, I have no way to
get back my original IN message which might be critical for processing.

Say I have a exchange that I splitted, did some processing on each of the
splitted exchange (which is in the IN message of the exchange), and set the
OUT message after each of the processing on the splitted exchange. Now in my
aggregation, I want to merge the OUT messages based on the content of the
original IN message. With this implementation, you simply can't do it
because the you don' t have the original IN message anymore. 

I understand you can check hasOut(). But the real problem here is that the
implementation clears the original IN message and it is a destructive
operation that can not be reversed!

At least it should provide a way to disable this behavior.

Alan



willem.jiang wrote:
> 
> Please use hasOut() to check if the out message is there.
> As the comments said, the prepareAggregation is make the user 
> aggregation strategy more easy, it just need to check the in message and 
> do not care about the out message.
> 
> Willem
> 
> snowbug wrote:
>> When doing aggregation, this code is executed before the actual
>> aggregation:
>>     /**
>>      * Prepares the exchanges for aggregation.
>>      * <p/>
>>      * This implementation will copy the OUT body to the IN body so when
>> you
>> do
>>      * aggregation the body is only in the IN body to avoid confusing end
>> users.
>>      *
>>      * @param oldExchange  the old exchange
>>      * @param newExchange  the new exchange
>>      */
>>     public static void prepareAggregation(Exchange oldExchange, Exchange
>> newExchange) {
>>         // copy body/header from OUT to IN
>>         if (oldExchange != null) {
>>             if (oldExchange.hasOut()) {
>>                 oldExchange.getIn().copyFrom(oldExchange.getOut());
>>                 oldExchange.setOut(null);
>>             }
>>         }
>> 
>>         if (newExchange != null) {
>>             if (newExchange.hasOut()) {
>>                 newExchange.getIn().copyFrom(newExchange.getOut());
>>                 newExchange.setOut(null);
>>             }
>>         }
>>     }
>> 
>> 
>> I have hard time to understand why the IN is overwritten automatically.
>> IN
>> is the message that comes in and should only be overwritten if I choose
>> to
>> based on my business logic, not have the framework code to assume this
>> behavior. 
>> 
>> To make the matter worse, the DefaultExchange.getOut() will automatically
>> create an empty Message when it is invoked. In other words, if
>> DefaultExchange.getOut() is called somewhere either in your code or
>> Camel's
>> code, the OUT message is automatically created, and the hasOut() method
>> will
>> then be true, and this default empty OUT message is then automatically
>> copied to the IN. 
>> 
>> If there is a compelling reason shows this behavior is absolutely
>> necessary,
>> I'd like to create a bug ticket to have it fixed.
>> 
>> Thanks,
> 
> 
> 

-- 
View this message in context: http://www.nabble.com/Why-does-ExchangeHelper.prepareAggregation-modify-the-in-body--tp25249162p25251098.html
Sent from the Camel - Users mailing list archive at Nabble.com.


Re: Why does ExchangeHelper.prepareAggregation modify the in body?

Posted by Willem Jiang <wi...@gmail.com>.
Please use hasOut() to check if the out message is there.
As the comments said, the prepareAggregation is make the user 
aggregation strategy more easy, it just need to check the in message and 
do not care about the out message.

Willem

snowbug wrote:
> When doing aggregation, this code is executed before the actual aggregation:
>     /**
>      * Prepares the exchanges for aggregation.
>      * <p/>
>      * This implementation will copy the OUT body to the IN body so when you
> do
>      * aggregation the body is only in the IN body to avoid confusing end
> users.
>      *
>      * @param oldExchange  the old exchange
>      * @param newExchange  the new exchange
>      */
>     public static void prepareAggregation(Exchange oldExchange, Exchange
> newExchange) {
>         // copy body/header from OUT to IN
>         if (oldExchange != null) {
>             if (oldExchange.hasOut()) {
>                 oldExchange.getIn().copyFrom(oldExchange.getOut());
>                 oldExchange.setOut(null);
>             }
>         }
> 
>         if (newExchange != null) {
>             if (newExchange.hasOut()) {
>                 newExchange.getIn().copyFrom(newExchange.getOut());
>                 newExchange.setOut(null);
>             }
>         }
>     }
> 
> 
> I have hard time to understand why the IN is overwritten automatically. IN
> is the message that comes in and should only be overwritten if I choose to
> based on my business logic, not have the framework code to assume this
> behavior. 
> 
> To make the matter worse, the DefaultExchange.getOut() will automatically
> create an empty Message when it is invoked. In other words, if
> DefaultExchange.getOut() is called somewhere either in your code or Camel's
> code, the OUT message is automatically created, and the hasOut() method will
> then be true, and this default empty OUT message is then automatically
> copied to the IN. 
> 
> If there is a compelling reason shows this behavior is absolutely necessary,
> I'd like to create a bug ticket to have it fixed.
> 
> Thanks,