-->
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.  [ 10 posts ] 
Author Message
 Post subject: why em.persist() immediately inserts data into database?
PostPosted: Thu Jun 24, 2010 10:18 am 
Newbie

Joined: Fri Feb 12, 2010 4:09 pm
Posts: 10
auto commit is off, I checked the hibernate logging.

code is like this:

try{
tx.begin();
em.persist(entity);
tx.commit();
}catch(Exception ex)
{
tx.rollabck();
}

after em.persist() is executed, the data is in my database! tx.commit() seems to be useless here.


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Fri Jun 25, 2010 9:05 am 
Newbie

Joined: Fri Feb 12, 2010 4:09 pm
Posts: 10
anyone can answer this question?


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Fri Jun 25, 2010 9:17 am 
Hibernate Team
Hibernate Team

Joined: Fri Oct 05, 2007 4:47 pm
Posts: 2536
Location: Third rock from the Sun
all managed objects need to have assigned a primary key before it can be added to the persistence context.
I guess you're using a type of primary key which is generated by the database (like mysql autoincrements?) so Hibernate needs to send the INSERT statement to the database in order to have a PK assigned. This doesn't change semantics as of course using the transaction is still needed, as you are still able to rollback the database transaction until the call to commit(); it might be interesting to consider this for performance tuning, but your code should behave the same way.

_________________
Sanne
http://in.relation.to/


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Fri Jun 25, 2010 11:18 am 
Newbie

Joined: Fri Feb 12, 2010 4:09 pm
Posts: 10
s.grinovero wrote:
all managed objects need to have assigned a primary key before it can be added to the persistence context.
I guess you're using a type of primary key which is generated by the database (like mysql autoincrements?) so Hibernate needs to send the INSERT statement to the database in order to have a PK assigned. This doesn't change semantics as of course using the transaction is still needed, as you are still able to rollback the database transaction until the call to commit(); it might be interesting to consider this for performance tuning, but your code should behave the same way.

Thank you so much!
Yes, the primary key is generated by MySQL. Did not realize that could cause me so much trouble especially in terms of performance. I guess that also applies to calling em.merge(): in order to Save or Update an entity what I ended up doing is to find the object by using its unique key and based on whether it can be found or not, call em.persist() or change the loaded entity.
Is there a good practice to solve this kind of problems or should I dump mysql auto-increments ?


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Fri Jun 25, 2010 11:23 am 
Hibernate Team
Hibernate Team

Joined: Fri Oct 05, 2007 4:47 pm
Posts: 2536
Location: Third rock from the Sun
that shouldn't be a huge hit in terms of performance :/
Even if you get the next value of a sequence, you'll have to ask the DB for a value. If your really need to avoid the DB rountrip, use uuid generated values (Hibernate provides several generators), or when possible assign a key yourself.

_________________
Sanne
http://in.relation.to/


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Thu Jul 15, 2010 4:13 pm 
Newbie

Joined: Fri Feb 12, 2010 4:09 pm
Posts: 10
s.grinovero wrote:
all managed objects need to have assigned a primary key before it can be added to the persistence context.
I guess you're using a type of primary key which is generated by the database (like mysql autoincrements?) so Hibernate needs to send the INSERT statement to the database in order to have a PK assigned. This doesn't change semantics as of course using the transaction is still needed, as you are still able to rollback the database transaction until the call to commit(); it might be interesting to consider this for performance tuning, but your code should behave the same way.


I got another problem because of that behavior. When I use em.merge() to save a record. Hibernate always send an insert statement to database first which fails every time because of duplicate unique key.
So in order to save a record, instead of one line em.merge(entity), I have to do something like this:

public void save(MobileAppOwner entity) {
try {
MobileAppOwner existingEntity = this.find(entity.getMobileApp(), entity.getPerson());

existingEntity.setMobileApp(entity.getMobileApp());
existingEntity.setPerson(entity.getPerson());
existingEntity.setStatus(entity.getStatus());
existingEntity.setLastUpdatedTime(entity.getLastUpdatedTime());

em.merge(entity);
} catch (javax.persistence.NoResultException e) {
em.persist(entity);
}

}

What is the best practice to solve this problem? This has been bothering me for months, any help will be greatly appreciated.


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Thu Jul 15, 2010 6:39 pm 
Hibernate Team
Hibernate Team

Joined: Fri Oct 05, 2007 4:47 pm
Posts: 2536
Location: Third rock from the Sun
Quote:
When I use em.merge() to save a record.

Sorry I don't understand; why are you using merge to save a record? it should be used only to update an existing record. To save a new entity use persist.

_________________
Sanne
http://in.relation.to/


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Fri Jul 16, 2010 9:36 am 
Newbie

Joined: Fri Feb 12, 2010 4:09 pm
Posts: 10
s.grinovero wrote:
Quote:
When I use em.merge() to save a record.

Sorry I don't understand; why are you using merge to save a record? it should be used only to update an existing record. To save a new entity use persist.

Hi Sanne :
Thanks for your reply!
This is because in my case, the data I received from the caller does not contain primary key, which is generated by mysql database(MyISAM btw). It dose include unique constrain tough. So in my code I have to take care of either inserting or updating a record.
So say I am using merge only to update a record, in my situation, i.e, primary key generated by MySQL database, what would you recommend to handle the update? Is it possible to just em.merge(entity) to do that? Thanks.


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Fri Jul 16, 2010 9:50 am 
Newbie

Joined: Fri Feb 12, 2010 4:09 pm
Posts: 10
yet another question here:
Since I am using MyISAM store engine, I found transaction rollback method does not really work here. I figured this is because myisam does not support transaction.
I guess I have to simulate rollback by code like this:

//somewhere in code entity1 inserted into db

try {
em.getTransaction().begin();
em.persist(entity2);

em.getTransaction().commit();
} catch (RuntimeException ex) {
logger.error(ex,ex);

// em.getTransaction().rollback();
// do our own rollback
em.delete(entity1);
}

what is your suggestion?


Top
 Profile  
 
 Post subject: Re: why em.persist() immediately inserts data into database?
PostPosted: Sat Jul 17, 2010 4:54 am 
Hibernate Team
Hibernate Team

Joined: Fri Oct 05, 2007 4:47 pm
Posts: 2536
Location: Third rock from the Sun
I'd really suggest you to configure MySQL to use InnoDB, so you have foreign keys and transactions. Why should you be using MyISAM?

_________________
Sanne
http://in.relation.to/


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