complete support for DateFormat

Project: http://git-wip-us.apache.org/repos/asf/johnzon/repo
Commit: http://git-wip-us.apache.org/repos/asf/johnzon/commit/fb05f282
Tree: http://git-wip-us.apache.org/repos/asf/johnzon/tree/fb05f282
Diff: http://git-wip-us.apache.org/repos/asf/johnzon/diff/fb05f282

Branch: refs/heads/master
Commit: fb05f282c9d0ec0f03426cfe6be1688ff9aa078f
Parents: 8583655
Author: amoscatelli <[email protected]>
Authored: Fri Mar 30 15:59:37 2018 +0200
Committer: amoscatelli <[email protected]>
Committed: Fri Mar 30 15:59:37 2018 +0200

----------------------------------------------------------------------
 .../apache/johnzon/jsonb/JohnzonBuilder.java    | 245 ++++++++++++-------
 .../apache/johnzon/jsonb/JsonbTypesTest.java    | 134 +++++++++-
 2 files changed, 287 insertions(+), 92 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/johnzon/blob/fb05f282/johnzon-jsonb/src/main/java/org/apache/johnzon/jsonb/JohnzonBuilder.java
----------------------------------------------------------------------
diff --git 
a/johnzon-jsonb/src/main/java/org/apache/johnzon/jsonb/JohnzonBuilder.java 
b/johnzon-jsonb/src/main/java/org/apache/johnzon/jsonb/JohnzonBuilder.java
index 1ae554a..3af5efc 100644
--- a/johnzon-jsonb/src/main/java/org/apache/johnzon/jsonb/JohnzonBuilder.java
+++ b/johnzon-jsonb/src/main/java/org/apache/johnzon/jsonb/JohnzonBuilder.java
@@ -90,8 +90,19 @@ import java.util.function.Supplier;
 import java.util.stream.Stream;
 
 import static java.time.format.DateTimeFormatter.ofPattern;
+import static java.time.temporal.ChronoField.DAY_OF_MONTH;
+import static java.time.temporal.ChronoField.HOUR_OF_DAY;
+import static java.time.temporal.ChronoField.MILLI_OF_SECOND;
+import static java.time.temporal.ChronoField.MINUTE_OF_HOUR;
+import static java.time.temporal.ChronoField.MONTH_OF_YEAR;
+import static java.time.temporal.ChronoField.SECOND_OF_MINUTE;
+import static java.time.temporal.ChronoField.YEAR;
+import java.time.temporal.TemporalAccessor;
+import java.time.temporal.TemporalQueries;
 import static java.util.Collections.emptyMap;
+import java.util.Objects;
 import static java.util.Optional.ofNullable;
+import java.util.concurrent.TimeUnit;
 import static javax.json.bind.config.PropertyNamingStrategy.IDENTITY;
 import static javax.json.bind.config.PropertyOrderStrategy.LEXICOGRAPHICAL;
 
