-->
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.  [ 11 posts ] 
Author Message
 Post subject: Transfering lazy many to many over RMI (Serialization)
PostPosted: Fri Jun 10, 2005 4:47 am 
Newbie

Joined: Thu Jun 09, 2005 10:59 am
Posts: 8
Location: Netherlands
Hello all,

I'm relatively new to Hibernate, but i have already built an application with it. The application works :), but now we want to make an addition to it.

I'll sketch the required situation:
There will be one main server with a database (using Hibernate). This server contains all available data and should always remain that way. On top of that will be multiple local servers located elsewhere. The local servers have the same database structure as the main server. They will need an extract of the data of the main server. After that they will have to remain synchronized. The database is completly lazily loaded. The initial transfer and synchronization is done using RMI.

My question is the following: I can transfer everything succesfully to the local servers, except for the many-to-many relations. This is because they exist only in the Sets of the objects they belong to. The Sets are lazy and are hard to send over RMI. How can i send and save a lazy many to many relation using RMI (Serialization)?

I've tried eager fetching which i think is a step in the right direction. I can actually read the related objects out of the Set on the local server (client) side, but when i save the object (which is the inverse=false side, the side that is in charge of the relation), the many to many relations are not saved! I think it may have something to do with the Proxies, but am not sure of anything anymore. I'm starting to question if it is even possible to do what i want. Can anyone tell me what I am doing wrong?


Top
 Profile  
 
 Post subject:
PostPosted: Mon Jun 13, 2005 3:59 am 
Newbie

Joined: Thu Jun 09, 2005 10:59 am
Posts: 8
Location: Netherlands
If my question is unclear in any way, please tell me. If anyone has any idea on this at all, please tell me.

Can i send a lazy many-to-many over RMI? Why is my filled many-to-many Set not saved? I'm out of ideas.

BTW, my Hibernate version is 2.1.6


Top
 Profile  
 
 Post subject:
PostPosted: Tue Jun 14, 2005 5:10 am 
Newbie

Joined: Thu Jun 09, 2005 10:59 am
Posts: 8
Location: Netherlands
I just discovered something. If i do this:

Code:
                    Role role = (Role) object;

                    //TODO: this works, so something must be wrong with the set. Some broken interceptor or something?
                    System.out.println("Copy rights from RMI'd Role into new Set and putting into RMI'd role");
                   
                    Set rights = new HashSet(role.getRights());
                    role.setRights(rights);


The relation is created in the database. It appears the Set that came over RMI has somehow gotten confused or broken. As i said, when i read the Set, i get the Rights i expect, but when i save it, nothing happens, no many to many relation is saved. How can this be?


Top
 Profile  
 
 Post subject:
PostPosted: Tue Jun 14, 2005 11:03 am 
Beginner
Beginner

Joined: Wed Sep 17, 2003 10:43 am
Posts: 48
Calling Hibernate.initialize(role.getRights()) will initialize the collection.


Top
 Profile  
 
 Post subject:
PostPosted: Thu Jun 16, 2005 5:06 am 
Newbie

Joined: Thu Jun 09, 2005 10:59 am
Posts: 8
Location: Netherlands
Thank you for your reply. I tried to apply your idea, but it didn't work. I get a LazyInitializationException at the client side. The Set (rights) is clearly not initialized. The Hibernate javadocs read:
Code:
public static void initialize(Object proxy)
                       throws HibernateException

    Force initialization of a proxy or persistent collection.

    Note: This only ensures intialization of a proxy object or collection; it is not guaranteed that the elements INSIDE the collection will be initialized/materialized.

    Parameters:
        proxy - a persistable object, proxy, persistent collection or null
    Throws:
        HibernateException - if we can't initialize the proxy at this time, eg. the Session was closed

It appears the function does not guarantee the Set will be retreived from the database after this call. I will continue to use eager fetching.

