-->
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.  [ 15 posts ] 
Author Message
 Post subject: Hibernate FetchType.LAZY problem
PostPosted: Sun Feb 17, 2008 12:43 pm 
Newbie

Joined: Sat May 12, 2007 3:10 am
Posts: 8
Hi,

I'm having a problem using FetchType.LAZY on hibernate 3.x where it does not call the database every time I want to use a OneToMany collection...

Here is an example:

class MyRoutine
{
...
@OneToMany
private List<MyRoutineStep> steps;

...

}

When I update a step, and call getSteps() on MyRoutine it retrieves the data lazily as it is supposed to. However when I update it again and then call getSteps it returns the old data and refuses to return the current data unless I reload the whole context...

I have noticed that during refreshes the database is not used...

Any ideas?


Top
 Profile  
 
 Post subject: Re: Hibernate FetchType.LAZY problem
PostPosted: Sun Feb 17, 2008 2:52 pm 
Expert
Expert

Joined: Wed Apr 11, 2007 11:39 am
Posts: 735
Location: Montreal, QC
How is the second update done?


Farzad-


Top
 Profile  
 
 Post subject: Re: Hibernate FetchType.LAZY problem
PostPosted: Mon Feb 18, 2008 1:11 am 
Newbie

Joined: Sat May 12, 2007 3:10 am
Posts: 8
farzad wrote:
How is the second update done?


Farzad-


There is no second update... Basically I update an entity, let's say I change some text, then save my object back to the database. I then run a query to retrieve an object with the onetomany relationship with the object I just saved.

When I run getSteps on that object it returns what seams to be a cached PersistentBag of step objects, rather than fetching them from the database...


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 18, 2008 3:36 am 
Expert
Expert

Joined: Thu Jul 05, 2007 9:38 am
Posts: 287
Is the second select in a different session? Make sure the transaction of that session startet after the commit of the first session/transaction

_________________
Please rate useful posts.


Schauderhaft: Softwaredevelopment, Projectmanagement, Qualitymanagement and all things "schauderhaft"


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 18, 2008 6:47 am 
Newbie

Joined: Sat May 12, 2007 3:10 am
Posts: 8
schauder wrote:
Is the second select in a different session? Make sure the transaction of that session startet after the commit of the first session/transaction


To be honest, I thought it would all be in the same session. If I save the routine object (basically that has the relationship) and refresh the page I'm displaying it on, it updates.

Code:
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
      <property name="dataSource" ref="dataSource" />
      <property name="jpaVendorAdapter">
         <bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
            <property name="database" value="POSTGRESQL" />
            <property name="showSql" value="true" />
            <property name="generateDdl" value="true"/>
            <property name="databasePlatform" value="org.hibernate.dialect.PostgreSQLDialect"/>
         </bean>
      </property>
      <property name="jpaProperties">
         <props>
            <prop key="hibernate.cache.use_query_cache">false</prop>
         </props>
      </property>
   </bean>


Now I am saving the step through my admin interface, when I refresh the routine (routine being the object containing a list of steps) it shows happily (although I'm not doing anything to the routine object, but rather using DWR to retrieve steps, so that the page doesn't refresh).

All DAO's are application beans, which means that they should all be in the same hibernate session?

The problem is when I run: getSteps() it uses a cache and does not call the database, unless it is the first time it runs. The only way I've worked around it, is by manually querying the database and returning a list of steps based on the routine currently being displayed on the page.

As far as I am concerned, hibernate should query the database every time I run myroutine.getSteps(); as it is pointless if it will only reflect the changes when I reload the whole context and it runs it's query for the first and only time...

So in point form:

1. In admin using the same DAO beans, I modify the text of a step and save.
2. I can see the changes in the database and in the list of steps as it's retrieved using javascript and dwr (and not getSteps()) on the routine.
3. When I go to the publicly available page and view said routine, the method getSteps() does not even call the database, but returns a PersistentBag from the first time it was run, rather than actually call the database for updates.

Is there a way to force it to use the database every time I run getSteps()?


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 18, 2008 2:18 pm 
Expert
Expert

