The goal of this method is to take a utc date, convert it to the timezone specified and return the DateTimeValue
object. However we recently found a bug with this method when using it with certain timezones.
private static DateTimeValue toDateTimeValue(Date endDate, TimeZone timeZone) {
Calendar cal = Calendar.getInstance();
cal.setTime(endDate);
cal.setTimeZone(timeZone);
cal.set(Calendar.HOUR_OF_DAY, 23); // move to the end of the day
cal.set(Calendar.MINUTE, 59);
cal.set(Calendar.SECOND, 59);
int year = cal.get(Calendar.YEAR);
int month = cal.get(Calendar.MONTH) + 1;
int day = cal.get(Calendar.DAY_OF_MONTH); //ends up being 3 but should be 4
int hour = cal.get(Calendar.HOUR_OF_DAY);
int minute = cal.get(Calendar.MINUTE);
int second = cal.get(Calendar.SECOND);
return new DateTimeValueImpl(year, month, day, hour, minute, second);
}
Main case illustrating bug:
- endDate value: Mon Oct 03 21:00:00 UTC 2022
- timezone value: Europe/Helsinki +3
In the method above the Day value ends up being the 3rd, but it should be the 4th since Oct 03 21:00:00 in UTC is actually Oct 4th in the Helsinki timezone
I did some further testing with this code in place of that method.
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd hh:mm:ss");
sdf.setTimeZone(TimeZone.getTimeZone("UTC"));
String utcDate = sdf.format(endDate);
System.out.println(utcDate); //2022-10-03 09:00:00
sdf.setTimeZone(timeZone);
String timeZoneDate = sdf.format(endDate);
System.out.println(timeZoneDate); //2022-10-04 12:00:00
So this shows the correct/expected results however this is a string, and I need it as a DateTimeValue
.
Why does java.util.calendar not update the date (the day) when we set the timezone to Helsinki?