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.  [ 6 posts ] 
Author Message
 Post subject: one-to-one and lazy loading - only possible with PK assoc?
PostPosted: Mon Nov 24, 2008 4:51 pm 
Regular
Regular

Joined: Wed Jan 07, 2004 5:16 pm
Posts: 65
Location: CA, USA
Are lazy loaded associations only possible for one-to-one associations that are mapped using the PK approach (verses the unique FK approach?)?

We're currently using 3.0.4 in a system that is in production, so upgrading to a later version is not something we can do instantly.

Are there any one-to-one mapping features in later versions of Hibernate that are more flexible regarding the lazy loading behavior that would prevent eager loading of the other side when using the unique FK mapping approach?

What I've noticed is that with the PK association one-to-one mapping approach you have the constrained="true" option. This approach has lazy loaded associations when queried from either side of the one-to-one.

When using a unique FK mapping for one-to-one however, from what I understand the constrained-"true" option no longer applies, and the 3.0.4 manual clearly says that proxying is not possible for constrained="false" associations, and will always load the association eagerly.

Ideally what I'm looking for is a one-to-one mapping approach that uses unique FK mapping approach for one-to-ones (the database is already in production so this cannot be changed easily to the PK mapping approach), and also has lazy loading of both sides of the association no matter what side you navigate from.

Does such a thing exist? If it doesn't that's ok because it explains the behavior we're seeing (unexpected eager loading of one-to-one associations), but if it does exist then let me know and I'll share the specifics of the mappings so we can find out what we're doing wrong.

Thanks, Kevin



Need help with Hibernate? Read this first:
http://www.hibernate.org/ForumMailingli ... AskForHelp

Hibernate version: 3.0.4

Mapping documents:

Code between sessionFactory.openSession() and session.close():

Full stack trace of any exception that occurs:

Name and version of the database you are using:

The generated SQL (show_sql=true):

Debug level Hibernate log excerpt:


Problems with Session and transaction handling?

Read this: http://hibernate.org/42.html


Top
 Profile  
 
 Post subject:
PostPosted: Mon Nov 24, 2008 6:19 pm 
Expert
Expert

Joined: Wed Mar 03, 2004 6:35 am
Posts: 1240
Location: Lund, Sweden
Quote:
Does such a thing exist? If it doesn't that's ok because it explains the behavior we're seeing (unexpected eager loading of one-to-one associations), but if it does exist then let me know and I'll share the specifics of the mappings so we can find out what we're doing wrong.


No, it is not possible to have the association lazy from both sides. Lazy only works from the side containing the foreign key column. From the other side there is no way to know if the associated object exists or not without querying the database and Hibernate at least needs to know if a proxy should be created or if the association should be null. So, since the database always has to be queried, I guess Hibernate simply loads the entire entity eagerly.

The only workaround I know for this is to map the problematic side as a <set> (or another collection but <set> is the easiest). This will of course affect your API and also query syntax, so this may not be an option considering that your system is in production.


Top
 Profile  
 
 Post subject:
PostPosted: Mon Nov 24, 2008 6:35 pm 
Regular
Regular

Joined: Wed Jan 07, 2004 5:16 pm
Posts: 65
Location: CA, USA
Thanks for the confirmation - this is good to know.

Actually your suggestion of the work around may be exactly what we're looking for (we can do isolated code changes to the production system easier than replacing versions of dependent jars since the regression testing is more isolated). Mapping one side as a Set would allow us to have the lazy loading in both directions, which would eliminate the additional SQL queries that are currently being executed every time we touch one of these objects with the one-to-ones.

Thanks!


Top
 Profile  
 
 Post subject:
PostPosted: Thu Dec 04, 2008 3:28 pm 
Regular
Regular

Joined: Tue Feb 19, 2008 6:05 pm
Posts: 82
I have the same issue but the child is loading eagerly in separate select statements for no reason. What are lazy="no-proxy" and lazy="proxy" for then?

I have a user and user_termination tables with only the user_termination having the user_id as the foreign key and the user may or may not have a user_termination entry!

I defined the userTermination mapping in user as
Code:
<one-to-one name="userTermination" class="UserTermination"
         property-ref="user" lazy="no-proxy">
</one-to-one>


And the userTermination has a user entry as a many-to-one
Code:
<many-to-one name="participant" class="Participant" column="participant_id" unique="true" not-null="false" />


I chose lazy="no-proxy" in my parent however, whenever I write my HQL on parent User table such as

Code:
from User user where user.user_deleted_date_time is null
it fetches all of my user's first in a single select and then follows by a separate select statements of userTermination, obviously whenever they may only exist, although I don't need them to be fetched eagerly unless I do a left join fetch or something!


There is no alternative by avoiding the userTermination entry in user object and write my HQL query as select from user, userTermination where
user.userId = userTermination.userId it looses the user objects as only not all users have userTermination!!

In a normal SQL statement all I have to do is a left join as in
select .. from user, userTermination where user.userId = userTermination.userId(+)

I am not sure if I can write my left join HQL query without having it to be mentioned as a one-to-one object in my parent mapping?



Any suggestions?

Regards
Rama


Top
 Profile  
 
 Post subject:
PostPosted: Thu Dec 04, 2008 6:31 pm 
Expert
Expert

Joined: Wed Mar 03, 2004 6:35 am
Posts: 1240
Location: Lund, Sweden
The lazy="no-proxy" setting is used to enable lazy fetching with out proxies. It might actually be the only way to have the <one-to-one> end not load eagerly.

But it requires byte-code manipulation as described here: http://www.hibernate.org/hib_docs/v3/re ... properties

I have no experience whatsoever with using this so I don't know more than what the docs say about. Try it and reporter your findings!


Top
 Profile  
 
 Post subject: byte code manipulation??
PostPosted: Thu Dec 04, 2008 7:24 pm 
Regular
Regular

Joined: Tue Feb 19, 2008 6:05 pm
Posts: 82
I did see the byte-code manipulation :) from http://www.hibernate.org/hib_docs/refer ... pping.html 5.1.13

Thought that this is a very simple scenario that might have already been addressed, discussed and take care of in Hibernate as it includes performance.

Aren't there any work arounds in the mapping file or writing a left join query without actually mentioning the relationship in the mapping file?

I will try and look up byte-code manipulation and hope it is simple!

Thanks
Rama


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 6 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.