Joined: Thu Jul 05, 2007 9:38 am
Posts: 287
I think you have two options:

Either implement getSteps using some kind of query instead of a mapped multivalue attribute.

Or (and I'd recommend that) reload your object in a new Session().

It makes perfectly sense for Hibernate to use the values it retrieved the very first time.
a) this way it guaranties consistency. Even the simplest loop over your steps can become very difficult when everytime you call getSteps() it would possibly return a different result.

b) It would be a performance nightmare.

Jens

_________________
Please rate useful posts.


Schauderhaft: Softwaredevelopment, Projectmanagement, Qualitymanagement and all things "schauderhaft"


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 18, 2008 3:00 pm 
Newbie

Joined: Sat May 12, 2007 3:10 am
Posts: 8
schauder wrote:
I think you have two options:

Either implement getSteps using some kind of query instead of a mapped multivalue attribute.

Or (and I'd recommend that) reload your object in a new Session().

It makes perfectly sense for Hibernate to use the values it retrieved the very first time.
a) this way it guaranties consistency. Even the simplest loop over your steps can become very difficult when everytime you call getSteps() it would possibly return a different result.

b) It would be a performance nightmare.

Jens


I can understand the performance gains, although in theory if you are worried about performance you would actually switch the cache on. This is what is baffling me, I don't want a cache for what I'm doing, and have had to work around it...

However if you are using the same session in theory it should update the step object and it should then easily reflect the changes in getSteps as the object is persistent...

Oh well, I guess I have a work around for now anyhow.


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 18, 2008 3:03 pm 
Newbie

Joined: Sat May 12, 2007 3:10 am
Posts: 8
the_thunderbird wrote:
schauder wrote:
I think you have two options:

Either implement getSteps using some kind of query instead of a mapped multivalue attribute.

Or (and I'd recommend that) reload your object in a new Session().

It makes perfectly sense for Hibernate to use the values it retrieved the very first time.
a) this way it guaranties consistency. Even the simplest loop over your steps can become very difficult when everytime you call getSteps() it would possibly return a different result.

b) It would be a performance nightmare.

Jens


I can understand the performance gains, although in theory if you are worried about performance you would actually switch the cache on. This is what is baffling me, I don't want a cache for what I'm doing, and have had to work around it...

However if you are using the same session in theory it should update the step object and it should then easily reflect the changes in getSteps as the object is persistent...

Oh well, I guess I have a work around for now anyhow.


Actually thinking about it... You're right...

getSteps should only use the values it retrieved the first time round, if I'm calling it from an object already fetched from the database. However it should not use those results if I actually query for a new copy of the object which contains getSteps, as the way it works now is making it inconsistent...

I can update the routine and see the changes on the page immediately, but if I update a step even the modified routine still returns an old PersistentBag from when getSteps was first called on a totally different object in the java sense.


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 18, 2008 3:04 pm 
Newbie

Joined: Sat May 12, 2007 3:10 am
Posts: 8
the_thunderbird wrote:
schauder wrote:
I think you have two options:

Either implement getSteps using some kind of query instead of a mapped multivalue attribute.

Or (and I'd recommend that) reload your object in a new Session().

It makes perfectly sense for Hibernate to use the values it retrieved the very first time.
a) this way it guaranties consistency. Even the simplest loop over your steps can become very difficult when everytime you call getSteps() it would possibly return a different result.

b) It would be a performance nightmare.

Jens


I can understand the performance gains, although in theory if you are worried about performance you would actually switch the cache on. This is what is baffling me, I don't want a cache for what I'm doing, and have had to work around it...

However if you are using the same session in theory it should update the step object and it should then easily reflect the changes in getSteps as the object is persistent...

Oh well, I guess I have a work around for now anyhow.


Actually thinking about it... You're right...

getSteps should only use the values it retrieved the first time round, if I'm calling it from an object already fetched from the database. However it should not use those results if I actually query for a new copy of the object which contains getSteps, as the way it works now is making it inconsistent...

I can update the routine and see the changes on the page immediately, but if I update a step even the modified routine still returns an old PersistentBag from when getSteps was first called on a totally different object in the java sense.