@@ -141,52 +152,52 @@ public class JohnzonBuilder implements JsonbBuilder {
         final String orderValue = 
config.getProperty(JsonbConfig.PROPERTY_ORDER_STRATEGY).map(String::valueOf).orElse(LEXICOGRAPHICAL);
         final PropertyVisibilityStrategy visibilityStrategy = 
config.getProperty(JsonbConfig.PROPERTY_VISIBILITY_STRATEGY)
                 .map(PropertyVisibilityStrategy.class::cast).orElse(new 
PropertyVisibilityStrategy() {
-                    private final ConcurrentMap<Class<?>, 
PropertyVisibilityStrategy> strategies = new ConcurrentHashMap<>();
+            private final ConcurrentMap<Class<?>, PropertyVisibilityStrategy> 
strategies = new ConcurrentHashMap<>();
 
-                    @Override
-                    public boolean isVisible(final Field field) {
-                        if (field.getAnnotation(JsonbProperty.class) != null) {
-                            return true;
-                        }
-                        final PropertyVisibilityStrategy strategy = 
strategies.computeIfAbsent(field.getDeclaringClass(), this::visibilityStrategy);
-                        return strategy == this ? 
Modifier.isPublic(field.getModifiers()) : strategy.isVisible(field);
-                    }
+            @Override
+            public boolean isVisible(final Field field) {
+                if (field.getAnnotation(JsonbProperty.class) != null) {
+                    return true;
+                }
+                final PropertyVisibilityStrategy strategy = 
strategies.computeIfAbsent(field.getDeclaringClass(), this::visibilityStrategy);
+                return strategy == this ? 
Modifier.isPublic(field.getModifiers()) : strategy.isVisible(field);
+            }
 
-                    @Override
-                    public boolean isVisible(final Method method) {
-                        final PropertyVisibilityStrategy strategy = 
strategies.computeIfAbsent(method.getDeclaringClass(), 
this::visibilityStrategy);
-                        return strategy == this ? 
Modifier.isPublic(method.getModifiers()) : strategy.isVisible(method);
-                    }
+            @Override
+            public boolean isVisible(final Method method) {
+                final PropertyVisibilityStrategy strategy = 
strategies.computeIfAbsent(method.getDeclaringClass(), 
this::visibilityStrategy);
+                return strategy == this ? 
Modifier.isPublic(method.getModifiers()) : strategy.isVisible(method);
+            }
 
-                    private PropertyVisibilityStrategy 
visibilityStrategy(final Class<?> type) { // can be cached
-                        JsonbVisibility visibility = 
type.getAnnotation(JsonbVisibility.class);
-                        if (visibility != null) {
-                            try {
-                                return visibility.value().newInstance();
-                            } catch (final InstantiationException | 
IllegalAccessException e) {
-                                throw new IllegalArgumentException(e);
-                            }
-                        }
-                        Package p = type.getPackage();
-                        while (p != null) {
-                            visibility = 
p.getAnnotation(JsonbVisibility.class);
-                            if (visibility != null) {
-                                try {
-                                    return visibility.value().newInstance();
-                                } catch (final InstantiationException | 
IllegalAccessException e) {
-                                    throw new IllegalArgumentException(e);
-                                }
-                            }
-                            final String name = p.getName();
-                            final int end = name.lastIndexOf('.');
-                            if (end < 0) {
-                                break;
-                            }
-                            p = Package.getPackage(name.substring(0, end));
+            private PropertyVisibilityStrategy visibilityStrategy(final 
Class<?> type) { // can be cached
+                JsonbVisibility visibility = 
type.getAnnotation(JsonbVisibility.class);
+                if (visibility != null) {
+                    try {
+                        return visibility.value().newInstance();
+                    } catch (final InstantiationException | 
IllegalAccessException e) {
+                        throw new IllegalArgumentException(e);
+                    }
+                }
+                Package p = type.getPackage();
+                while (p != null) {
+                    visibility = p.getAnnotation(JsonbVisibility.class);
+                    if (visibility != null) {
+                        try {
+                            return visibility.value().newInstance();
+                        } catch (final InstantiationException | 
IllegalAccessException e) {
+                            throw new IllegalArgumentException(e);
                         }
-                        return this;
                     }
-                });
+                    final String name = p.getName();
+                    final int end = name.lastIndexOf('.');
+                    if (end < 0) {
+                        break;
+                    }
+                    p = Package.getPackage(name.substring(0, end));
+                }
+                return this;
+            }
+        });
 
         config.getProperty("johnzon.attributeOrder").ifPresent(comp -> 
builder.setAttributeOrder(Comparator.class.cast(comp)));
         config.getProperty("johnzon.enforceQuoteString")
@@ -227,13 +238,13 @@ public class JohnzonBuilder implements JsonbBuilder {
         final AccessMode accessMode = config.getProperty("johnzon.accessMode")
                 .map(this::toAccessMode)
                 .orElseGet(() -> new JsonbAccessMode(
-                        propertyNamingStrategy, orderValue, visibilityStrategy,
-                        
!namingStrategyValue.orElse("").equals(PropertyNamingStrategy.CASE_INSENSITIVE),
-                        defaultConverters,
-                        factory, parserFactoryProvider,
-                        config.getProperty("johnzon.accessModeDelegate")
-                                .map(this::toAccessMode)
-                                .orElseGet(() -> new 
FieldAndMethodAccessMode(true, true, false))));
+                propertyNamingStrategy, orderValue, visibilityStrategy,
+                
!namingStrategyValue.orElse("").equals(PropertyNamingStrategy.CASE_INSENSITIVE),
+                defaultConverters,
+                factory, parserFactoryProvider,
+                config.getProperty("johnzon.accessModeDelegate")
+                        .map(this::toAccessMode)
+                        .orElseGet(() -> new FieldAndMethodAccessMode(true, 
true, false))));
         builder.setAccessMode(accessMode);
 
 
