-->
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.  [ 9 posts ] 
Author Message
 Post subject: Lazy update (update only the "not null" members)
PostPosted: Sat Jun 10, 2006 4:49 pm 
Newbie

Joined: Sat Jun 10, 2006 4:20 pm
Posts: 3
Location: San Francisco
Hibernate version: 3.1.3
Mapping documents: Annotation 3.1.0 Beta10
Name and version of the database you are using: Mysql 5.0 (windows)

Is there a way to update only the "not null" values of an object. I have been looking at "dynamic-update", but this is not really what I need.

I would like hibernate to generate/execute an update statement with only the "not null" properties of an object (completely ignoring the null properties)

My client is sending a partial object (in XML) and I would like to avoid reloading the whole object on the server, but just treat the partial object as the delta to be updated.

Ideally, I would see this as a runtime parameter on the "session.update" method.

Am I missing anything obvious?


Jeremy,


Top
 Profile  
 
 Post subject:
PostPosted: Sun Jun 11, 2006 1:14 pm 
Senior
Senior

Joined: Tue Mar 09, 2004 2:38 pm
Posts: 141
Location: Lowell, MA USA
While it would be a bit more work on you end, you could generate a DML-style update statement to execute your query:

http://www.hibernate.org/hib_docs/v3/re ... tch-direct

This way you can control exactly what fields are updated. You can take this further by looking at the mapping package:

http://www.hibernate.org/hib_docs/v3/ap ... mmary.html

Using the PersistentClass object, you can find all properties which are "not null" and generate an HQL statement from that. A little complicated, yes. But other than that, I can't htink of anything that could update only "not null" fields exclusively. Now if only we could do updates via Criteria :)

Ryan-

_________________
Ryan J. McDonough
http://damnhandy.com

Please remember to rate!


Top
 Profile  
 
 Post subject:
PostPosted: Sun Jun 11, 2006 2:52 pm 
Senior
Senior

Joined: Sun Jun 04, 2006 1:58 am
Posts: 136
You can define you sql with required colums ( not null type in ur case)

http://www.hibernate.org/hib_docs/v3/re ... erysql-cud


Top
 Profile  
 
 Post subject:
PostPosted: Sun Jun 11, 2006 7:29 pm 
Newbie

Joined: Sat Jun 10, 2006 4:20 pm
Posts: 3
Location: San Francisco
scarface wrote:
You can define you sql with required colums ( not null type in ur case)

http://www.hibernate.org/hib_docs/v3/re ... erysql-cud


Thanks, I was hoping to do something once for all my classes. But I will look into custom sql per class if I cannot find a more generic way.

Tx a lot.


Top
 Profile  
 
 Post subject:
PostPosted: Sun Jun 11, 2006 8:27 pm 
Senior
Senior

Joined: Tue Mar 09, 2004 2:38 pm
Posts: 141
Location: Lowell, MA USA
As I mentioned before, you can be a bit more generic by looking at Configuration and getting a hold of a PersistenClass instance. By doing this, you can find all properties which map to columns that are not null. Here's some example code I posted in another thread:

Code:
Configuration cfg = HibernateUtil.getConfiguration();
StringBuffer hqlQuery = new StringBuffer();
PersistentClass pc = cfg.getPersistentClass(SomeEntity.class.getName());
Iterator properties = pc.getPropertyIterator();
while(properties.hasNext()) {
   Property property = (Property) properties.next();
   Iterator columns = property.getColumnIterator();
   while(columns.hasNext()) {
      Column column = (Column) columns.next();
      if(!column.isNullable()) {
         /*
          * Insert your own code to add this property to your HQL query
          */
      }
   }
}

Once you've generated your HQL, or SQL for that matter, you can simply execute an update:
Code:
Session session = HibernateUtil.getCurrentSession();
int updatedEntities = s.createQuery(hqlQuery.toString()).executeUpdate();


While not as elegant as some type of mapping attribute, it will do the trick. It's generally a good idea to generate the query strings at startup to avoid any performance hot of creating a query over & over again.

_________________
Ryan J. McDonough
http://damnhandy.com

Please remember to rate!


Top
 Profile  
 
 Post subject:
PostPosted: Sun Jun 11, 2006 9:10 pm 
Newbie

Joined: Sat Jun 10, 2006 4:20 pm
Posts: 3
Location: San Francisco
Tx Damnhandy,

I was responding to the custom sql solution. I was still trying to understand yours (I am not deeply familiar with the Hibernate "internals" yet). Thanks a lot for the extra help. This is very helpful.

BTW, I was referring to the "java properties" being not null and not the columns. So, in a pure update, I do not really need to check if the column is nullable, but rather if the object instance property has a value.

Anyway, thanks a lot for your help.

Jeremy,


Top
 Profile  
 
 Post subject:
PostPosted: Sun Jun 11, 2006 10:40 pm 
Senior
Senior

Joined: Tue Mar 09, 2004 2:38 pm
Posts: 141
Location: Lowell, MA USA
Just FYI Jeremy, the Column.isNullable() method will return true if the mapping file declares a property's not-null attrubute as true. The PersistentClass represents what is declared in your mapping file, it does not look at the database table. I only bring this approach out as I have to do something very similar before.

Ryan-

_________________
Ryan J. McDonough
http://damnhandy.com

Please remember to rate!


Top
 Profile  
 
 Post subject:
PostPosted: Mon Jun 12, 2006 3:00 pm 
Newbie

Joined: Wed Nov 16, 2005 10:58 am
Posts: 5
You may find it useful to look at the ClassMetaData class as well. It gives you much of the same information as PersistentClass, and doesn't require that you have the Configuration available. You can get access to the field values through ClassMetaData.getPropertyValue(...).


Top
 Profile  
 
 Post subject:
PostPosted: Mon Jun 12, 2006 3:04 pm 
Newbie

Joined: Wed Nov 16, 2005 10:58 am
Posts: 5
I forgot to mention how to get the ClassMetaData. You can get it per class from the session factory, either by .class or by name.
ex. sessionFactory.getClassMetaData(Foo.class) or
sessionFactory.getClassMetaData("package.name.Foo")


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