>>And all this story is only for Clone ?  Bah?!?!?
Ideally the Clone should be backed up by Merge.

>>How much often you are using Clone ? for what ? Which is the reason to go so
deeper in a persistent-layer to clone an entity ?
I did describe the reason in previous post. But ok, let me do it
again.

Within first session application:
Load list of Customers
Bind it to the grid
Close session.

Lately user decide to edit some of the objects in grid.
Application:
Open new session
Attach selected  Customer object to it
After user has done with editing commits it to db.

Now the most interesting part:

If user decides to cancel the edit -or-
Commit falied due to whatever reason

We need to rollback changes made to object. And the only way to do
that now is to call Refresh().

1. This is another call to db. If db is somewhere far - this means bad
app performance.
2. I can't just pass instance of Customer to any part of the program
where it can be (potentially) edited without some callback which can
tell me that I need to refresh it.
3. Refresh do not mean exact object transaction guarantee as you can
got back in object graph different instances of objects.

If we always edit only the copy of object (ie clone) we can just throw
away session and that's it.

>>Is the Clone a responsibility of the persistent-layer ?
Are we talking about support? :) I can't say that NH "should" be
responsible for that but any decent ORM has this feature support. Why
NH? Well it has all required information to do that properly. It knows
about cascades, components, inverse references, colllections etc.

When you are making a clone of object for editing you always want it
to work along cascades. So for example in Customer -> Order ->
OrderItem <- Product model when you clone customer you will get back:

Customer (clone)
Order (clone) which references back Customer (clone)
OrderItem (clone) which references back Order (clone) which references
Product (original)

We don't need to clone Poduct as it is counter cascade (external to
aggregate being edited) and it won't be edited.

>>Even the CLR does not give you a way to clone an entirely object graph.
You've counter yourself :)
>>Define all your entities as Serializable, manage the serialization attributes 
>>where needed, and use the BinaryFormatter

We can use it but it will clone whatever graph it can reach. Doesn't
work with lazy and will touch whatever it can reach.

