Использование DateTimeFormatterBuilder в Java 8, в частности optionals
Я пытаюсь перейти от Joda к Java 8's ZonedDateTime
и я бьюсь об стену с DateTimeFormatterBuilder
что я, кажется, не могу обойти.
Я хочу принять любой из этих форматов:
2013-09-20T07:00:33
2013-09-20T07:00:33.123
2013-09-20T07:00:33.123+0000
2013-09-20T07:00:33.123Z
2013-09-20T07:00:33.123Z+0000
2013-09-20T07:00:33+0000
вот мой текущий строитель:
DateTimeFormatter formatter = new DateTimeFormatterBuilder()
.parseCaseInsensitive()
.append(DateTimeFormatter.ISO_LOCAL_DATE_TIME)
.optionalStart()
.appendPattern(".SSS")
.optionalEnd()
.optionalStart()
.appendZoneId()
.optionalEnd()
.optionalStart()
.appendPattern("Z")
.optionalEnd()
.toFormatter();
Я, вероятно, ошибаюсь, но, похоже, это должно соответствовать шаблонам, которые я хочу... правильно?
если бы кто-нибудь мог указать на то, что я, возможно, пропустил, это было бы оценено. Я также не слишком уверен в использовании appendOffset
, так ясность в этом также приветствуется, если это окажется ответом.
Edit:
Text '2013-09-20T07:00:33.061+0000' could not be parsed at index 23
глядя на строителя, это, кажется, соответствует из-за дополнительных этапов?
Edit 2:
увидев совет из первого ответа, я попробовал это:
DateTimeFormatter formatter = new DateTimeFormatterBuilder()
.parseCaseInsensitive()
.append(DateTimeFormatter.ISO_LOCAL_DATE_TIME)
.optionalStart()
.appendPattern(".SSS")
.optionalEnd()
.optionalStart()
.appendZoneOrOffsetId()
.optionalEnd()
.toFormatter()
он продолжает терпеть неудачу на строке выше.
Edit 3:
последние тесты приводят к этому исключение:
java.time.format.DateTimeParseException: Text '2013-09-20T07:00:33.061+0000' could not be parsed at index 23
at java.time.format.DateTimeFormatter.parseResolved0(DateTimeFormatter.java:1947)
at java.time.format.DateTimeFormatter.parse(DateTimeFormatter.java:1849)
at java.time.ZonedDateTime.parse(ZonedDateTime.java:597)
at java.time.ZonedDateTime.parse(ZonedDateTime.java:582)
1 ответов
это может быть причиной того, что +0000
- это не идентификатор зоны, а смещение зоны.
на документация предлагает такой список:
Symbol Meaning Presentation Examples
------ ------- ------------ -------
V time-zone ID zone-id America/Los_Angeles; Z; -08:30
z time-zone name zone-name Pacific Standard Time; PST
O localized zone-offset offset-O GMT+8; GMT+08:00; UTC-08:00;
X zone-offset 'Z' for zero offset-X Z; -08; -0830; -08:30; -083015; -08:30:15;
x zone-offset offset-x +0000; -08; -0830; -08:30; -083015; -08:30:15;
Z zone-offset offset-Z +0000; -0800; -08:00;
вы можете использовать appendOffset("+HHMM", "0000")
(doc) или appendZoneOrOffsetId()
(doc) вместо appendZoneId()
.
таким образом, ваш полный формат может выглядеть следующим образом
DateTimeFormatter formatter = new DateTimeFormatterBuilder()
.parseCaseInsensitive()
.append(DateTimeFormatter.ISO_LOCAL_DATE_TIME)
.optionalStart()
.appendPattern(".SSS")
.optionalEnd()
.optionalStart()
.appendZoneOrOffsetId()
.optionalEnd()
.optionalStart()
.appendOffset("+HHMM", "0000")
.optionalEnd()
.toFormatter();
далее способ создания ZonedDateTime может повлиять, если есть исключение или нет. Поэтому я бы рекомендовал следуя, как это работало без каких-либо исключений.
LocalDateTime time = LocalDateTime.parse("2013-09-20T07:00:33.123+0000", formatter);
ZonedDateTime zonedTime = time.atZone(ZoneId.systemDefault());