javatype-conversionjava-timejava.time.instant

Unable to obtain Instant from TemporalAccessor: 2023-08-31T20:37:49.005832800 of type java.time.LocalDateTime


I am using parmeterised method for Temporal class and passing LocalDateTime to Temporal argument and getting error in Instant.from(Temporal t) method where, t instancof LocalDateTime in my case. Here is program,

public Class DateTimeUtils {
public static <T extends Temporal> T withZone(T datetime, ZoneId zone) {
        ZonedDateTime zdt = Instant.from(datetime).atZone(zone);    //error Unable to obtain Instant from TemporalAccessor for LocalDateTime
        if (datetime instanceof LocalDate)
            return (T) zdt.toLocalDate();
        else if (datetime instanceof LocalTime)
            return (T) zdt.toLocalTime();
        else if (datetime instanceof LocalDateTime)
            return (T) zdt.toLocalDateTime();
        else if (datetime instanceof Instant)
            return (T) zdt.toInstant();
        else
          return datetime;
}
//getting error while calling DateConvertUtils.withZone function through main
   public static void main(String[] args) {
        System.out.println(LocalDateTime.now());
        System.out.println(DateConvertUtils.withZone(LocalDateTime.now(), ZoneId.systemDefault()));
    }
}

Following error is occured while runing this file

Exception in thread "main" java.time.DateTimeException: Unable to obtain Instant from TemporalAccessor: 2023-08-31T20:37:49.005832800 of type java.time.LocalDateTime
    at java.base/java.time.Instant.from(Instant.java:378)
    at javaapplicationpjl.DateConvertUtils.withZone(DateConvertUtils.java:?)
    at javaapplicationpjl.DateConvertUtils.main(DateConvertUtils.java:?)
Caused by: java.time.temporal.UnsupportedTemporalTypeException: Unsupported field: InstantSeconds
    at java.base/java.time.LocalDate.get0(LocalDate.java:708)
    at java.base/java.time.LocalDate.getLong(LocalDate.java:687)
    at java.base/java.time.LocalDateTime.getLong(LocalDateTime.java:720)
    at java.base/java.time.Instant.from(Instant.java:373)
    ... 2 more

Request you to tell me the reason of this error b'coz we should able to get instant from LocalDateTime object and also request you to improvise my function: withZone(..). Purpose of this function is very clear. Thanks in advance.

I am trying to prepare a generic function for getting time library class object with zone specific where input and output type is both and both must be instance of Temporal.

Got **error **while I have tried it when accessing Instant.from(LocalDateTime) method.


Solution

  • ZonedDateTime zdt = Instant.from(datetime).atZone(zone); //error Unable to obtain Instant from TemporalAccessor for LocalDateTime

    This error is because LocalDateTime does not contain information about the offset from UTC Greenwich, which is required to convert it to an Instant. This exception is thrown in Instant.from before it reches atZone. LocalDateTime does implement TemporalAccessor, but but does not support time zone:

    https://docs.oracle.com/javase/8/docs/api/java/time/LocalDateTime.html

    This class does not store or represent a time-zone. Instead, it is a description of the date, as used for birthdays, combined with the local time as seen on a wall clock. It cannot represent an instant on the time-line without additional information such as an offset or time-zone.

    You can convert LocalDateTime to ZonedDateTime using specified ZoneID, and then convert it to Instant:

    public static <T extends Temporal> T withZone(T datetime, ZoneId zone) {
        ZonedDateTime zdt;
        if (datetime instanceof LocalDateTime) {
            zdt = ((LocalDateTime) datetime).atZone(zone);
        else if(datetime instanceof LocalDate) {
            zdt = ((LocalDate) datetime).atStartOfDay(zone);
        } else {
            zdt = Instant.from(datetime).atZone(zone);
        }
        if (datetime instanceof LocalDate)
            return (T) zdt.toLocalDate();
        else if (datetime instanceof LocalTime)
            return (T) zdt.toLocalTime();
        else if (datetime instanceof LocalDateTime)
            return (T) zdt.toLocalDateTime();
        else if (datetime instanceof Instant)
            return (T) zdt.toInstant();
        else
            return datetime;
    }