-->
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.  [ 4 posts ] 
Author Message
 Post subject: fetch children always, 1 level deep.
PostPosted: Tue Nov 02, 2010 11:48 am 
Newbie

Joined: Tue Nov 02, 2010 11:39 am
Posts: 2
Hi,

Here's my problem:
I have a whole bunch of classes. And whenever i get an object, be it using HQL or session.get(className.class , id), i would like hibernate to also fetch all the children of that object. Only 1 level down though. So if i need the children of the children hibernate will use lazy loading. But if i need the children of my object i just loaded it should allready be present.

(I'm not using mapping files, but annotations)

If I put
@OneToMany(fetch = FetchType.EAGER)
at every @onetomany/ @manytomany/@manytoone attribute i got. Then I think it will go waaay to deep and also get the children of the children of the...

I also don't like this solution because then i would need to change all my List collections into a Set.

I hope there is a property i can change in the hibernate.cfg.xml for this?
Or some kind of annotation that i must add at the top of every class?

Something i could also live with is to add fetch all properties to my query... But that doesn't seem to load the children?
Another thing i've tried is just adding inner join fetch x.collectionName(like: from Festival f Inner join fetch f.zones inner join fetch f.days).
It works with 1 inner join fetch, 2 results in the error cannot simultaneously fetch multiple bags :(
Note that i've used List everywhere, never Set.


With mapping files i've read you can add
lazy="false". Unfortunately i can't seem to find the annotation for this.


Top
 Profile  
 
 Post subject: Re: fetch children always, 1 level deep.
PostPosted: Tue Nov 02, 2010 2:50 pm 
Beginner
Beginner

Joined: Sat Sep 24, 2005 11:04 pm
Posts: 21
Try a Criteria Query with an explicit FetchMode of SELECT for the collections mapped as bags. You should be able to join fetch the other single-valued associations.

Code:
session.createCriteria(Parent.class)
  .setFetchMode("child1", FetchMode.JOIN)
  .setFetchMode("children1", FetchMode.SELECT)
  .setFetchMode("children2", FetchMode.SELECT)
  .uniqueResult();


Hope that helps...


Top
 Profile  
 
 Post subject: Re: fetch children always, 1 level deep.
PostPosted: Wed Nov 03, 2010 9:05 am 
Newbie

Joined: Tue Nov 02, 2010 11:39 am
Posts: 2
FetchMode.SELECT doesn't seem to do anything.
After the query i terminate(commit) the transaction. Followed by a for-loop, looping trough the children resulting in the lazy-instantiation error.

I am now using Hibernate.initialize(..) to load the children.
I created a method which takes the object and uses every get method to initialize whatever is in it.
Code:
private static <T> T initializeChildren(T o) {
        Class c = o.getClass();
        for (Method m : c.getDeclaredMethods()) {
            if (m.getName().startsWith("get")) {
                try {
                    Hibernate.initialize(m.invoke(o, null));
                } catch (IllegalAccessException e) {
                    e.printStackTrace();
                } catch (InvocationTargetException e) {
                    e.printStackTrace();
                }
            }
        }
        return o;
}

It'll also go over the non-association getters, but i suppose that's not too bad. Now all i do is, when getting the object pass it to the method and it returns filled and loaded.


Top
 Profile  
 
 Post subject: Re: fetch children always, 1 level deep.
PostPosted: Wed Nov 03, 2010 9:59 am 
Beginner
Beginner

Joined: Sat Sep 24, 2005 11:04 pm
Posts: 21
Yeah, interestingly enough it appears with regard to FetchMode.SELECT, the Hibernate docs have been incorrect for quite some time now (it looks like it was actually intended to act as a replacement for the deprecated FetchMode.LAZY)...

FetchMode.SELECT: "Fetch eagerly, using a separate select."

is definitely misleading. Seems like that would have been corrected by now.

http://ajava.org/online/hibernate3api/
http://opensource.atlassian.com/project ... se/HHH-980
http://opensource.atlassian.com/project ... e/HHH-1211


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