On 20 июн, 01:36, Fabio Maulo <[email protected]> wrote:
> I don't think that is a matter of "luck". Perhaps what you should find is
> support.
>
> And all this story is only for Clone ?  Bah?!?!?
>
> How much often you are using Clone ? for what ? Which is the reason to go so
> deeper in a persistent-layer to clone an entity ?
> Is the Clone a responsibility of the persistent-layer ?
> Even the CLR does not give you a way to clone an entirely object graph.
>
> Boh?!?!?
>
> 2009/6/19 Yevhen.Bobrov <[email protected]>
>
>
>
>
>
> > Merge is of no value here. We need a completely new instance with but
> > with values from db and it shoud worlk along cascades.
>
> > Tyler,
>
> > As I understand you're working on desktop app as this kind of problems
> > only show up in desktop apps. Me too.
>
> > NHibernate is perfect for web apps but not so developer friendly for
> > desktop development as I want it to be. The need for Clone and Merge
> > is obvious for desktop apps.
>
> > Take a look how this is works in other ORM frameworks. I'm familiar
> > with TopLink and it's UnitOfWork works in such friendly way. See here
> >http://toplink.waldura.com/javadoc/oracle/toplink/sessions/UnitOfWork...
> > .
>
> > Basically you're registering an original object within UoW and it lend
> > back to you a full clone that you will use for editing. This is of
> > course respect an aggregate boundaries (ie cascades). You can even
> > start nested UoW for some child ojbect inside aggregate and when you
> > commit it it will merge values back to parent UoW. This is very handy
> > for Parent-Child, Ok-Cancel scenario.
>
> > Imagine that you have Customer -> Order -> OrderLine model.
> > You can start edit Customer and then create nested UoW for Order or
> > even OrderLine.
> > When you will create nested UoW for Order it will backreference to
> > clone of Customer (which is a totally proper behavior). Check url
> > above.
>
> > We need this kind of infrastructure support for desktop apps. Some
> > time ago I've created framework to deal with this. It was using a lot
> > of NH internals and than i dsicarded it (well it was hard to be in
> > sync with internal stuff as NH experienced a major refactor over last
> > few years :) and get back to manual cloning.
>
> > Everything there but we just need to use it somehow. For example NH
> > can dehydrate object graph data into 2nd level cache and than back to
> > new instance. If we can somehow use this feature thatt will be cool.
> > We can assemble new instance from data and attach it to session. This
> > is what I'm looking for.
>
> > If we can't get support from NH devs than we're out of luck :( (as all
> > other desktop app devs) and I will be interested to cooperate with you
> > on writing such generic Clone-Merge functionality (I like TopLink's
> > implementation :).
>
> > Cheers.
>
> > On 19 июн, 21:24, Tyler Burd <[email protected]> wrote:
> > > That does look handy; thanks!
>
> > > I've also started following the meta-data to get to the cascade settings,
> > so if I come up with a generic way to handle this I'll post it here in case
> > it's useful to others.
>
> > > From: [email protected] [mailto:[email protected]] On
> > Behalf Of Fabio Maulo
> > > Sent: Friday, June 19, 2009 11:37 AM
> > > To: [email protected]
> > > Subject: [nhusers] Re: deep copy aggregate root
>
> > > Perhaps AutoMapper is useful in your case.
> > > 2009/6/19 Tyler Burd <[email protected]<mailto:[email protected]>>
>
> > > Hiya, Fabio.
>
> > > I'm not annoyed to do it by myself, it's just that when adding properties
> > to a persistent class the development team has to remember to add those
> > properties into all of the places the deep copy occurs as well.  This is
> > pretty error prone and non-obvious.  Serialization doesn't do it, because
> > there are some associations that aren't supposed to get copied (as they
> > aren't part of the aggregate tree).  Here is an example:
>
> > > class UserSettings
>
> > >  -Id
>
> > > -MailingAddress <-set to cascade=all
>
> > >  -Organization <-set to cascade=none
>
> > > var newUserSettings = deepCopy(oldUserSettings);
>
> > > newUserSettings.MailingAddress.City = "Denver";
>
> > > session.Save(newUserSettings);
>
> > > This would result in two separate UserSettings rows in the db, both with
> > unique ids.  It would also result in a completely new MailingAddress row,
> > but NOT a new Organization row.
>
> > > Serialization won't work, because I can only say "serialize or ignore
> > this property".  I can't say "when performing a deep copy, either cascade it
> > to this object or just copy over the reference, depending on the cascade
> > settings".
>
> > > I was simply curious to see if anyone had encountered this issue before
> > and if they had any pointers.  The need seems to pop up pretty often here.
>
> > > From: [email protected]<mailto:[email protected]> [mailto:
> > [email protected]<mailto:[email protected]>] On Behalf Of
> > Fabio Maulo
> > > Sent: Friday, June 19, 2009 10:28 AM
> > > To: [email protected]<mailto:[email protected]>
> > > Subject: [nhusers] Re: deep copy aggregate root
>
> > > 2009/6/19 Yevhen.Bobrov <[email protected]<mailto:
> > [email protected]>>
>
> > > I've tried creating fresh session and using SaveOrUpdateCopy to get
> > > back clone.
> > > But the problem I see now (maybe a bug until someone can prove that
> > > this is by design) that SaveOrUpdateCopy do not create clones of
> > > collections.
>
> > > The method is session.Merge and its behaviour depend on cascade in the
> > mapping.
>
> > > The Merge work with entities so what you will have is each entity merged
> > even if inside a collection.
>
> > > If you want a completely new instance with DB values you should use
> > Refresh (another time refresh work depending on cascade in the mapping).
>
> > > Btw what you should do is a deep copy... annoyed to do it by your self ?
> > well... what we should do ?
>
> > > If you want an easy implementation of DeepCloner it is very easy. Define
> > all your entities as Serializable, manage the serialization attributes where
> > needed, and use the BinaryFormatter.
>
> > > --
> > > Fabio Maulo
>
> > > --
> > > Fabio Maulo
>
> --
> Fabio Maulo
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"nhusers" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to 
[email protected]
For more options, visit this group at 
http://groups.google.com/group/nhusers?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to