-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 5 posts ] 
Author Message
 Post subject: Dirty checking for detached objects, and cascading
PostPosted: Wed Apr 14, 2004 5:32 am 
Regular
Regular

Joined: Wed Mar 03, 2004 9:38 am
Posts: 70
Hello,

I'm using an architecture pretty much resembling the application transaction with session-per-request-with-detached-objects as explained at http://www.hibernate.org/168.html.

Now, the problem is that when I give the client an object with associated objects mapped with cascade="all" or cascade="save-update", calling saveOrUpdate() on the object also causes all the associated objects to be written to the database even though they have not changed. So if the client modifies the root of an object tree, there can be *a lot* of updates even though only one object has actually changed. Clearly this is not desirable.

So, how can this problem be solved? Hibernate cannot do an automatic dirty check for detached objects, so some kind of manual intervention is required.

1. Looping through all the associated objects and locking them to the session. LockMode.NONE doesn't seem to do any dirty checking, LockMode.READ works but it causes a SELECT of the object in question, so DB traffic doesn't decrease.

2. Looping through all the associated objects and loading them. I haven't tried this, but this should work, and the objects would be loaded from the cache. However, I would have to do some manual dirty checking between the newly loaded objects and the detached objects and copying changed properties to the new object, right?

3. Manual dirty checking with a non-persistent "boolean dirty" property for every persistent object. I.e. when a persistent property is modified, mark the object as dirty.

3a. When saveOrUpdate, don't use cascade="all" or cascade="save-update", but rather loop through all the associated objects and saveOrUpdate them if they are marked dirty, otherwise do nothing.

3b. Use cascading, have persistent objects implement the LifeCycle interface. Override the OnUpdate() method to VETO the updating if the "dirty" property is false.

3c. Use cascading. Make an interceptor which uses the findDirty() method to check if the object is dirty. A problem with this approach is that I would need an interceptor for every persistent class since findDirty is supposed to return an int[] containing indexes of the dirty properties. Or can I cheat, and just return some bogus int[] array as long as I don't use dynamic-update?

4. Some other approach, what?

I guess I'm not the only one to encounter this problem, so how have other people solved it? Is there any "best practice" way?


Top
 Profile  
 
 Post subject:
PostPosted: Thu Apr 15, 2004 7:07 am 
Hibernate Team
Hibernate Team

Joined: Mon Aug 25, 2003 9:11 pm
Posts: 4592
Location: Switzerland
Don't use cascade="all" if you don't want to cascade all.

_________________
JAVA PERSISTENCE WITH HIBERNATE
http://jpwh.org
Get the book, training, and consulting for your Hibernate team.


Top
 Profile  
 
 Post subject:
PostPosted: Thu Apr 15, 2004 2:44 pm 
Regular
Regular

Joined: Wed Mar 03, 2004 9:38 am
Posts: 70
Uh, my point is that *I want* to cascade. I just want to avoid writing unchanged objects to the DB.

For a typical example, consider say some kind of order entry system, where a user modifies an order. So I would have an Order object containing a Set of OrderItems. If the user changes only Order.shippingAddress, I wouldn't want to UPDATE all the OrderItem objects. On the other hand, if the user modifies say the amount for a particular OrderItem, then only one OrderItem should be UPDATEd, while Order and all the other OrderItem:s will be left unchanged (I mean, the same screen in the application is used for modifying both the order itself as well as the orderitems, and in both cases the same method is called when the user chooses to save).

Anyways, I went with option 3b. as explained in my previous post. So far it seems to work, although I'm not that comfortable with having my domain model depend on Hibernate. Also, having to set the object dirty in all the setter methods for the persistent properties is also somewhat ugly.

Or does somebody have some suggestions for a better design?


Top
 Profile  
 
 Post subject:
PostPosted: Fri Apr 16, 2004 7:14 am 
Hibernate Team
Hibernate Team

Joined: Tue Aug 26, 2003 12:50 pm
Posts: 5130
Location: Melbourne, Australia
Quote:
Or does somebody have some suggestions for a better design?


(1) use select-before-update="true"
(2) try using saveOrUpdateCopy()

though these options will not improve performance.


Top
 Profile  
 
 Post subject: Re: Dirty checking for detached objects, and cascading
PostPosted: Sat Aug 28, 2010 7:32 am 
Newbie

Joined: Sat Aug 28, 2010 7:30 am
Posts: 2
It is possible to implement dirty check for Detached Objects using Hibernate by extending some of its public API. Here is another link to a blog i created -
Check this out - http://www.brimllc.com/2010/08/hibernate-automatic-dirty-check-for-detached-objects/


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 5 posts ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.