b85411 b85411 - 1 year ago 137
Android Question

ThreeTenABP not parsing date

I am trying to convert ISO 8601 time into something human readable and in the local timezone of the Android device.

String date = "2016-09-24T06:24:01Z";
LocalDate test = LocalDate.parse(date, ISO_INSTANT);

But it returns:

method threw 'org.threeten.bp.format.DateTimeParseException' exception

From reading http://www.threeten.org/threetenbp/apidocs/org/threeten/bp/format/DateTimeFormatter.html#ISO_INSTANT it seems like what I'm doing should be possible.

What am I doing wrong?


Expanded exception error:

Unable to obtain LocalDate from TemporalAccessor: DateTimeBuilder[fields={MilliOfSecond=0, NanoOfSecond=0, InstantSeconds=1474698241, MicroOfSecond=0}, ISO, null, null, null], type org.threeten.bp.format.DateTimeBuilder

Edit 2

The solution is in the answer below. For anyone that stumbles across this, if you want to specify a custom output format you can use:

String format = "MMMM dd, yyyy \'at\' HH:mm a";
String dateString = DateTimeFormatter.ofPattern(format).withZone(ZoneId.systemDefault()).format(instant);

Answer Source

@alex answer is correct. Here is a working example.

Instant represents a point in time. To convert to any other local types you will need timezone.

String date = "2016-09-24T06:24:01Z";

This date string is parsed using the DateTimeFormatter#ISO_INSTANT internally.

Instant instant = Instant.parse(date);

From here you can convert to other local types just using timezone ( defaulting to system time zone )

LocalDateTime localDateTime = instant.atZone(ZoneId.systemDefault()).toLocalDateTime();
LocalDate localDate = instant.atZone(ZoneId.systemDefault()).toLocalDate();
LocalTime localTime = instant.atZone(ZoneId.systemDefault()).toLocalTime();

Alternatively, you can use static method to get to local date time and then to local date and time.

LocalDateTime localDateTime = LocalDateTime.ofInstant(instant, ZoneId.systemDefault());
LocalDate localDate = localDateTime.toLocalDate();
LocalTime localTime = localDateTime.toLocalTime();