@@ -309,7 +320,7 @@ public class JohnzonBuilder implements JsonbBuilder {
                 final ParameterizedType pt = findPT(s, JsonbSerializer.class);
                 if (pt == null) {
                     throw new IllegalArgumentException(s + " doesn't implement 
JsonbSerializer");
-                }
+                    }
                 final Type[] args = pt.getActualTypeArguments();
                 // TODO: support PT in ObjectConverter (list)
                 if (args.length != 1 || !Class.class.isInstance(args[0])) {
@@ -325,7 +336,7 @@ public class JohnzonBuilder implements JsonbBuilder {
                 final ParameterizedType pt = findPT(d, 
JsonbDeserializer.class);
                 if (pt == null) {
                     throw new IllegalArgumentException(d + " doesn't implement 
JsonbDeserializer");
-                }
+                    }
                 final Type[] args = pt.getActualTypeArguments();
                 if (args.length != 1 || !Class.class.isInstance(args[0])) {
                     throw new IllegalArgumentException("We only support 
deserializer on Class for now");
@@ -619,7 +630,6 @@ public class JohnzonBuilder implements JsonbBuilder {
         }));
         addDateFormatConfigConverters(converters, zoneIDUTC);
 
-
         converters.forEach((k, v) -> builder.addAdapter(k.getFrom(), 
k.getTo(), v));
         return converters;
     }
@@ -630,98 +640,151 @@ public class JohnzonBuilder implements JsonbBuilder {
             final Optional<Locale> locale = 
config.getProperty(JsonbConfig.LOCALE).map(Locale.class::cast);
             final DateTimeFormatter formatter = locale.isPresent() ? 
ofPattern(dateFormat, locale.get()) : ofPattern(dateFormat);
 
-            // Note: we try and fallback in the parsing cause we don't know if 
the date format provided is
-            // for date, datetime, time
-
             converters.put(new AdapterKey(Date.class, String.class), new 
ConverterAdapter<>(new Converter<Date>() {
-                private volatile boolean useFormatter = true;
 
                 @Override
                 public String toString(final Date instance) {
-                    return LocalDateTime.ofInstant(instance.toInstant(), 
zoneIDUTC).toString();
+                    return 
formatter.format(ZonedDateTime.ofInstant(instance.toInstant(), zoneIDUTC));
                 }
 
                 @Override
                 public Date fromString(final String text) {
-                    if (useFormatter) {
-                        try {
-                            return Date.from(LocalDateTime.parse(text, 
formatter).toInstant(ZoneOffset.UTC));
-                        } catch (final DateTimeParseException dpe) {
-                            useFormatter = false;
-                        }
+                    try {
+                        return Date.from(parseZonedDateTime(text, formatter, 
zoneIDUTC).toInstant());
+                    } catch (final DateTimeParseException dpe) {
+                        return 
Date.from(LocalDateTime.parse(text).toInstant(ZoneOffset.UTC));
                     }
-                    return 
Date.from(LocalDateTime.parse(text).toInstant(ZoneOffset.UTC));
                 }
             }));
             converters.put(new AdapterKey(LocalDateTime.class, String.class), 
new ConverterAdapter<>(new Converter<LocalDateTime>() {
-                private volatile boolean useFormatter = true;
 
                 @Override
                 public String toString(final LocalDateTime instance) {
-                    return instance.toString();
+                    return 
formatter.format(ZonedDateTime.ofInstant(instance.toInstant(ZoneOffset.UTC), 
zoneIDUTC));
                 }
 
                 @Override
                 public LocalDateTime fromString(final String text) {
-                    if (useFormatter) {
-                        try {
-                            return LocalDateTime.parse(text, formatter);
-                        } catch (final DateTimeParseException dpe) {
-                            useFormatter = false;
-                        }
+                    try {
+                        return parseZonedDateTime(text, formatter, 
zoneIDUTC).toLocalDateTime();
+                    } catch (final DateTimeParseException dpe) {
+                        return LocalDateTime.parse(text);
                     }
-                    return LocalDateTime.parse(text);
                 }
             }));
             converters.put(new AdapterKey(LocalDate.class, String.class), new 
ConverterAdapter<>(new Converter<LocalDate>() {
-                private volatile boolean useFormatter = true;
 
                 @Override
                 public String toString(final LocalDate instance) {
-                    return instance.toString();
+                    return 
formatter.format(ZonedDateTime.ofInstant(Instant.ofEpochMilli(TimeUnit.DAYS.toMillis(instance.toEpochDay())),
 zoneIDUTC));
                 }
 
                 @Override
                 public LocalDate fromString(final String text) {
-                    if (useFormatter) {
-                        try {
-                            return LocalDate.parse(text, formatter);
-                        } catch (final DateTimeParseException dpe) {
-                            useFormatter = false;
-                        }
+                    try {
+                        return parseZonedDateTime(text, formatter, 
zoneIDUTC).toLocalDate();
+                    } catch (final DateTimeParseException dpe) {
+                        return LocalDate.parse(text);
+                    }
+                }
+            }));
+            converters.put(new AdapterKey(OffsetDateTime.class, String.class), 
new ConverterAdapter<>(new Converter<OffsetDateTime>() {
+
+                @Override
+                public String toString(final OffsetDateTime instance) {
+                    return 
formatter.format(ZonedDateTime.ofInstant(instance.toInstant(), zoneIDUTC));
+                }
+
+                @Override
+                public OffsetDateTime fromString(final String text) {
+                    try {
+                        return parseZonedDateTime(text, formatter, 
zoneIDUTC).toOffsetDateTime();
+                    } catch (final DateTimeParseException dpe) {
+                        return OffsetDateTime.parse(text);
                     }
-                    return LocalDate.parse(text);
                 }
             }));
             converters.put(new AdapterKey(ZonedDateTime.class, String.class), 
new ConverterAdapter<>(new Converter<ZonedDateTime>() {
-                private volatile boolean useFormatter = true;
 
                 @Override
                 public String toString(final ZonedDateTime instance) {
-                    return instance.toString();
+                    return 
formatter.format(ZonedDateTime.ofInstant(instance.toInstant(), zoneIDUTC));
                 }
 
                 @Override
                 public ZonedDateTime fromString(final String text) {
-                    if (useFormatter) {
-                        try {
-                            return ZonedDateTime.parse(text, formatter);
-                        } catch (final DateTimeParseException dpe) {
-                            useFormatter = false;
-                        }
+                    try {
+                        return parseZonedDateTime(text, formatter, zoneIDUTC);
+                    } catch (final DateTimeParseException dpe) {
+                        return ZonedDateTime.parse(text);
                     }
-                    return ZonedDateTime.parse(text);
+                }
+            }));
+            converters.put(new AdapterKey(Calendar.class, String.class), new 
ConverterAdapter<>(new Converter<Calendar>() {
+
+                @Override
+                public String toString(final Calendar instance) {
+                    return 
formatter.format(ZonedDateTime.ofInstant(instance.toInstant(), zoneIDUTC));
+                }
+
+                @Override
+                public Calendar fromString(final String text) {
+                    Calendar instance = Calendar.getInstance();
+                    instance.setTime(Date.from(parseZonedDateTime(text, 
formatter, zoneIDUTC).toInstant()));
+                    return instance;
+                }
+            }));
+            converters.put(new AdapterKey(GregorianCalendar.class, 
String.class), new ConverterAdapter<>(new Converter<GregorianCalendar>() {
+
+                @Override
+                public String toString(final GregorianCalendar instance) {
+                    return 
formatter.format(ZonedDateTime.ofInstant(instance.toInstant(), zoneIDUTC));
+                }
+
+                @Override
+                public GregorianCalendar fromString(final String text) {
+                    Calendar instance = GregorianCalendar.getInstance();
+                    instance.setTime(Date.from(parseZonedDateTime(text, 
formatter, zoneIDUTC).toInstant()));
+                    return GregorianCalendar.class.cast(instance);
+                }
+            }));
+            converters.put(new AdapterKey(Instant.class, String.class), new 
ConverterAdapter<>(new Converter<Instant>() {
+
+                @Override
+                public String toString(final Instant instance) {
+                    return formatter.format(ZonedDateTime.ofInstant(instance, 
zoneIDUTC));
+                }
+
+                @Override
+                public Instant fromString(final String text) {
+                    return parseZonedDateTime(text, formatter, 
zoneIDUTC).toInstant();
                 }
             }));
         });
     }
+    
+    private static ZonedDateTime parseZonedDateTime(final String text, final 
DateTimeFormatter formatter, final ZoneId defaultZone){
+        TemporalAccessor parse = formatter.parse(text);
+        ZoneId zone = parse.query(TemporalQueries.zone());
+        if (Objects.isNull(zone)) {
+            zone = defaultZone;
+        }
+        int year = parse.isSupported(YEAR) ? parse.get(YEAR) : 0;
+        int month = parse.isSupported(MONTH_OF_YEAR) ? 
parse.get(MONTH_OF_YEAR) : 0;
+        int day = parse.isSupported(DAY_OF_MONTH) ? parse.get(DAY_OF_MONTH) : 
0;
+        int hour = parse.isSupported(HOUR_OF_DAY) ? parse.get(HOUR_OF_DAY) : 0;
+        int minute = parse.isSupported(MINUTE_OF_HOUR) ? 
parse.get(MINUTE_OF_HOUR) : 0;
+        int second = parse.isSupported(SECOND_OF_MINUTE) ? 
parse.get(SECOND_OF_MINUTE) : 0;
+        int millisecond = parse.isSupported(MILLI_OF_SECOND) ? 
parse.get(MILLI_OF_SECOND) : 0;
+        return ZonedDateTime.of(year, month, day, hour, minute, second, 
millisecond, zone);
+    }
 
     private static void logIfDeprecatedTimeZone(final String text) {
         /* TODO: get the list, UTC is clearly not deprecated but uses 3 letters
         if (text.length() == 3) { // don't fail but log it
             
Logger.getLogger(JohnzonBuilder.class.getName()).severe("Deprecated timezone: " 
+ text);
         }
-        */
+         */
     }
 
     private Map<String, ?> generatorConfig() {

http://git-wip-us.apache.org/repos/asf/johnzon/blob/fb05f282/johnzon-jsonb/src/test/java/org/apache/johnzon/jsonb/JsonbTypesTest.java
----------------------------------------------------------------------
diff --git 
a/johnzon-jsonb/src/test/java/org/apache/johnzon/jsonb/JsonbTypesTest.java 
b/johnzon-jsonb/src/test/java/org/apache/johnzon/jsonb/JsonbTypesTest.java
index 0f792df..ad5b6d2 100644
--- a/johnzon-jsonb/src/test/java/org/apache/johnzon/jsonb/JsonbTypesTest.java
+++ b/johnzon-jsonb/src/test/java/org/apache/johnzon/jsonb/JsonbTypesTest.java
@@ -36,11 +36,13 @@ import java.time.Period;
 import java.time.ZoneId;
 import java.time.ZoneOffset;
 import java.time.ZonedDateTime;
+import java.time.format.DateTimeFormatter;
 import java.time.temporal.ChronoUnit;
 import java.util.Calendar;
 import java.util.Comparator;
 import java.util.Date;
 import java.util.GregorianCalendar;
+import java.util.Locale;
 import java.util.Objects;
 import java.util.Optional;
 import java.util.OptionalDouble;
@@ -49,6 +51,7 @@ import java.util.OptionalLong;
 import java.util.SimpleTimeZone;
 import java.util.TimeZone;
 import java.util.concurrent.TimeUnit;
+import org.apache.cxf.common.util.StringUtils;
 
 import static org.junit.Assert.assertEquals;
 
@@ -109,8 +112,44 @@ public class JsonbTypesTest {
         assertEquals(expected, jsonb.toJson(types));
     }
 
+    @Test
+    public void readAndWriteWithDateFormats() {
+        
readAndWriteWithDateFormat(DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mm:ss.SSSZ"),
 "yyyy-MM-dd'T'HH:mm:ss.SSSZ");
+        
readAndWriteWithDateFormat(DateTimeFormatter.ofPattern("yyyyMMdd+HHmmssZ"), 
"yyyyMMdd+HHmmssZ");
+        readAndWriteWithDateFormat(DateTimeFormatter.ofPattern("yyyy-MM-dd"), 
"yyyy-MM-dd");
+    }
+    
+    private void readAndWriteWithDateFormat(DateTimeFormatter 
dateTimeFormatter, String dateFormat) {
+        final LocalDate localDate = LocalDate.of(2015, 1, 1);
+        final LocalDateTime localDateTime = LocalDateTime.of(2015, 1, 1, 1, 1);
+        final ZonedDateTime zonedDateTime = ZonedDateTime.of(localDateTime, 
ZoneId.of("UTC"));
+        final String expected = "{" +
+            "\"calendar\":\"" + dateTimeFormatter.format(zonedDateTime) + 
"\"," +
+            "\"date\":\"" + 
dateTimeFormatter.format(ZonedDateTime.ofInstant(localDateTime.toInstant(ZoneOffset.UTC),
 ZoneId.of("UTC"))) + "\"," +
+            "\"gregorianCalendar\":\"" + 
dateTimeFormatter.format(zonedDateTime) + "\"," +
+            "\"instant\":\"" + 
dateTimeFormatter.format(ZonedDateTime.ofInstant(Instant.ofEpochMilli(TimeUnit.DAYS.toMillis(localDate.toEpochDay())),
 ZoneId.of("UTC"))) + "\"," +
+            "\"localDate\":\"" + 
dateTimeFormatter.format(ZonedDateTime.ofInstant(Instant.ofEpochMilli(TimeUnit.DAYS.toMillis(localDate.toEpochDay())),
 ZoneId.of("UTC"))) + "\"," +
+            "\"localDateTime\":\"" + 
dateTimeFormatter.format(ZonedDateTime.ofInstant(localDateTime.toInstant(ZoneOffset.UTC),
 ZoneId.of("UTC"))) + "\"," +
+            "\"offsetDateTime\":\"" + 
dateTimeFormatter.format(ZonedDateTime.ofInstant(OffsetDateTime.of(localDateTime,
 ZoneOffset.UTC).toInstant(), ZoneId.of("UTC"))) + "\"" +
+            "}";
+
+        final Jsonb jsonb = newJsonb(dateFormat);
+        
+        final DateTypes types = jsonb.fromJson(new StringReader(expected), 
DateTypes.class);
+        assertEquals(localDate, types.localDate);
+        assertEquals(expected, jsonb.toJson(types));
+    }
+    
     private static Jsonb newJsonb() {
-        return JsonbProvider.provider().create().withConfig(new 
JsonbConfig().setProperty("johnzon.attributeOrder", new Comparator<String>() {
+        return newJsonb(null);
+    }
+    
+    private static Jsonb newJsonb(String dateFormat) {
+        JsonbConfig jsonbConfig = new JsonbConfig();
+        if (!StringUtils.isEmpty(dateFormat)){
+            jsonbConfig.withDateFormat(dateFormat, Locale.getDefault());
+        }
+        return 
JsonbProvider.provider().create().withConfig(jsonbConfig.setProperty("johnzon.attributeOrder",
 new Comparator<String>() {
             @Override
             public int compare(final String o1, final String o2) {
                 return o1.compareTo(o2);
@@ -339,4 +378,97 @@ public class JsonbTypesTest {
                 period, localDateTime, localDate, offsetDateTime, offsetTime);
         }
     }
+
+    public static class DateTypes {
+        private Date date;
+        private Calendar calendar;
+        private GregorianCalendar gregorianCalendar;
+        private Instant instant;
+        private LocalDateTime localDateTime;
+        private LocalDate localDate;
+        private OffsetDateTime offsetDateTime;
+
+
+        public Date getDate() {
+            return date;
+        }
+
+        public void setDate(Date date) {
+            this.date = date;
+        }
+
+        public Calendar getCalendar() {
+            return calendar;
+        }
+
+        public void setCalendar(Calendar calendar) {
+            this.calendar = calendar;
+        }
+
+        public GregorianCalendar getGregorianCalendar() {
+            return gregorianCalendar;
+        }
+
+        public void setGregorianCalendar(GregorianCalendar gregorianCalendar) {
+            this.gregorianCalendar = gregorianCalendar;
+        }
+
+        public Instant getInstant() {
+            return instant;
+        }
+
+        public void setInstant(Instant instant) {
+            this.instant = instant;
+        }
+
+        public LocalDateTime getLocalDateTime() {
+            return localDateTime;
+        }
+
+        public void setLocalDateTime(LocalDateTime localDateTime) {
+            this.localDateTime = localDateTime;
+        }
+
+        public LocalDate getLocalDate() {
+            return localDate;
+        }
+
+        public void setLocalDate(LocalDate localDate) {
+            this.localDate = localDate;
+        }
+
+        public OffsetDateTime getOffsetDateTime() {
+            return offsetDateTime;
+        }
+
+        public void setOffsetDateTime(OffsetDateTime offsetDateTime) {
+            this.offsetDateTime = offsetDateTime;
+        }
+
+
+        @Override
+        public boolean equals(final Object o) {
+            if (this == o) {
+                return true;
+            }
+            if (o == null || getClass() != o.getClass()) {
+                return false;
+            }
+            final Types types = Types.class.cast(o);
+            return 
+                Objects.equals(date, types.date) &&
+                Objects.equals(calendar, types.calendar) &&
+                Objects.equals(gregorianCalendar, types.gregorianCalendar) &&
+                Objects.equals(instant, types.instant) &&
+                Objects.equals(localDateTime, types.localDateTime) &&
+                Objects.equals(localDate, types.localDate) &&
+                Objects.equals(offsetDateTime, types.offsetDateTime);
+        }
+
+        @Override
+        public int hashCode() {
+            return Objects.hash(
+                date, calendar, gregorianCalendar, instant, localDateTime, 
localDate, offsetDateTime);
+        }
+    }
 }

Reply via email to