javajsonjsonb-api

JSONB applies minus one day on date


I'm trying to serialize a simple object with a date in JSON. For that I'm using the JSONB library from Java EE. I'd rather use a Date object than a simple String as I want the data to be strongly typed.

Unfortunately, as I serialize the object JSON format, it seems to apply minus one day on the date, as if it was using another locale or time zone.

Here's my first try, using the default locale:

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Date;

import javax.json.bind.JsonbBuilder;
import javax.json.bind.annotation.JsonbDateFormat;

public class MyDate {
    
    @JsonbDateFormat("yyyy-MM-dd")
    private Date myDate;

    // Getter + setter
    
    public static void main(String[] args) throws ParseException {
        MyDate myDate = new MyDate();
        myDate.setMyDate(new SimpleDateFormat("yyyy-MM-dd").parse("2021-03-19"));
        System.out.println(JsonbBuilder.create().toJson(myDate));
    }
}

Result is: {"myDate":"2021-03-18"}

Then I did a second version with the locale en-US:

    @JsonbDateFormat(value = "yyyy-MM-dd", locale = "en_US")
    private Date myDate;

    // Getter + setter
    
    public static void main(String[] args) throws ParseException {
        MyDate myDate = new MyDate();
        myDate.setMyDate(new SimpleDateFormat("yyyy-MM-dd", Locale.US).parse("2021-03-19"));
        System.out.println(JsonbBuilder.create().toJson(myDate));
    }

Result: {"myDate":"2021-03-18"}

Then I tried specifying a time and it worked but this is not a solution:

    @JsonbDateFormat(value = "yyyy-MM-dd", locale = "en_US")
    private Date myDate;
    
    // Getter + setter

    public static void main(String[] args) throws ParseException {
        MyDate myDate = new MyDate();
        myDate.setMyDate(new SimpleDateFormat("yyyy-MM-dd HH:MM:SS", Locale.US).parse("2021-03-19 12:00:00"));
        System.out.println(JsonbBuilder.create().toJson(myDate));
    }

Result: {"myDate":"2020-12-19"}

Can you help with this ?


Solution

  • Your issue is that you ignore the timezone when you create the date. If you create a date with timezone information, like:

    new SimpleDateFormat("yyyy-MM-dd ZZZZZ").parse("2021-03-19 +0000");
    

    you will get 2021-03-19. But, I would not use java.util.Date to store a date without time or timezone. It's better to use java.time.LocalDate which is more fitting for your needs. So:

    public class MyDate {
    
        private LocalDate myDate;
    
        // Getter + setter
    
        public static void main(String[] args) {
            MyDate myDate = new MyDate();
            myDate.setMyDate(LocalDate.of(2012, 3, 19));
            System.out.println(JsonbBuilder.create().toJson(myDate));
        }
    
    }
    

    See also: