-->
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: Fine grained control of what properties load from DB.
PostPosted: Fri Jan 09, 2004 9:54 pm 
Beginner
Beginner

Joined: Wed Nov 19, 2003 10:29 pm
Posts: 27
I have what must be a fairly common problem.

I have a table that has one column in it that I wouldn't normally want to load with the rest of the table, since it's often large. I have maintainability and performance reasons for not wanting to put this other column in a separate table and using a one-to-one association.

There's no ability to mark a particular property in a class as 'lazy', though this would be very helpful.

I thought I would be clever by decomposing my mapping into two different classes that shared a single table, and associating them with a one-to-one.

The problem is, when it tries to load the two objects, hibernate doesn't seem to like having two objects pointing at one table with the same primary key and tries to associate the parent object with ITSELF instead of the 'child' object in the relationship. This throws an IllegalArgumentException on the setter method for this special property.

Is there a better way of doing this without having to decompose my table in two pieces?

Does anyone else thing it might be a good idea to be able to mark any property or component as 'lazy' to prevent hibernate from loading particular properties until they are explicitly called for?

Thank you.


Top
 Profile  
 
 Post subject:
PostPosted: Sat Jan 10, 2004 8:21 am 
Hibernate Team
Hibernate Team

Joined: Tue Sep 09, 2003 2:10 pm
Posts: 3246
Location: Passau, Germany
http://www.hibernate.org/41.html


Top
 Profile  
 
 Post subject: Well...
PostPosted: Sat Jan 10, 2004 4:49 pm 
Beginner
Beginner

Joined: Wed Nov 19, 2003 10:29 pm
Posts: 27
Honestly, this seems like a poor work-around.
In order to load the 'full' version of my object, I first need to explicitly evict the light-weight one? Is this due to the same reason I can't have a relational link to the same row in the same table?

That document also states: Note that arguably Hibernate does not really need lazy property fetching, since the query language supports projection, allowing the Java code to fetch exactly the needed properties.

That might be true, but by using scalar queries, you lose all the benefits of working with persistent classes. You have to access your properties by array indexes. Heck, you can't even make changes to the object!

Or does this mean something else than I think it does when it says it 'supports projection'? Can someone clarify?

I wonder if there's a way to trick Hibernate into allowing me to load both objects in at the same time. So long as I don't allow the two copies to become unsynchronized (or only ever make changes to one copy) I can't see the harm in this.


Top
 Profile  
 
 Post subject:
PostPosted: Sat Jan 10, 2004 10:09 pm 
Hibernate Team
Hibernate Team

Joined: Tue Aug 26, 2003 12:50 pm
Posts: 5130
Location: Melbourne, Australia
Quote:
In order to load the 'full' version of my object, I first need to explicitly evict the light-weight one?


Correct, there are really good reasons for this if you think through the implications of having two diff in-memory objects representing the same database row.

Quote:
You have to access your properties by array indexes.


Not true. "select new Foo(...)" etc....

Quote:
Heck, you can't even make changes to the object!


Correct. Hence "arguably".

Quote:
I wonder if there's a way to trick Hibernate into allowing me to load both objects in at the same time.


No way. It is easy for you to call evict() and be explicit. This is simply not at all difficult.


Top
 Profile  
 
 Post subject:
PostPosted: Mon Jan 12, 2004 7:48 pm 
Beginner
Beginner

Joined: Wed Nov 19, 2003 10:29 pm
Posts: 27
Quote:
No way. It is easy for you to call evict() and be explicit. This is simply not at all difficult.


While this is easy, it's also an extra call to the database. To make it worse, both calls to the database query unnecessary properties. Instead of one database call loading one column from the database, you have one database call loading all columns from the database (evict and load with 'heavy' class) then another database call to load all columns but one from the database (evict and reload 'light' class). I cannot leave the object as a heavyweight object because my original class has implicitly polymorphic subclasses and I'd get a cast exception if I left it like that.

I suppose for now the best idea is simply to decompose the table into two.

Support for 'lazy' properties would allow me to simply mark a property as lazy and forget about it. I hear it's on a list for possible future features. I suppose another option would be a 'smart' explicit polymorphic casting mechanism which would allow you to do something as follows:

HeavyObject heavy = (HeavyObject) session.explicitCast(light, HeavyObject.class)

This might explicitly evict the lightweight object and only load the properties that HeavyObject has. One could then cast it back to the lightweight object (this should require no database calls) to make the 'heavy' properties eligible for GC.

Etc etc...

I still think it would be better to have 'lazy' properties, though. Is this feature actually planned? Or is it just an item on a wish-list?


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.