Sunday, September 7, 2008

Hibernate Stumbling Block

This is just a quick note to others out there doing a quick mock with hibernate involving an existing database.   I found myself spending an unreasonably long time this weekend troubleshooting something that was supposed to just take a moment.  I was trying to leverage hibernate to do a quick java mapping of objects from a pre-existing database in mysql.  The database contains around 60 tables so I was using the eclipse generation plugins to generate all my classes and mapping files.  It appeared to do a very nice job and I tweaked several of the configuration settings including a reverse engineering config file.   I could not get around a pesky error that seemed to be very difficult to read meaning into. The session factory bean creation repeated to fail due to a ClassCastException for the hibernate StringType!  Ok, this seems basic so what could be wrong here?!?

Exception in thread "main" org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'sessionFactory' defined in file [applicationContext.xml]: Invocation of init method failed; nested exception is java.lang.ClassCastException: org.hibernate.type.StringType

After making every logical tweak to the configuration properties of the generation tool and some other vain attempts at a quick fix I faced the reality that this "quick" prototype attempt would not be all that quick.  I linked the source and got friendly with the debugger to find out what simple thing I was missing here.

After tracking the issue down to the end of the line, I found something that I would assume someone experienced with hibernate would have spotted right away in the initial stack trace.   I have really only used hibernate briefly in about half a dozen prototypes or so and most of my projects involved my creating the mapping files and in most cases the data classes as well.   The following line from the stack trace turned out to be very telling in hindsight.

Caused by: java.lang.ClassCastException: org.hibernate.type.StringType

 at org.hibernate.tuple.PropertyFactory.buildVersionProperty(PropertyFactory.java:84)

A version property is a special properly hibernate uses to track the version of the data in order to be more creative with record locking.  Why would a pre-existing database, not built with hibernate in mind have version properties you might ask?  It wouldn't!   Ah ha.

Digging into the generated mapping files I quickly found a handful of tables where the generator had decided a field looked like and must be a version property.   Most times these were timestamp type fields, but in one case, it was a string field named 'version' which was the one responsible for blowing up my build at the present.

<version name="version" type="string">
  <column name="VERSION" length="20" />
</version>

After some search and replace work on the generated mapping files I had what appeared to be a workable solution.

<property name="version" type="string">
  <column name="VERSION" length="20" />
</property>

Excellent!

Hopefully this little nugget will help some other generated hibernate novice users over a potentially painful hump that can ruin your plans for a quick solution.

As for me, I'm on to the next stack trace.

-mw


1 comments:

Amit Jain said...

I used u r solution and it works for me.

Thanks!!