hibernate 4 and joda-time

JavaHibernateJodatime

Java Problem Overview


are they happily married ?

I am using the latest version of hibernate (4) and version 1.3 of joda-time hibernate support, which I also believe to be the current latest release.

Everything seems to be working OK (date columns created as expected) when using annotations :

@Column
@Type(type="org.joda.time.contrib.hibernate.PersistentLocalDate")
private LocalDate myDate; 

Are their any known problems with using these versions together ?

Update Well turns out the columns get created but unable to populate with any data :

Handler processing failed; nested exception is java.lang.AbstractMethodError: org.joda.time.contrib.hibernate.PersistentLocalDateTime.nullSafeSet

They are incompatible, and I should be using usertype. See answer below.

Java Solutions


Solution 1 - Java

A distinct paucity of documentation, means it might be helpful for me to write down the steps required for integration. Make sure your libraries are up to date.

You'll need : [assuming you already have hibernate4]

Latest version of joda-time

<dependency>
    <groupId>joda-time</groupId>
    <artifactId>joda-time</artifactId>
    <version>2.0</version>
</dependency>

and usertype lib

<dependency>
    <groupId>org.jadira.usertype</groupId>
    <artifactId>usertype.core</artifactId>
    <version>3.0.0.CR1</version>
</dependency>

Then use the following in entity classes (doesn't have to be LocalDateTime, could be any of the persisted classes available) :

import org.joda.time.LocalDateTime;

and for column definition:

@Column(name="updated", nullable = false)
@Type(type="org.jadira.usertype.dateandtime.joda.PersistentLocalDateTime")
private LocalDateTime updated;

Solution 2 - Java

I'll add this as a separate answer since it's in my opinion important information for anyone upgrading to Hibernate 4, and in need of migrating to using jadira's persistent temporal types. This page is highly ranked in google search results for hibernate 4 and jodatime, so I'll add it here. (For a separate discussion of this issue, see: https://stackoverflow.com/questions/10075385/joda-time-datetime-incorrectly-stores-in-database)

If you are in a timezone other than UTC, an important piece of configuration is needed in order to get the same behaviour as you would with a joda-time hibernate-support type. The way jadira's temporal types work by default, is through converting all values to the UTC timezone before persisting to the database, and converting back to the system's timezone when loading the values from the database.

I got burned by this after upgrading, when I had a lot of timestamps with my exact timezone in the database (UTC+1 (+2 when summertime)). When loaded after upgrading to Hibernate 4, 1 or 2 hours (depending on whether or not the timestamp was during summer time) was added to the value in the database, which meant that all existing timestamps were presented erroneously. Further, new timestamp values were stored in the database with UTC timezone, leading them to appear correctly in the application, but wrong in the database. All in all, a hot mess of timezones and timestamps.

So, in order to get the same behaviour as with joda-times hibernate-support (the datetime being persisted being of the timezone of the server in question, and the timestamps in the database being the same as what is being loaded into the application), the following properties must be added to the JPA/Hibernate configuration (in my case, hibernate.properties):

jadira.usertype.autoRegisterUserTypes=true
jadira.usertype.databaseZone=jvm
jadira.usertype.javaZone=jvm

This will make sure that the timestamps in the database will be of the same timezone as that of the application, which in turn will be the timezone of the jvm (in most cases the clock of the application server).

Also, from what I understand, the autoRegisterUserTypes-property removes the need for the @Type-annotation for a selection of common types, among them the Jodatime-types DateTime and LocalDate.

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionNimChimpskyView Question on Stackoverflow
Solution 1 - JavaNimChimpskyView Answer on Stackoverflow
Solution 2 - JavaTobbView Answer on Stackoverflow