Joda-Time
Here's my take on this problem, using Joda-Time 2.3.
Immutable
Generally you should use the immutable versions of the Joda-Time classes. Nearly all the methods return a new instance of a DateTime
rather than modify existing instance. Simplifies things, and makes for automatic thread-safety.
Start-Of-Day
Use the newer method withTimeAtStartOfDay()
rather than setting time of day to zero. Because of Daylight Saving Time (DST) and other anomalies, on some days in some time zones, there is no midnight or 00:00:00 time of day.
Convert: j.u.Date ↔ DateTime
To translate a Joda-Time DateTime
instance to a java.util.Date instance, simply call toDate
method. No need for constructor on Date.
Going the other way, if you hava a java.util.Date and want a Joda-Time DateTime, simply pass the Date to the constructor of DateTime along with the desired DateTimeZone
object.
Example Code
DateTimeZone timeZone = DateTimeZone.forID( "Europe/Paris" );
// Usually better to specify a time zone rather than rely on default.
DateTime now = new DateTime( timeZone ); // Or, for default time zone: new DateTime()
DateTime monthFromNow = now.plusMonths(1);
DateTime firstOfNextMonth = monthFromNow.dayOfMonth().withMinimumValue();
DateTime firstMomentOfFirstOfNextMonth = firstOfNextMonth.withTimeAtStartOfDay();
Or, if you are a maniac, string that all together in a single line of code.
DateTime allInOneLine = new DateTime( DateTimeZone.forID( "Europe/Paris" ) ).plusMonths( 1 ).dayOfMonth().withMinimumValue().withTimeAtStartOfDay();
Translate to an old java.util.Date for interaction with other classes/libraries.
java.util.Date date = firstMomentOfFirstOfNextMonth.toDate();
Dump to console…
System.out.println( "now: " + now );
System.out.println( "monthFromNow: " + monthFromNow );
System.out.println( "firstOfNextMonth: " + firstOfNextMonth );
System.out.println( "firstMomentOfFirstOfNextMonth: " + firstMomentOfFirstOfNextMonth );
System.out.println( "allInOneLine: " + allInOneLine );
System.out.println( "date: " + date );
When run…
now: 2014-01-21T02:46:16.834+01:00
monthFromNow: 2014-02-21T02:46:16.834+01:00
firstOfNextMonth: 2014-02-01T02:46:16.834+01:00
firstMomentOfFirstOfNextMonth: 2014-02-01T00:00:00.000+01:00
allInOneLine: 2014-02-01T00:00:00.000+01:00
date: Fri Jan 31 15:00:00 PST 2014
java.time
The java.time framework built into Java 8 and later supplants the old java.util.Date/.Calendar classes. Inspired by Joda-Time, and intended to be its successor.
These new classes include the TemporalAdjuster
interface (Tutorial) with a bunch of implementations in TemporalAdjusters
(notice the plural s
). Happens to have just the adjuster we need: firstDayOfNextMonth
.
ZoneId zoneId = ZoneId.of ( "America/Montreal" );
LocalDate today = LocalDate.now ( zoneId );
LocalDate firstOfNextMonth = today.with ( TemporalAdjusters.firstDayOfNextMonth () );
Dump to console.
System.out.println ( "today: " + today + " | firstOfNextMonth: " + firstOfNextMonth );
today: 2015-12-22 | firstOfNextMonth: 2016-01-01
If you want a date-time rather than date-only, adjust.
ZonedDateTime zdt = firstOfNextMonth.atStartOfDay( zoneId );
If you need to use the old java.util.Date for operating with old classes not yet updated to java.time, convert from an Instant
extracted from the ZonedDateTime object. An Instant is a moment on the timeline in UTC.
java.util.Date date = java.util.Date.from( zdt.toInstant() );
About java.time
The java.time framework is built into Java 8 and later. These classes supplant the troublesome old legacy date-time classes such as java.util.Date
, Calendar
, & SimpleDateFormat
.
The Joda-Time project, now in maintenance mode, advises migration to the java.time classes.
To learn more, see the Oracle Tutorial. And search Stack Overflow for many examples and explanations. Specification is JSR 310.
You may exchange java.time objects directly with your database. Use a JDBC driver compliant with JDBC 4.2 or later. No need for strings, no need for java.sql.*
classes.
Where to obtain the java.time classes?
The ThreeTen-Extra project extends java.time with additional classes. This project is a proving ground for possible future additions to java.time. You may find some useful classes here such as Interval
, YearWeek
, YearQuarter
, and more.