-->
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.  [ 7 posts ] 
Author Message
 Post subject: Native Query give wrong result when session not flushed.
PostPosted: Sun Feb 19, 2012 5:36 am 
Newbie

Joined: Sun Feb 19, 2012 5:14 am
Posts: 2
Hi .
I am using Hibernate inside user transaction and doing the following acations:
1. session.delete(obj); (not flush after).
2. select with Native Query (session.createSQLQuery(....))

The select action see records that was deleted throw the delete action .(ignoring the delete).
I have two question :
1. Why native query dont see the changes ? (i guess session.get see them).
2. What is flush inside user transaction does ? (is there a good reason why not to flush inside transaction).

thanks in advance .
p.s
I will be happy if some one can explaine the mechanism of native query vs get as well.


Top
 Profile  
 
 Post subject: Re: Native Query give wrong result when session not flushed.
PostPosted: Mon Feb 20, 2012 7:10 am 
Expert
Expert

Joined: Tue Jun 16, 2009 3:36 am
Posts: 990
Quote:
1. Why native query dont see the changes ?


I cannot give you the answer to this question,
but I can tell you that hibernate queries in general (therefore also HQL and Criteria) are not
filtering deleted entity objects from result-set.

Quote:
2. What is flush inside user transaction does ?


With flush the deletion is propagated to the database, so the returned result-set should not contain deleted objets anymore

Quote:
is there a good reason why not to flush inside transaction


There are some reasons against flushing during the transaction:
1. flush may throw exceptions which you otherwise will get only at commit time
Therefore a good code, should encapsulate flushing queries into a try-catch block and handle the exceptions properly
2. flush may create WRITE-LOCKs on the database and these are not released until you commit or rollback the transaction.
During this time-window other users (transaction) may get blocked or run into locktimeout exception due these WRITE-LOCKs
3. Flush actions can be cpu-intensive and slow down your application if they are called often and if your persistent context is big (=many entities and collections loaded)


Top
 Profile  
 
 Post subject: Re: Native Query give wrong result when session not flushed.
PostPosted: Mon Feb 20, 2012 7:24 am 
Newbie

Joined: Wed Feb 15, 2012 11:38 am
Posts: 9
Quote:
1. Why native query dont see the changes ? (i guess session.get see them).

Because the changes that you have made *may* may not have flushed (written) to the database.
See this paragraph: http://docs.jboss.org/hibernate/core/3. ... ns-working


Top
 Profile  
 
 Post subject: Re: Native Query give wrong result when session not flushed.
PostPosted: Mon Feb 20, 2012 9:19 am 
Expert
Expert

Joined: Tue Jun 16, 2009 3:36 am
Posts: 990
Hi justinwalsh,
Quote:
Because the changes that you have made *may* may not have flushed (written) to the database.


I believe that we all including shmuelb,are aware of the fact,
that the query don't returns the deleted objects anymore once we call flush.

I think the real question is following:
why does hibernate query not filter the deleted object from the result set anyway?

This question is eligible, as Hibernate does iterate the result-set anyway before returning it to the user.
Hibernate must iterate throug the result-set (except projections and scalar queries) because it tries to match entity objects of the result-set with the ones already present in the persistent context.
This to guarantee:
1. object identity within the persistent context (see http://docs.jboss.org/hibernate/core/4.0/manual/en-US/html/transactions.html#transactions-basics-identity)
2. simulate repeatable-read isolation behavior
(if entity a was already present in your context (=first level cache) with a.name='beta'
then it will remain 'beta' even if the result-set returns the record relative to instance a with name = 'alpha')

It would therefore be a tittle for Hibernate to do also check the state of the matched entity objects in this context.

So why Hibernate query does return objects in deleted state?

I guess the answer is given by following counter-arguments:

1. A query without flush also don't considers new instances (instances created in current transaction),
so why it should indeed recognize deleted instances?

2. Scalar results and projections would return different results than normal queries:

Quote:
Example:
A aa = session.get(A.class,5);
session.delete(aa);
select count(*) from A; // scalar query, return value = 10
select id from A; // projection query, returns 10 objects
select A.* from A; // entity query, would return only 9 entity objects of type A, because instance aa is in deleted state


Such discordance would surely create further embarrassments


Last edited by pb00067 on Wed Feb 22, 2012 7:40 am, edited 2 times in total.

Top
 Profile  
 
 Post subject: Re: Native Query give wrong result when session not flushed.
PostPosted: Tue Feb 21, 2012 1:05 am 
Newbie

Joined: Tue Feb 21, 2012 12:57 am
Posts: 5
That's great.

_________________
nostale gold


Top
 Profile  
 
 Post subject: Re: Native Query give wrong result when session not flushed.
PostPosted: Tue Feb 21, 2012 8:25 am 
Newbie

Joined: Sun Feb 19, 2012 5:14 am
Posts: 2
Hi.
First thanks for the answers (I allmost entered flush inside the transaction).
So if i summarize one can not expect a correct result on the following flow :
1.Open UserTransaction.
2.Read List of Elemnts via Hql.
3.Delete one Element.
4.Preform Hql (that should consider the remove value).
5. acoording to 4 value do logic.
6. commit transaction.


Top
 Profile  
 
 Post subject: Re: Native Query give wrong result when session not flushed.
PostPosted: Wed Feb 22, 2012 7:07 am 
Expert
Expert

Joined: Tue Jun 16, 2009 3:36 am
Posts: 990
Quote:
So if i summarize one can not expect a correct result on the following flow :
1.Open UserTransaction.
2.Read List of Elemnts via Hql.
3.Delete one Element.
4.Preform Hql (that should consider the remove value).
5. acoording to 4 value do logic.
6. commit transaction.


Your statement above is not fully correct in this form.
Note that the default behavior in hibernate is FlushMode.AUTO,
so if each query does implicit flushing (as it is by default), the results are correct.

Only when excplicitely disabling flushing, you run into the described problem.


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