For as long as Java has been around, java.util.Date and java.util.Calendar have been nuisances. This will hopefully very soon be a thing of the past with the addition of JSR-310, the Date and Time API, to the Java API. At the basis of JSR-310 lies the Joda time library, which has been around for quite some time as a replacement for the standard Date and Calendar classes. However that this API is not without its own peculiarities need not come as a surprise, given the complexity of the human interpretation of time all over the world.

In our current project we have a value in the database that contains a timestamp in the UTC or “Zulu” timezone. This timestamp is fetched from the database using a java.sql.Timestamp instance. Our application however deals with org.joda.time.DateTime instances in the local time zone, which for the Netherlands are either CET (UTC+0100) or CEST (UTC+0200) depending on Daylight Savings Time.

So in a nutshell our problem encompasses converting a UTC java.sql.Timestamp to an org.joda.time.DateTime in the correct time zone, which represents the correct time. Let’s start off with writing a small skeleton JUnit test:

Now we want to convert this timestamp to a DateTime object representing the following string: 2008-03-26T21:13:39.059+01:00. We first try the most simple option we can think of:

This test fails. In order to make the test succeed, we have to expect WRONG_TIME in there. Though according to the JavaDoc of DateTime this should have been a step in the right direction:

Maybe we should first force the time zone to UTC before converting the DateTime to a European time zone. Let’s give that a try:

This test also fails, substituting WRONG_TIME for CORRECT_TIME yields a green bar, but an undesired result, so we should take a different approach. LocalDateTime is a Joda time class which does not take into account any time zone information. May we can convert this to a DateTime in the correct time zone. Let’s write a new test case:

Again, this test fails. We need to expect the WRONG_TIME in there to get a green bar. What seems to do the trick is converting the LocalDateTime to a DateTime in the UTC time zone, and then assigning the correct time zone to that. Lo and behold, the following test case works:

Though this solution works, I think it is not the most optimal solution. Does anyone know of a better solution? If so, please add a comment.