Meanwhile, i still wonder why the lazy Set (and it's proxy) are corrupted? Why can hibernate not see the Set as i do? If i create a new Set with the copied contents, it works just fine. Why?


Top
 Profile  
 
 Post subject:
PostPosted: Thu Jun 16, 2005 5:11 am 
Beginner
Beginner

Joined: Wed Sep 17, 2003 10:43 am
Posts: 48
You have to initialize the collection *before* transfering with RMI. After transfer the object cannot communicate with the it's hibernate session, as that resides on the data/business tier.


Top
 Profile  
 
 Post subject:
PostPosted: Thu Jun 16, 2005 7:20 am 
Newbie

Joined: Thu Jun 09, 2005 10:59 am
Posts: 8
Location: Netherlands
True, that is what i am doing (sorry for not being clear on that). I retreive the objects from the database on the server side, i try to initialize() the Set and send it over RMI. On the client side, i try to access the Set which results in a LazyInitializationException. When I eagerly fetch the collection, it works fine.

The docs state that it is not guaranteed the Set items will be initialized/materialized, so i guess it failed to do that.


Top
 Profile  
 
 Post subject:
PostPosted: Thu Jun 16, 2005 9:38 am 
Newbie

Joined: Thu Jun 09, 2005 10:59 am
Posts: 8
Location: Netherlands
Correction, my apologies. Hibernate.initialize() appears to work after all. I must have done something wrong on my previous try.

I now retreive my objects normally, after which i Hibernate.initialize the many to many Sets. I send them to the client using RMI. I still have to copy the Set to a new Set on the client, in order for the relation to be created. If i don't copy it, the set is somehow ignored and no relation is created.

The system is now functioning, but i'm not very happy on the solution. Having to copy the Set to a new one (which leaves me with an identical Set, for as far as i can see) is not my idea of a solution. If anyone has any idea on why my original Set is corrupted (or whatever) please tell me.

Again, my apologies for my earlier reply. I was wrong, mbatsis was right.


Top
 Profile  
 
 Post subject:
PostPosted: Fri Jun 17, 2005 4:40 am 
Beginner
Beginner

Joined: Wed Sep 17, 2003 10:43 am
Posts: 48
I dont get it, we've never had to copy a collection for RMI transfer to work. The following EJB method works fine:
Code:

public Collection getFoo(fooId){
   // init session, load foo etc
   Hibernate.initialize(foo.getBars());
   return foo;
}


The object along with it's initialized collection is transfered through RMI and everything works fine.


Top
 Profile  
 
 Post subject:
PostPosted: Fri Jun 17, 2005 5:07 am 
Newbie

Joined: Thu Jun 09, 2005 10:59 am
Posts: 8
Location: Netherlands
But can you save it into the database on the other side? So the client requests an object (with a lazy collection) from the server, the server retrieves it, initializes the object and returns it (over RMI) to the client. The client *saves* the object into it's own database (which is a copy of the database on the server with assigned id's).

I can read the initialized collection with my own code, i can get the objects and print their names. But when i save it to the database, the Set (which i can read myself) is somehow ignored and no many to many relation is created.

Btw: thank you for your help :)


Top
 Profile  
 
 Post subject:
PostPosted: Wed Aug 24, 2005 4:53 am 
Senior
Senior

Joined: Mon Aug 22, 2005 5:45 am
Posts: 146
What if you are on a different jvm, e.g. on a RMI-client?!

We use SessionBeans to access our database over hibernate-session.
Our plan is a solution like this:

in BaseSessionBean:
void initialize(Collection c) {
Hibernate.initialize(c);
(...)
}

in Pojo:
private mySessionBean
Set getContacts() {
sessionBean.initialize(contacts);
return contacts;
}

Is this common practise?
Any easier solution evailable?


mbatsis wrote:
I dont get it, we've never had to copy a collection for RMI transfer to work. The following EJB method works fine:
Code:

public Collection getFoo(fooId){
   // init session, load foo etc
   Hibernate.initialize(foo.getBars());
   return foo;
}


The object along with it's initialized collection is transfered through RMI and everything works fine.


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