Top
 Profile  
 
 Post subject:
PostPosted: Mon Feb 18, 2008 3:04 pm 
Newbie

Joined: Sat May 12, 2007 3:10 am
Posts: 8
schauder wrote:
I think you have two options:

Either implement getSteps using some kind of query instead of a mapped multivalue attribute.

Or (and I'd recommend that) reload your object in a new Session().

It makes perfectly sense for Hibernate to use the values it retrieved the very first time.
a) this way it guaranties consistency. Even the simplest loop over your steps can become very difficult when everytime you call getSteps() it would possibly return a different result.

b) It would be a performance nightmare.

Jens



I can understand the performance gains, although in theory if you are worried about performance you would actually switch the cache on. This is what is baffling me, I don't want a cache for what I'm doing, and have had to work around it...

However if you are using the same session in theory it should update the step object and it should then easily reflect the changes in getSteps as the object is persistent...

Oh well, I guess I have a work around for now anyhow.[/quote]

Actually thinking about it... You're right...

getSteps should only use the values it retrieved the first time round, if I'm calling it from an object already fetched from the database. However it should not use those results if I actually query for a new copy of the object which contains getSteps, as the way it works now is making it inconsistent...

I can update the routine and see the changes on the page immediately, but if I update a step even the modified routine still returns an old PersistentBag from when getSteps was first called on a totally different object in the java sense.


Top
 Profile  
 
 Post subject:
PostPosted: Tue Feb 19, 2008 3:42 am 
Expert
Expert

Joined: Thu Jul 05, 2007 9:38 am
Posts: 287
the_thunderbird wrote:
I don't want a cache for what I'm doing


Well the session by definition is a cache, so if you don't want cached objects, close the session and open a new one

_________________
Please rate useful posts.


Schauderhaft: Softwaredevelopment, Projectmanagement, Qualitymanagement and all things "schauderhaft"


Top
 Profile  
 
 Post subject:
PostPosted: Tue Feb 19, 2008 7:00 am 
Newbie

Joined: Sat May 12, 2007 3:10 am
Posts: 8
schauder wrote:
the_thunderbird wrote:
I don't want a cache for what I'm doing


Well the session by definition is a cache, so if you don't want cached objects, close the session and open a new one


Surely though a single session would update the changes I make to the object (which should be reflected in getSteps())?


Top
 Profile  
 
 Post subject:
PostPosted: Tue Feb 19, 2008 9:03 am 
Newbie

Joined: Thu Nov 29, 2007 4:11 am
Posts: 2
The same problem as yours, gotta work it out

_________________
http://www.love-vs-hate.com/ - tupac
http://www.mybestcity.com/ - amaru
http://www.newbabyassistant.com/ - shakur


Top
 Profile  
 
 Post subject:
PostPosted: Wed Feb 20, 2008 1:38 pm 
Expert
Expert

Joined: Thu Jul 05, 2007 9:38 am
Posts: 287
the_thunderbird wrote:
Surely though a single session would update the changes I make to the object (which should be reflected in getSteps())?


Actually: no. Hibernate doesn't update your objects.

Say you have a class A containing a collection of Bs.

you now delete one of Bs (b) by calling session.delete(b);

The collection in A will still contain the b probably causing problems sooner or later.

Of course if A has a simple attribute 'name' and you call setName("someName"); and persist/update it your object reflects the current state of affairs.

Back to the problem at hand: I don't really understand what you are doing (to many Steps involved :).

Can you please show some code what you are actually doing?

_________________
Please rate useful posts.


Schauderhaft: Softwaredevelopment, Projectmanagement, Qualitymanagement and all things "schauderhaft"


Top
 Profile  
 
 Post subject:
PostPosted: Wed Feb 20, 2008 8:23 pm 
Newbie

Joined: Wed Apr 12, 2006 7:02 am
Posts: 7
Location: Southampton, UK
the_thunderbird wrote:
schauder wrote:
I

Is there a way to force it to use the database every time I run getSteps()?


You could just call Session.refresh(myRoutine) to force the data to be re-read from the database? Or use Session.evict(step) for all the steps you don't want to be cached in the session?


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