Search code examples
springspring-boothibernatespring-data

Is there simple way of changing timezone between dto and entities at database?


I write application on Spring Boot with Spring Data(postgresql).

I have the following case. I want to store in database time at UTC timezone, and parse it to/from "America/San-Paulo" timezone in dto.

For example: in controller I get dto with LocalDateTime in America/San-Paulo timezone. And I want to save it in database in UTC timezone.

I can do in when mapping from dto to entity. But maybe there is another simple way like setting some properties of hibernate/spring?


Solution

  • Since Java 8, we have the Date/Time API under java.time!

    (1) Convert the timezone in annotated @PrePersist, @PreUpdate, and @PostLoad methods.

    For example, in annotated @PostLoad, convert from UTC to America/San-Paulo.

    private static ZoneId UTC_ZONE = ZoneId.of("UTC");
    private static ZoneId LOCAL_ZONE = ZoneId.of("America/San_Paulo");
    
    private LocalDateTime dateTime;
    
    @PostLoad
    public void toLocal() {
      dateTime = dateTime.atZone(UTC_ZONE).withZoneSameInstant(LOCAL_ZONE).toLocalDateTime();
    }
    

    (2) Assuming you are using Jackson, you can write a custom serializer/deserializer.

    UPDATE:

    With PostgreSQL, you can use the type timestamp with time zone. By default, if you insert/update the column, it will convert the value to UTC.

    In JPA:

    @Column(columnDefinition = "timestamp with time zone")
    

    UPDATE (22-07-01):

    You could also use an AttributeConverter.