Ranides Atterwim 11 months ago
parent
commit
65d01edc31

+ 40 - 166
assira.commons/src/main/java/net/ranides/assira/time2/DateTimeFormatters.java

@@ -1,189 +1,63 @@
 package net.ranides.assira.time2;
 
-import lombok.experimental.UtilityClass;
-import net.ranides.assira.text.StringUtils;
 import org.jetbrains.annotations.Contract;
 import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 
+import java.time.ZoneId;
 import java.time.ZonedDateTime;
 import java.time.format.DateTimeFormatter;
-import java.time.format.TextStyle;
 import java.util.Locale;
 import java.util.Objects;
 
-@UtilityClass
-public class DateTimeFormatters {
-
-    public static final Locale LOCALE_PL = Locale.forLanguageTag("PL");
-
-    public static final String ISO_ZONED_PATTERN           = "yyyy-MM-dd'T'HH:mm:ss.SSSX";
-
-    public static final DateTimeFormatter ISO_ZONED        = DateTimeFormatter.ofPattern(ISO_ZONED_PATTERN);
-    public static final DateTimeFormatter COMPRESSED       = DateTimeFormatter.ofPattern("yyyy-MM-dd HHmmss");
-    public static final DateTimeFormatter DATE             = DateTimeFormatter.ofPattern("yyyy-MM-dd");
-    public static final DateTimeFormatter DATETIME         = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm");
-    public static final DateTimeFormatter DATETIME_PRECISE = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
-    public static final DateTimeFormatter TIME             = DateTimeFormatter.ofPattern("HH:mm");
-    public static final DateTimeFormatter TIME_PRECISE     = DateTimeFormatter.ofPattern("HH:mm:ss");
-    public static final DateTimeFormatter YEAR             = DateTimeFormatter.ofPattern("yyyy");
-    public static final DateTimeFormatter DATENAME         = DateTimeFormatter.ofPattern("dd.MM EE");
-    public static final DateTimeFormatter DAY_NAME         = DateTimeFormatter.ofPattern("EEEE");
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatUtc(@Nullable ZonedDateTime input) {
-        return format(ISO_ZONED, DateTimeUtils.withZoneUtc(input));
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatIso(@Nullable ZonedDateTime input) {
-        return format(ISO_ZONED, input);
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatCompressed(@Nullable ZonedDateTime input) {
-        return format(COMPRESSED, input);
-    }
 
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatUtcDate(@Nullable ZonedDateTime input) {
-        return formatDate(DateTimeUtils.withZoneUtc(input));
-    }
+public class DateTimeFormatters {
 
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatPolishDate(@Nullable ZonedDate input) {
+    private static final ZoneId ZONE_PL  = DateTimeUtils.ZONE_PL;
+    private static final ZoneId ZONE_UTC = DateTimeUtils.ZONE_UTC;
+
+    private static final Locale LOCALE_PL = Locale.forLanguageTag("PL");
+    private static final Locale LOCALE_EN = Locale.forLanguageTag("EN");
+
+    public static final String ISO            = "yyyy-MM-dd'T'HH:mm:ss.SSSX";
+    public static final String COMPRESSED     = "yyyy-MM-dd HHmmss";
+    public static final String DATE           = "yyyy-MM-dd";
+    public static final String DATETIME_SHORT = "yyyy-MM-dd HH:mm";
+    public static final String DATETIME_LONG  = "yyyy-MM-dd HH:mm:ss";
+    public static final String TIME_SHORT     = "HH:mm";
+    public static final String TIME_LONG      = "HH:mm:ss";
+    public static final String YEAR           = "yyyy";
+    public static final String DATE_WEEKDAY   = "dd.MM EE";
+    public static final String WEEKDAY        = "EEEE";
+
+    private static final DateTimeFormatter FMT_ISO            = DateTimeFormatter.ofPattern(ISO);
+    private static final DateTimeFormatter FMT_COMPRESSED     = DateTimeFormatter.ofPattern(COMPRESSED);
+    private static final DateTimeFormatter FMT_DATE           = DateTimeFormatter.ofPattern(DATE);
+    private static final DateTimeFormatter FMT_DATETIME_SHORT = DateTimeFormatter.ofPattern(DATETIME_SHORT);
+    private static final DateTimeFormatter FMT_DATETIME_LONG  = DateTimeFormatter.ofPattern(DATETIME_LONG);
+    private static final DateTimeFormatter FMT_TIME_SHORT     = DateTimeFormatter.ofPattern(TIME_SHORT);
+    private static final DateTimeFormatter FMT_TIME_LONG      = DateTimeFormatter.ofPattern(TIME_LONG);
+    private static final DateTimeFormatter FMT_YEAR           = DateTimeFormatter.ofPattern(YEAR);
+    private static final DateTimeFormatter FMT_DATE_WEEKDAY   = DateTimeFormatter.ofPattern(DATE_WEEKDAY);
+    private static final DateTimeFormatter FMT_WEEKDAY        = DateTimeFormatter.ofPattern(WEEKDAY);
+
+
+    @Contract("_,_,_,!null -> !null; _,_,_,null -> null")
+    private static @Nullable String format(@NotNull DateTimeFormatter format, @NotNull Locale locale, @NotNull ZoneId zone, @Nullable ZonedDate input) {
         if(Objects.isNull(input)) {
             return null;
         }
-        return formatPolishDate(input.withMin());
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatPolishDate(@Nullable ZonedDateTime input) {
-        return formatDate(DateTimeUtils.withZonePolish(input));
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatDate(@Nullable ZonedDateTime input) {
-        return format(DATE, input);
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatDateTime(@Nullable ZonedDateTime input) {
-        return format(DATETIME, input);
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatPolishDateTime(@Nullable ZonedDateTime input) {
-        return format(DATETIME, DateTimeUtils.withZonePolish(input));
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatDateTimePrecise(@Nullable ZonedDateTime input) {
-        return format(DATETIME_PRECISE, input);
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatPolishDateTimePrecise(@Nullable ZonedDateTime input) {
-        return format(DATETIME_PRECISE, DateTimeUtils.withZonePolish(input));
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatTime(@Nullable ZonedDateTime input) {
-        return format(TIME, input);
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatUtcTime(@Nullable ZonedDateTime input) {
-        return formatTime(DateTimeUtils.withZoneUtc(input));
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatPolishTime(@Nullable ZonedDateTime input) {
-        return formatTime(DateTimeUtils.withZonePolish(input));
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatTimePrecise(@Nullable ZonedDateTime input) {
-        return format(TIME_PRECISE, input);
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatYear(@Nullable ZonedDateTime input) {
-        return format(YEAR, input);
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatPolishYear(@Nullable ZonedDateTime input) {
-        return format(YEAR, DateTimeUtils.withZonePolish(input));
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatDateShort(@Nullable ZonedDateTime input) {
-        return format(DATENAME, input);
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatUtcDateShort(@Nullable ZonedDateTime input) {
-        return format(DATENAME, LOCALE_PL, DateTimeUtils.withZoneUtc(input));
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String formatPolishDateShort(@Nullable ZonedDateTime input) {
-        return format(DATENAME, LOCALE_PL, input);
-    }
-
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String getDayName(@Nullable ZonedDateTime input) {
-        return format(DAY_NAME, input);
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String getPolishDayName(@Nullable ZonedDateTime input) {
-        return format(DAY_NAME, LOCALE_PL, input);
+        if(!input.isSameZone(zone)) {
+            throw new UnsupportedOperationException();
+        }
+        return format.withLocale(locale).format(input.withZero());
     }
 
-    @ZoneExplicit
-    @Contract("_,!null -> !null; _,null -> null")
-    public static @Nullable String getPolishMonthName(@NotNull Locale locale, @Nullable ZonedDateTime input) {
+    @Contract("_,_,_,!null -> !null; _,_,_,null -> null")
+    private static @Nullable String format(@NotNull DateTimeFormatter format, @NotNull Locale locale, @NotNull ZoneId zone, @Nullable ZonedDateTime input) {
         if(Objects.isNull(input)) {
             return null;
         }
-        return StringUtils.capitalize(input.getMonth().getDisplayName(TextStyle.FULL_STANDALONE, locale));
-    }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String getPolishMonthName(@Nullable ZonedDateTime input) {
-        return getPolishMonthName(LOCALE_PL, input);
+        return format.withLocale(locale).withZone(zone).format(input);
     }
-
-    @ZoneExplicit
-    @Contract("!null -> !null; null -> null")
-    public static @Nullable String getPolishTime(@Nullable ZonedDateTime input) {
-        return format(TIME, DateTimeUtils.withZonePolish(input));
-    }
-
-    @Contract("_,!null -> !null; _,null -> null")
-    public static @Nullable String format(@NotNull DateTimeFormatter format, @Nullable ZonedDateTime input) {
-        return input == null ? null : format.format(input);
-    }
-
-    @Contract("_,_,!null -> !null; _,_,null -> null")
-    public static @Nullable String format(@NotNull DateTimeFormatter format, @NotNull Locale locale, @Nullable ZonedDateTime input) {
-        return input == null ? null : format.withLocale(locale).format(input);
-    }
-
 }

+ 218 - 0
assira.commons/src/main/java/net/ranides/assira/time2/DateTimeFormatters1.java

@@ -0,0 +1,218 @@
+package net.ranides.assira.time2;
+
+import lombok.experimental.UtilityClass;
+import net.ranides.assira.text.StringUtils;
+import org.jetbrains.annotations.Contract;
+import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
+
+import java.time.ZoneId;
+import java.time.ZonedDateTime;
+import java.time.format.DateTimeFormatter;
+import java.time.format.TextStyle;
+import java.util.Locale;
+import java.util.Objects;
+
+import static net.ranides.assira.time2.DateTimeUtils.ZONE_PL;
+import static net.ranides.assira.time2.DateTimeUtils.ZONE_UTC;
+
+@UtilityClass
+public class DateTimeFormatters1 {
+
+    public static final Locale LOCALE_PL = Locale.forLanguageTag("PL");
+
+    public static final String ISO_ZONED_PATTERN           = "yyyy-MM-dd'T'HH:mm:ss.SSSX";
+
+    public static final DateTimeFormatter ISO_ZONED        = DateTimeFormatter.ofPattern(ISO_ZONED_PATTERN);
+    public static final DateTimeFormatter COMPRESSED       = DateTimeFormatter.ofPattern("yyyy-MM-dd HHmmss");
+    public static final DateTimeFormatter DATE             = DateTimeFormatter.ofPattern("yyyy-MM-dd");
+    public static final DateTimeFormatter DATETIME         = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm");
+    public static final DateTimeFormatter DATETIME_PRECISE = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
+    public static final DateTimeFormatter TIME             = DateTimeFormatter.ofPattern("HH:mm");
+    public static final DateTimeFormatter TIME_PRECISE     = DateTimeFormatter.ofPattern("HH:mm:ss");
+    public static final DateTimeFormatter YEAR             = DateTimeFormatter.ofPattern("yyyy");
+    public static final DateTimeFormatter DATENAME         = DateTimeFormatter.ofPattern("dd.MM EE");
+    public static final DateTimeFormatter DAY_NAME         = DateTimeFormatter.ofPattern("EEEE");
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatUtc(@Nullable ZonedDateTime input) {
+        return format(ISO_ZONED, LOCALE_PL, ZONE_UTC, input);
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatIso(@Nullable ZonedDateTime input) {
+        return format(ISO_ZONED, LOCALE_PL, ZONE_UTC, input);
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatUtcCompressed(@Nullable ZonedDateTime input) {
+        return format(COMPRESSED, LOCALE_PL, ZONE_UTC, input);
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishCompressed(@Nullable ZonedDateTime input) {
+        return format(COMPRESSED, LOCALE_PL, ZONE_PL, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatUtcDate(@Nullable ZonedDateTime input) {
+        return format(DATE, LOCALE_PL, ZONE_UTC, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatUtcDate(@Nullable ZonedDate input) {
+        return format(DATE, LOCALE_PL, ZONE_UTC, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishDate(@Nullable ZonedDateTime input) {
+        return format(DATE, LOCALE_PL, ZONE_PL, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishDate(@Nullable ZonedDate input) {
+        return format(DATE, LOCALE_PL, ZONE_PL, input);
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatUtcDateHoursMinutesSeconds(@Nullable ZonedDateTime input) {
+        return format(DATETIME_PRECISE, LOCALE_PL, ZONE_UTC, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishDateHoursMinutes(@Nullable ZonedDateTime input) {
+        return format(DATETIME, LOCALE_PL, ZONE_PL, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishDateHoursMinutesSeconds(@Nullable ZonedDateTime input) {
+        return format(DATETIME_PRECISE, LOCALE_PL, ZONE_PL, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatUtcTimeShort(@Nullable ZonedDateTime input) {
+        return format(TIME, LOCALE_PL, ZONE_UTC, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatUtcTimeShort(@Nullable ZonedTime input) {
+        return format(TIME, LOCALE_PL, ZONE_UTC, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishTimeShort(@Nullable ZonedDateTime input) {
+        return format(TIME, LOCALE_PL, ZONE_PL, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishTimeShort(@Nullable ZonedTime input) {
+        return format(TIME, LOCALE_PL, ZONE_PL, input);
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatTimePrecise(@Nullable ZonedDateTime input) {
+        return format(TIME_PRECISE, input);
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatYear(@Nullable ZonedDateTime input) {
+        return format(YEAR, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishYear(@Nullable ZonedDateTime input) {
+        return format(YEAR, DateTimeUtils.withZonePolish(input));
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatDateShort(@Nullable ZonedDateTime input) {
+        return format(DATENAME, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatUtcDateShort(@Nullable ZonedDateTime input) {
+        return format(DATENAME, LOCALE_PL, DateTimeUtils.withZoneUtc(input));
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String formatPolishDateShort(@Nullable ZonedDateTime input) {
+        return format(DATENAME, LOCALE_PL, input);
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String getDayName(@Nullable ZonedDateTime input) {
+        return format(DAY_NAME, input);
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String getPolishDayName(@Nullable ZonedDateTime input) {
+        return format(DAY_NAME, LOCALE_PL, input);
+    }
+
+    @ZoneExplicit
+    @Contract("_,!null -> !null; _,null -> null")
+    public static @Nullable String getPolishMonthName(@NotNull Locale locale, @Nullable ZonedDateTime input) {
+        if(Objects.isNull(input)) {
+            return null;
+        }
+        return StringUtils.capitalize(input.getMonth().getDisplayName(TextStyle.FULL_STANDALONE, locale));
+    }
+
+    @ZoneExplicit
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String getPolishMonthName(@Nullable ZonedDateTime input) {
+        return getPolishMonthName(LOCALE_PL, input);
+    }
+
+    @Contract("!null -> !null; null -> null")
+    public static @Nullable String getPolishTime(@Nullable ZonedDateTime input) {
+        return format(TIME, DateTimeUtils.withZonePolish(input));
+    }
+
+    @Contract("_,_,_,!null -> !null; _,_,_,null -> null")
+    private static @Nullable String format(@NotNull DateTimeFormatter format, @NotNull Locale locale, @Nullable ZoneId zone, @Nullable ZonedDate input) {
+        if(Objects.isNull(input)) {
+            return null;
+        }
+        if(Objects.nonNull(zone) && !input.isSameZone(zone)) {
+            throw new UnsupportedOperationException();
+        }
+        return format.withLocale(locale).format(input.withZero());
+    }
+
+    @Contract("_,_,_,!null -> !null; _,_,_,null -> null")
+    private static @Nullable String format(@NotNull DateTimeFormatter format, @NotNull Locale locale, @Nullable ZoneId zone, @Nullable ZonedTime input) {
+        if(Objects.isNull(input)) {
+            return null;
+        }
+        if(Objects.nonNull(zone) && !input.isSameZone(zone)) {
+            throw new UnsupportedOperationException();
+        }
+
+        return format.withLocale(locale).format(input.withDate(ZonedDate.ofEpochSecond(input.getZone(), 0L)));
+    }
+
+    @Contract("_,_,_,!null -> !null; _,_,_,null -> null")
+    private static @Nullable String format(@NotNull DateTimeFormatter format, @NotNull Locale locale, @Nullable ZoneId zone, @Nullable ZonedDateTime input) {
+        if(Objects.isNull(input)) {
+            return null;
+        }
+        return format.withLocale(locale).withZone(zone).format(input);
+    }
+
+}

+ 60 - 207
assira.commons/src/main/java/net/ranides/assira/time2/ZonedDate.java

@@ -2,7 +2,6 @@ package net.ranides.assira.time2;
 
 import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
 import com.fasterxml.jackson.databind.annotation.JsonSerialize;
-import lombok.RequiredArgsConstructor;
 import net.ranides.assira.time2.json.ZonedDateDeserializer;
 import net.ranides.assira.time2.json.ZonedDateSerializer;
 import org.jetbrains.annotations.Contract;
@@ -11,7 +10,6 @@ import org.jetbrains.annotations.Nullable;
 
 import java.sql.Timestamp;
 import java.time.*;
-import java.time.format.DateTimeFormatter;
 import java.time.temporal.ChronoField;
 import java.time.temporal.ChronoUnit;
 import java.time.temporal.TemporalField;
@@ -20,50 +18,61 @@ import java.util.Objects;
 
 @JsonDeserialize(using = ZonedDateDeserializer.class)
 @JsonSerialize(using = ZonedDateSerializer.class)
-public abstract class ZonedDate implements Comparable<ZonedDate> {
+public class ZonedDate implements Comparable<ZonedDate> {
 
-    private static final boolean ALLOW_ZONE_CONVERSION = true;
+    private final ZoneId zone;
+
+    private final LocalDate date;
+
+    private ZonedDate(ZoneId zone, LocalDate date) {
+        this.zone = zone;
+        this.date = date;
+    }
 
     @Contract("null -> null; !null -> !null")
     public static @Nullable ZonedDate of(@Nullable ZonedDateTime input) {
         if(Objects.isNull(input)) {
             return null;
         }
-        return new Complete(input);
+        return new ZonedDate(input.getZone(), input.toLocalDate());
     }
 
     @ZoneExplicit
     public static @NotNull ZonedDate of(@NotNull ZoneId zone, @NotNull LocalDate date) {
-        return new Incomplete(zone, date);
+        return new ZonedDate(zone, date);
     }
 
     @Contract("null -> null; !null -> !null")
     public static @Nullable ZonedDate of(@Nullable Timestamp source) {
-        if(Objects.isNull(source)) {
-            return null;
-        }
         return of(ZoneId.systemDefault(), source);
     }
 
-    @ZoneExplicit
     @Deprecated
-    public static ZonedDate of(@NotNull ZoneId zone, @NotNull Timestamp source) {
-        return new Incomplete(zone, source.toLocalDateTime().atZone(zone).toLocalDate());
+    @ZoneExplicit
+    @Contract("_,null -> null; _,!null -> !null")
+    public static @Nullable ZonedDate of(@NotNull ZoneId zone, @Nullable Timestamp source) {
+        if(Objects.isNull(source)) {
+            return null;
+        }
+        return new ZonedDate(zone, source.toLocalDateTime().atZone(zone).toLocalDate());
     }
 
     @ZoneExplicit
     public static @NotNull ZonedDate ofEpochSecond(@NotNull ZoneId zone, long epoch) {
-        LocalDate date = Instant.ofEpochSecond(epoch).atZone(zone).toLocalDate();
-        return of(zone, date);
+        return of(zone, Instant.ofEpochSecond(epoch).atZone(zone).toLocalDate());
     }
 
     public static @NotNull ZonedDate now() {
-        return new Complete(ZonedDateTime.now());
+        return of(ZonedDateTime.now());
     }
 
-    public abstract ZoneId getZone();
+    public ZoneId getZone() {
+        return zone;
+    }
 
-    public abstract long toEpochDay();
+    public long toEpochDay() {
+        return date.toEpochDay();
+    }
 
     public final boolean isAfter(ZonedDate other) {
         return withMin().isAfter(other.withMin());
@@ -103,50 +112,31 @@ public abstract class ZonedDate implements Comparable<ZonedDate> {
 
     // @todo nullabity
 
-    public abstract boolean isZoneConvertible(@NotNull ZoneId zone);
-
-    public abstract ZonedDate with(TemporalField field, long amount);
-
-    public ZonedDate withYear(int value) {
-        return with(ChronoField.YEAR, value);
+    public ZonedDate with(TemporalField field, long amount) {
+        if(!field.isDateBased()) {
+            throw new IllegalArgumentException();
+        }
+        return new ZonedDate(zone, date.with(field, amount));
     }
 
-    public ZonedDate withMonth(int value) {
-        return with(ChronoField.MONTH_OF_YEAR, value);
+    public ZonedDate withYear(int amount) {
+        return with(ChronoField.YEAR, amount);
     }
 
-    public ZonedDate withDay(int value) {
-        return with(ChronoField.DAY_OF_MONTH, value);
+    public ZonedDate withMonth(int amount) {
+        return with(ChronoField.MONTH_OF_YEAR, amount);
     }
 
-
-    @ZoneExplicit
-    @ZoneHazard
-    public abstract ZonedDate withZone(ZoneId zone);
-
-    @ZoneExplicit
-    @ZoneHazard
-    public final ZonedDate withZoneUtc() {
-        return withZone(DateTimeUtils.ZONE_UTC);
-    }
-
-    @ZoneExplicit
-    @ZoneHazard
-    public final ZonedDate withZonePolish() {
-        return withZone(DateTimeUtils.ZONE_PL);
+    public ZonedDate withDay(int amount) {
+        return with(ChronoField.DAY_OF_MONTH, amount);
     }
 
     @ZoneHazard
     public final ZonedDateTime withTime(ZonedTime time) {
-        if(!isSameZone(time.getZone()) && !isZoneConvertible(time.getZone())) {
+        if(!isSameZone(time.getZone())) {
             throw new UnsupportedOperationException();
         }
-        return withZero()
-                .withZoneSameInstant(time.getZone())
-                .plusHours(time.getHour())
-                .plusMinutes(time.getMinute())
-                .plusSeconds(time.getSecond())
-                .plusNanos(time.getNano());
+        return ZonedDateTime.of(date, LocalTime.ofNanoOfDay(time.toNanoOfDay()), zone);
     }
 
     @ZoneHazard
@@ -154,14 +144,18 @@ public abstract class ZonedDate implements Comparable<ZonedDate> {
         return withTime(ZonedTime.of(time));
     }
 
-    public abstract ZonedDateTime withMin();
+    public ZonedDateTime withMin() {
+        return ZonedDateTime.of(date, LocalTime.MIN, getZone());
+    }
+
+    public ZonedDateTime withMax() {
+        return ZonedDateTime.of(date, LocalTime.MAX, getZone());
+    }
 
     public final ZonedDateTime withZero() {
         return withMin();
     }
 
-    public abstract ZonedDateTime withMax();
-
     public final ZonedDateTime withMidnight() {
         return withZero();
     }
@@ -190,7 +184,10 @@ public abstract class ZonedDate implements Comparable<ZonedDate> {
         return (int)withZero().until(end.withZero(), unit);
     }
 
-    public abstract ZonedDate plus(long amount, ChronoUnit unit);
+    public ZonedDate plus(long amount, ChronoUnit unit) {
+        return new ZonedDate(zone, date.plus(amount, unit));
+    }
+
 
     public final ZonedDate minus(long amount, ChronoUnit unit) {
         return plus(-amount, unit);
@@ -220,12 +217,17 @@ public abstract class ZonedDate implements Comparable<ZonedDate> {
         return minus(days, ChronoUnit.DAYS);
     }
 
-    public abstract int getYear();
-
-    public abstract int getMonth();
+    public int getYear() {
+        return date.getYear();
+    }
 
-    public abstract int getDay();
+    public int getMonth() {
+        return date.getMonthValue();
+    }
 
+    public int getDay() {
+        return date.getDayOfMonth();
+    }
     @Override
     public int compareTo(ZonedDate other) {
         if(this.isBefore(other)) {
@@ -247,158 +249,9 @@ public abstract class ZonedDate implements Comparable<ZonedDate> {
         return Objects.hash(getYear(), getMonth(), getDay());
     }
 
-    public String format(DateTimeFormatter format) {
-        return DateTimeFormatters.format(format, withZero());
-    }
-
     @Override
     public String toString() {
-        return DateTimeFormatters.formatDate(withZero()) + " [" + getZone() + "]";
-    }
-
-    /**
-     * This wrapper allows all operations even if timezones do not match.
-     * Because we have full datetime, we can convert between timezones safely.
-     */
-    @RequiredArgsConstructor
-    private static class Complete extends ZonedDate {
-
-        private final ZonedDateTime value;
-
-        @Override
-        public ZoneId getZone() {
-            return value.getZone();
-        }
-
-        @Override
-        public long toEpochDay() {
-            return value.toLocalDate().toEpochDay();
-        }
-
-        @Override
-        public boolean isZoneConvertible(ZoneId zone) {
-            return isSameZone(zone) || ALLOW_ZONE_CONVERSION;
-        }
-
-        @Override
-        public ZonedDate with(TemporalField field, long amount) {
-            if(!field.isDateBased()) {
-                throw new IllegalArgumentException();
-            }
-            return new Complete(value.with(field, amount));
-        }
-
-        @Override
-        public ZonedDate withZone(ZoneId zone) {
-            if(!isZoneConvertible(zone)) {
-                throw new UnsupportedOperationException();
-            }
-            return new Complete(value.withZoneSameInstant(zone));
-        }
-
-        @Override
-        public ZonedDateTime withMin() {
-            return value.with(LocalTime.MIN);
-        }
-
-        @Override
-        public ZonedDateTime withMax() {
-            return value.with(LocalTime.MAX);
-        }
-
-        @Override
-        public ZonedDate plus(long amount, ChronoUnit unit) {
-            return new Complete(value.plus(amount, unit));
-        }
-
-        @Override
-        public int getYear() {
-            return value.getYear();
-        }
-
-        @Override
-        public int getMonth() {
-            return value.getMonthValue();
-        }
-
-        @Override
-        public int getDay() {
-            return value.getDayOfMonth();
-        }
-    }
-
-    /**
-     * This wrapper throws exception when timezones do not match.
-     * It is impossible to convert between timezones without full datetime.
-     */
-    @RequiredArgsConstructor
-    private static class Incomplete extends ZonedDate {
-
-        private final ZoneId zone;
-
-        private final LocalDate value;
-
-        @Override
-        public ZoneId getZone() {
-            return zone;
-        }
-
-        @Override
-        public long toEpochDay() {
-            return value.toEpochDay();
-        }
-
-        @Override
-        public boolean isZoneConvertible(ZoneId zone) {
-            return getZone().equals(zone);
-        }
-
-        @Override
-        public ZonedDate with(TemporalField field, long amount) {
-            if(!field.isDateBased()) {
-                throw new IllegalArgumentException();
-            }
-            return new Incomplete(zone, value.with(field, amount));
-        }
-
-        @Override
-        public ZonedDate withZone(ZoneId zone) {
-            if(!isSameZone(zone)) {
-                throw new UnsupportedOperationException("This date " + this + " can't be converted to " + zone);
-            } else {
-                return this;
-            }
-        }
-
-        @Override
-        public ZonedDateTime withMin() {
-            return ZonedDateTime.of(value, LocalTime.MIN, getZone());
-        }
-
-        @Override
-        public ZonedDateTime withMax() {
-            return ZonedDateTime.of(value, LocalTime.MAX, getZone());
-        }
-
-        @Override
-        public ZonedDate plus(long amount, ChronoUnit unit) {
-            return new Incomplete(zone, value.plus(amount, unit));
-        }
-
-        @Override
-        public int getYear() {
-            return value.getYear();
-        }
-
-        @Override
-        public int getMonth() {
-            return value.getMonthValue();
-        }
-
-        @Override
-        public int getDay() {
-            return value.getDayOfMonth();
-        }
+        return DateTimeFormatters1.formatDate(withZero()) + " [" + getZone() + "]";
     }
 
 }

+ 0 - 43
assira.commons/src/main/java/net/ranides/assira/time2/ZonedDateRange.java

@@ -1,43 +0,0 @@
-package net.ranides.assira.time2;
-
-import lombok.Builder;
-
-import java.time.ZonedDateTime;
-import java.time.temporal.TemporalField;
-
-@Builder
-public class ZonedDateRange {
-
-    // @todo ranides remove or use
-
-    private final TemporalField precision;
-    private final boolean inclusive;
-    private final ZonedDate begin;
-    private final ZonedDate end;
-
-    private ZonedDateRange(TemporalField precision, boolean inclusive, ZonedDate begin, ZonedDate end) {
-        this.precision = precision;
-        this.inclusive = inclusive;
-        this.begin = begin;
-        this.end = end;
-    }
-
-    public boolean between(ZonedDateTime testedDate) {
-        // eliminate dates "before"
-        if(begin != null && begin.isBefore(testedDate)) {
-            return false;
-        }
-        if(end == null) {
-            return true;
-        }
-
-        return inclusive ? !end.isAfter(testedDate) : end.isBefore(testedDate);
-    }
-
-    public boolean between(ZonedDate testedDate) {
-        return false;
-    }
-
-
-
-}

+ 0 - 82
assira.commons/src/main/java/net/ranides/assira/time2/ZonedDateTimeRange.java

@@ -1,82 +0,0 @@
-package net.ranides.assira.time2;
-
-import java.io.Serializable;
-import java.time.ZonedDateTime;
-
-public abstract class ZonedDateTimeRange implements Serializable {
-
-    // @todo ranides remove or use
-
-    public static ZonedDateTimeRange of(ZonedDateTime begin, ZonedDateTime end) {
-        if(begin == null) {
-            return new BeginRange(end);
-        }
-        if(end == null) {
-            return new BeginRange(end);
-        }
-        return new FullRange(begin, end);
-    }
-
-    public abstract boolean between(ZonedDateTime testedDate);
-
-    public abstract boolean between(ZonedDate testedDate);
-
-    private static class EndRange extends ZonedDateTimeRange {
-        private final ZonedDateTime end;
-
-        private EndRange(ZonedDateTime end) {
-            this.end = end;
-        }
-
-        @Override
-        public boolean between(ZonedDateTime testedDate) {
-            return testedDate.isBefore(end);
-        }
-
-        @Override
-        public boolean between(ZonedDate testedDate) {
-            if(!testedDate.getZone().equals(end.getZone())) {
-                throw new IllegalArgumentException();
-            }
-            return testedDate.withMidnight().isBefore(end);
-        }
-    }
-
-    private static class BeginRange extends ZonedDateTimeRange {
-        private final ZonedDateTime begin;
-
-        private BeginRange(ZonedDateTime begin) {
-            this.begin = begin;
-        }
-
-        @Override
-        public boolean between(ZonedDateTime testedDate) {
-            return !testedDate.isBefore(begin);
-        }
-
-        @Override
-        public boolean between(ZonedDate testedDate) {
-            return !testedDate.withMidnight().isBefore(begin);
-        }
-    }
-
-    private static class FullRange extends ZonedDateTimeRange {
-        private final ZonedDateTime begin;
-        private final ZonedDateTime end;
-
-        public FullRange(ZonedDateTime begin, ZonedDateTime end) {
-            this.begin = begin;
-            this.end = end;
-        }
-
-        @Override
-        public boolean between(ZonedDateTime testedDate) {
-            return false;
-        }
-
-        @Override
-        public boolean between(ZonedDate testedDate) {
-            return false;
-        }
-    }
-}

+ 84 - 225
assira.commons/src/main/java/net/ranides/assira/time2/ZonedTime.java

@@ -2,7 +2,6 @@ package net.ranides.assira.time2;
 
 import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
 import com.fasterxml.jackson.databind.annotation.JsonSerialize;
-import lombok.RequiredArgsConstructor;
 import net.ranides.assira.time2.json.ZonedTimeDeserializer;
 import net.ranides.assira.time2.json.ZonedTimeSerializer;
 import org.jetbrains.annotations.Contract;
@@ -10,7 +9,12 @@ import org.jetbrains.annotations.NotNull;
 import org.jetbrains.annotations.Nullable;
 
 import java.sql.Timestamp;
-import java.time.*;
+import java.time.Duration;
+import java.time.Instant;
+import java.time.LocalDate;
+import java.time.LocalTime;
+import java.time.ZoneId;
+import java.time.ZonedDateTime;
 import java.time.temporal.ChronoField;
 import java.time.temporal.ChronoUnit;
 import java.time.temporal.TemporalField;
@@ -18,23 +22,30 @@ import java.util.Objects;
 
 @JsonDeserialize(using = ZonedTimeDeserializer.class)
 @JsonSerialize(using = ZonedTimeSerializer.class)
-public abstract class ZonedTime implements Comparable<ZonedTime> {
-
-    private static final boolean ALLOW_ZONE_CONVERSION = true;
+public class ZonedTime implements Comparable<ZonedTime> {
 
     // @todo SQL timestamp test
 
+    private final ZoneId zone;
+
+    private final LocalTime time;
+
+    private ZonedTime(ZoneId zone, LocalTime time) {
+        this.zone = zone;
+        this.time = time;
+    }
+
     @Contract("null -> null; !null -> !null")
     public static @Nullable ZonedTime of(@Nullable ZonedDateTime input) {
         if(Objects.isNull(input)) {
             return null;
         }
-        return new Complete(input);
+        return new ZonedTime(input.getZone(), input.toLocalTime());
     }
 
     @ZoneExplicit
     public static @NotNull ZonedTime of(@NotNull ZoneId zone, @NotNull LocalTime time) {
-        return new Incomplete(zone, time);
+        return new ZonedTime(zone, time);
     }
 
     @Contract("null -> null; !null -> !null")
@@ -45,10 +56,11 @@ public abstract class ZonedTime implements Comparable<ZonedTime> {
         return of(ZoneId.systemDefault(), input);
     }
 
-    @ZoneExplicit
     @Deprecated
-    public static ZonedTime of(@NotNull ZoneId zone, @NotNull Timestamp source) {
-        return new Incomplete(zone, source.toLocalDateTime().atZone(zone).toLocalTime());
+    @ZoneExplicit
+    @Contract("_,null -> null; _,!null -> !null")
+    public static ZonedTime of(@NotNull ZoneId zone, @Nullable Timestamp source) {
+        return new ZonedTime(zone, source.toLocalDateTime().atZone(zone).toLocalTime());
     }
 
     @ZoneExplicit
@@ -58,12 +70,16 @@ public abstract class ZonedTime implements Comparable<ZonedTime> {
     }
 
     public static @NotNull ZonedTime now() {
-        return new Complete(ZonedDateTime.now());
+        return of(ZonedDateTime.now());
     }
 
-    public abstract ZoneId getZone();
+    public ZoneId getZone() {
+        return zone;
+    }
 
-    public abstract ZonedTime plus(long amount, ChronoUnit unit);
+    public ZonedTime plus(long amount, ChronoUnit unit) {
+        return new ZonedTime(zone, time.plus(amount, unit));
+    }
 
     public final ZonedTime minus(long amount, ChronoUnit unit) {
         return plus(-amount, unit);
@@ -101,25 +117,45 @@ public abstract class ZonedTime implements Comparable<ZonedTime> {
         return minus(nanos, ChronoUnit.NANOS);
     }
 
-    public abstract int getHour();
+    public int getHour() {
+        return time.getHour();
+    }
 
-    public abstract int getMinute();
+    public int getMinute() {
+        return time.getMinute();
+    }
 
-    public abstract int getSecond();
+    public int getSecond() {
+        return time.getSecond();
+    }
 
-    public abstract int getNano();
+    public int getNano() {
+        return time.getNano();
+    }
 
-    public abstract long toNanoOfDay();
+    public long toNanoOfDay() {
+        return time.toNanoOfDay();
+    }
 
     @ZoneHazard
-    public abstract boolean isAfter(ZonedTime other);
+    public boolean isAfter(ZonedTime other) {
+        if(!isSameZone(other)) {
+            throw new UnsupportedOperationException();
+        }
+        return toNanoOfDay() > other.toNanoOfDay();
+    }
 
     public final boolean isAfter(ZonedDateTime other) {
         return toNanoOfDay() > other.withZoneSameInstant(getZone()).toLocalTime().toNanoOfDay();
     }
 
     @ZoneHazard
-    public abstract boolean isBefore(ZonedTime other);
+    public boolean isBefore(ZonedTime other) {
+        if(!isSameZone(other)) {
+            throw new UnsupportedOperationException();
+        }
+        return toNanoOfDay() < other.toNanoOfDay();
+    }
 
     public final boolean isBefore(ZonedDateTime other) {
         return toNanoOfDay() < other.withZoneSameInstant(getZone()).toLocalTime().toNanoOfDay();
@@ -135,8 +171,9 @@ public abstract class ZonedTime implements Comparable<ZonedTime> {
         return (obj instanceof ZonedTime) && isEqual((ZonedTime)obj);
     }
 
-    @ZoneHazard
-    public abstract boolean isEqual(ZonedTime other);
+    public boolean isEqual(ZonedTime other) {
+        return isSameZone(other) && toNanoOfDay() == other.toNanoOfDay();
+    }
 
     public final boolean isEqualTime(ZonedDateTime other) {
         return toNanoOfDay() == other.withZoneSameInstant(getZone()).toLocalTime().toNanoOfDay();
@@ -156,50 +193,39 @@ public abstract class ZonedTime implements Comparable<ZonedTime> {
         return getZone().equals(other);
     }
 
-    public abstract boolean isZoneConvertible(@NotNull ZoneId zone);
-
-    @ZoneExplicit
-    @ZoneHazard
-    public abstract ZonedTime withZone(ZoneId zone);
-
-    @ZoneExplicit
-    @ZoneHazard
-    public final ZonedTime withZoneUtc() {
-        return withZone(DateTimeUtils.ZONE_UTC);
-    }
-
-    @ZoneExplicit
-    @ZoneHazard
-    public final ZonedTime withZonePolish() {
-        return withZone(DateTimeUtils.ZONE_PL);
+    public ZonedTime with(TemporalField field, long amount) {
+        return new ZonedTime(zone, time.with(field, amount));
     }
 
-    public abstract ZonedTime with(TemporalField field, long amount);
-
-    public ZonedTime withHour(int value) {
-        return with(ChronoField.HOUR_OF_DAY, value);
+    public ZonedTime withHour(int amount) {
+        return with(ChronoField.HOUR_OF_DAY, amount);
     }
 
-    public ZonedTime withMinute(int value) {
-        return with(ChronoField.MINUTE_OF_HOUR, value);
+    public ZonedTime withMinute(int amount) {
+        return with(ChronoField.MINUTE_OF_HOUR, amount);
     }
 
-    public ZonedTime withSecond(int value) {
-        return with(ChronoField.SECOND_OF_MINUTE, value);
+    public ZonedTime withSecond(int amount) {
+        return with(ChronoField.SECOND_OF_MINUTE, amount);
     }
 
-    public ZonedTime withNano(int value) {
-        return with(ChronoField.NANO_OF_SECOND, value);
+    public ZonedTime withNano(int amount) {
+        return with(ChronoField.NANO_OF_SECOND, amount);
     }
 
     @ZoneHazard
-    public final @NotNull ZonedDateTime withDate(@NotNull ZonedDate time) {
-        return Objects.requireNonNull(time).withTime(this);
+    public final @NotNull ZonedDateTime withDate(@NotNull ZonedDate date) {
+        if(!isSameZone(date.getZone())) {
+            throw new UnsupportedOperationException();
+        }
+        return ZonedDateTime.of(LocalDate.ofEpochDay(date.toEpochDay()), time, getZone());
     }
 
     public ZonedDateTime withDate(ZonedDateTime datetime) {
-        //noinspection timezone-hazard
-        return withDate(ZonedDate.of(datetime));
+        if(!isSameZone(datetime)) {
+            throw new UnsupportedOperationException();
+        }
+        return ZonedDateTime.of(datetime.toLocalDate(), time, getZone());
     }
 
     public final Duration until(ZonedDateTime end) {
@@ -217,7 +243,11 @@ public abstract class ZonedTime implements Comparable<ZonedTime> {
     }
 
     @ZoneHazard
-    public abstract long until(ZonedTime end, ChronoUnit unit);
+    public long until(ZonedTime end, ChronoUnit unit) {
+        // @todo require zone
+        long nanos = end.toNanoOfDay() - toNanoOfDay();
+        return nanos / unit.getDuration().toNanos();
+    }
 
     @ZoneHazard
     @Override
@@ -233,178 +263,7 @@ public abstract class ZonedTime implements Comparable<ZonedTime> {
 
     @Override
     public String toString() {
-        return DateTimeFormatters.formatTime(withDate(ZonedDateTime.now())) + " [" + getZone() + "]";
-    }
-
-    /**
-     * This wrapper allows all operations even if timezones do not match.
-     * Because we have full datetime, we can convert between timezones safely.
-     */
-    @RequiredArgsConstructor
-    private static class Complete extends ZonedTime {
-
-        private final ZonedDateTime value;
-
-        @Override
-        public ZoneId getZone() {
-            return value.getZone();
-        }
-
-        @Override
-        public boolean isAfter(ZonedTime other) {
-            return withZone(other.getZone()).toNanoOfDay() > other.toNanoOfDay();
-        }
-
-        @Override
-        public boolean isBefore(ZonedTime other) {
-            return withZone(other.getZone()).toNanoOfDay() < other.toNanoOfDay();
-        }
-
-        @Override
-        public boolean isEqual(ZonedTime other) {
-            return withZone(other.getZone()).toNanoOfDay() == other.toNanoOfDay();
-        }
-
-        @Override
-        public boolean isZoneConvertible(ZoneId zone) {
-            return isSameZone(zone) || ALLOW_ZONE_CONVERSION;
-        }
-
-        @Override
-        public ZonedTime withZone(ZoneId zone) {
-            if(!isZoneConvertible(zone)) {
-                throw new UnsupportedOperationException();
-            }
-            return new Complete(value.withZoneSameInstant(zone));
-        }
-
-        @Override
-        public ZonedTime with(TemporalField field, long amount) {
-            return new Complete(value.with(field, amount));
-        }
-
-        @Override
-        public ZonedTime plus(long amount, ChronoUnit unit) {
-            return new Complete(value.plus(amount, unit));
-        }
-
-        @Override
-        public long until(ZonedTime end, ChronoUnit unit) {
-            long nanos = end.toNanoOfDay() - withZone(end.getZone()).toNanoOfDay();
-            return nanos / unit.getDuration().toNanos();
-        }
-
-        @Override
-        public int getHour() {
-            return value.getHour();
-        }
-
-        @Override
-        public int getMinute() {
-            return value.getMinute();
-        }
-
-        @Override
-        public int getSecond() {
-            return value.getSecond();
-        }
-
-        @Override
-        public int getNano() {
-            return value.getNano();
-        }
-
-        @Override
-        public long toNanoOfDay() {
-            return value.toLocalTime().toNanoOfDay();
-        }
-    }
-
-    /**
-     * This wrapper throws exception when timezones do not match.
-     * It is impossible to convert between timezones without full datetime.
-     */
-    @RequiredArgsConstructor
-    private static class Incomplete extends ZonedTime {
-
-        private final ZoneId zone;
-
-        private final LocalTime value;
-
-        @Override
-        public ZoneId getZone() {
-            return zone;
-        }
-
-        @Override
-        public boolean isAfter(ZonedTime other) {
-            return toNanoOfDay() > other.withZone(getZone()).toNanoOfDay();
-        }
-
-        @Override
-        public boolean isBefore(ZonedTime other) {
-            return toNanoOfDay() < other.withZone(getZone()).toNanoOfDay();
-        }
-
-        @Override
-        public boolean isEqual(ZonedTime other) {
-            return toNanoOfDay() == other.withZone(getZone()).toNanoOfDay();
-        }
-
-        @Override
-        public boolean isZoneConvertible(ZoneId zone) {
-            return getZone().equals(zone);
-        }
-
-        @Override
-        public ZonedTime withZone(ZoneId zone) {
-            if(!isSameZone(zone)) {
-                throw new UnsupportedOperationException("This time " + this + " can't be converted to " + zone);
-            } else {
-                return this;
-            }
-        }
-
-        @Override
-        public ZonedTime with(TemporalField field, long amount) {
-            return new Incomplete(zone, value.with(field, amount));
-        }
-
-        @Override
-        public ZonedTime plus(long amount, ChronoUnit unit) {
-            return new Incomplete(zone, value.plus(amount, unit));
-        }
-
-        @Override
-        public long until(ZonedTime end, ChronoUnit unit) {
-            long nanos = end.withZone(getZone()).toNanoOfDay() - toNanoOfDay();
-            return nanos / unit.getDuration().toNanos();
-        }
-
-        @Override
-        public int getHour() {
-            return value.getHour();
-        }
-
-        @Override
-        public int getMinute() {
-            return value.getMinute();
-        }
-
-        @Override
-        public int getSecond() {
-            return value.getSecond();
-        }
-
-        @Override
-        public int getNano() {
-            return value.getNano();
-        }
-
-        @Override
-        public long toNanoOfDay() {
-            return value.toNanoOfDay();
-        }
+        return DateTimeFormatters1.formatTimeShort(withDate(ZonedDateTime.now())) + " [" + getZone() + "]";
     }
 
 }

+ 2 - 2
assira.commons/src/main/java/net/ranides/assira/time2/json/ZonedDateDeserializer.java

@@ -10,7 +10,7 @@ import com.fasterxml.jackson.databind.JsonDeserializer;
 import com.fasterxml.jackson.databind.JsonMappingException;
 import com.fasterxml.jackson.databind.deser.ContextualDeserializer;
 import com.fasterxml.jackson.databind.deser.std.StdDeserializer;
-import net.ranides.assira.time2.DateTimeFormatters;
+import net.ranides.assira.time2.DateTimeFormatters1;
 import net.ranides.assira.time2.DateTimeParsers;
 import net.ranides.assira.time2.DateTimeUtils;
 import net.ranides.assira.time2.ZonedDate;
@@ -46,7 +46,7 @@ public class ZonedDateDeserializer extends StdDeserializer<ZonedDate> implements
             : DateTimeParsers.DATE;
 
         DateTimeFormatter formatter2 = formatter1
-            .withLocale(format.hasLocale() ? format.getLocale() : DateTimeFormatters.LOCALE_PL);
+            .withLocale(format.hasLocale() ? format.getLocale() : DateTimeFormatters1.LOCALE_PL);
 
         return new ZonedDateDeserializer(formatter2, format.hasTimeZone() ? format.getTimeZone().toZoneId() : DateTimeUtils.ZONE_UTC);
     }

+ 5 - 5
assira.commons/src/main/java/net/ranides/assira/time2/json/ZonedDateSerializer.java

@@ -8,7 +8,7 @@ import com.fasterxml.jackson.databind.JsonSerializer;
 import com.fasterxml.jackson.databind.SerializerProvider;
 import com.fasterxml.jackson.databind.ser.ContextualSerializer;
 import com.fasterxml.jackson.databind.ser.std.StdSerializer;
-import net.ranides.assira.time2.DateTimeFormatters;
+import net.ranides.assira.time2.DateTimeFormatters1;
 import net.ranides.assira.time2.DateTimeUtils;
 import net.ranides.assira.time2.ZonedDate;
 
@@ -21,7 +21,7 @@ public class ZonedDateSerializer extends StdSerializer<ZonedDate> implements Con
     private final boolean           useNumeric;
 
     protected ZonedDateSerializer() {
-        this(DateTimeFormatters.DATE.withZone(DateTimeUtils.ZONE_PL), false);
+        this(DateTimeFormatters1.DATE.withZone(DateTimeUtils.ZONE_PL), false);
     }
 
     public ZonedDateSerializer(DateTimeFormatter formatter, boolean useNumeric) {
@@ -42,10 +42,10 @@ public class ZonedDateSerializer extends StdSerializer<ZonedDate> implements Con
 
         DateTimeFormatter formatter1 = format.hasPattern()
             ? DateTimeFormatter.ofPattern(format.getPattern())
-            : DateTimeFormatters.DATE;
+            : DateTimeFormatters1.DATE;
 
         DateTimeFormatter formatter2 = formatter1
-            .withLocale(format.hasLocale() ? format.getLocale() : DateTimeFormatters.LOCALE_PL)
+            .withLocale(format.hasLocale() ? format.getLocale() : DateTimeFormatters1.LOCALE_PL)
             .withZone(format.hasTimeZone() ? format.getTimeZone().toZoneId() : DateTimeUtils.ZONE_UTC);
 
         return new ZonedDateSerializer(formatter2, false);
@@ -57,7 +57,7 @@ public class ZonedDateSerializer extends StdSerializer<ZonedDate> implements Con
         if (useNumeric) {
             gen.writeNumber(value.withMin().toEpochSecond());
         } else {
-            gen.writeString(DateTimeFormatters.format(formatter, value.withMin()));
+            gen.writeString(DateTimeFormatters1.format(formatter, value.withMin()));
         }
     }
 

+ 2 - 2
assira.commons/src/main/java/net/ranides/assira/time2/json/ZonedTimeDeserializer.java

@@ -10,7 +10,7 @@ import com.fasterxml.jackson.databind.JsonDeserializer;
 import com.fasterxml.jackson.databind.JsonMappingException;
 import com.fasterxml.jackson.databind.deser.ContextualDeserializer;
 import com.fasterxml.jackson.databind.deser.std.StdDeserializer;
-import net.ranides.assira.time2.DateTimeFormatters;
+import net.ranides.assira.time2.DateTimeFormatters1;
 import net.ranides.assira.time2.DateTimeParsers;
 import net.ranides.assira.time2.DateTimeUtils;
 import net.ranides.assira.time2.ZonedTime;
@@ -47,7 +47,7 @@ public class ZonedTimeDeserializer extends StdDeserializer<ZonedTime> implements
             : DateTimeParsers.TIME;
 
         DateTimeFormatter formatter2 = formatter1
-            .withLocale(format.hasLocale() ? format.getLocale() : DateTimeFormatters.LOCALE_PL);
+            .withLocale(format.hasLocale() ? format.getLocale() : DateTimeFormatters1.LOCALE_PL);
 
         return new ZonedTimeDeserializer(formatter2, format.hasTimeZone() ? format.getTimeZone().toZoneId() : DateTimeUtils.ZONE_UTC);
     }

+ 5 - 5
assira.commons/src/main/java/net/ranides/assira/time2/json/ZonedTimeSerializer.java

@@ -8,7 +8,7 @@ import com.fasterxml.jackson.databind.JsonSerializer;
 import com.fasterxml.jackson.databind.SerializerProvider;
 import com.fasterxml.jackson.databind.ser.ContextualSerializer;
 import com.fasterxml.jackson.databind.ser.std.StdSerializer;
-import net.ranides.assira.time2.DateTimeFormatters;
+import net.ranides.assira.time2.DateTimeFormatters1;
 import net.ranides.assira.time2.DateTimeUtils;
 import net.ranides.assira.time2.ZonedTime;
 
@@ -23,7 +23,7 @@ public class ZonedTimeSerializer extends StdSerializer<ZonedTime> implements Con
     private final boolean           useNumeric;
 
     protected ZonedTimeSerializer() {
-        this(DateTimeFormatters.DATE.withZone(DateTimeUtils.ZONE_PL), false);
+        this(DateTimeFormatters1.DATE.withZone(DateTimeUtils.ZONE_PL), false);
     }
 
     public ZonedTimeSerializer(DateTimeFormatter formatter, boolean useNumeric) {
@@ -45,10 +45,10 @@ public class ZonedTimeSerializer extends StdSerializer<ZonedTime> implements Con
 
         DateTimeFormatter formatter1 = format.hasPattern()
             ? DateTimeFormatter.ofPattern(format.getPattern())
-            : DateTimeFormatters.DATE;
+            : DateTimeFormatters1.DATE;
 
         DateTimeFormatter formatter2 = formatter1
-            .withLocale(format.hasLocale() ? format.getLocale() : DateTimeFormatters.LOCALE_PL)
+            .withLocale(format.hasLocale() ? format.getLocale() : DateTimeFormatters1.LOCALE_PL)
             .withZone(format.hasTimeZone() ? format.getTimeZone().toZoneId() : DateTimeUtils.ZONE_UTC);
 
         return new ZonedTimeSerializer(formatter2, false);
@@ -60,7 +60,7 @@ public class ZonedTimeSerializer extends StdSerializer<ZonedTime> implements Con
             long seconds = value.withZoneUtc().toNanoOfDay() / ChronoUnit.SECONDS.getDuration().toNanos();
             gen.writeNumber(seconds);
         } else {
-            gen.writeString(DateTimeFormatters.format(formatter, value.withDate(ZonedDateTime.now())));
+            gen.writeString(DateTimeFormatters1.format(formatter, value.withDate(ZonedDateTime.now())));
         }
     }
 

+ 2 - 4
assira.commons/src/test/java/net/ranides/assira/time2/DateTimeFormattersTest.java

@@ -4,14 +4,12 @@ import org.junit.Test;
 
 import java.time.ZonedDateTime;
 
-import static org.junit.Assert.*;
-
 public class DateTimeFormattersTest {
 
     @Test
     public void testFormatUtc() {
-        DateTimeFormatters.formatUtc(ZonedDateTime.now());
+        DateTimeFormatters1.formatUtc(ZonedDateTime.now());
 
-        System.out.println( DateTimeFormatters.formatUtc(null) );
+        System.out.println( DateTimeFormatters1.formatUtc(null) );
     }
 }

+ 0 - 3
assira.commons/src/test/java/net/ranides/assira/time2/json/ZonedTimeDeserializerTest.java

@@ -8,13 +8,10 @@ import com.fasterxml.jackson.databind.json.JsonMapper;
 import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
 import lombok.Builder;
 import lombok.Data;
-import net.ranides.assira.time2.DateTimeFormatters;
 import net.ranides.assira.time2.DateTimeLiteral;
-import net.ranides.assira.time2.ZonedDate;
 import net.ranides.assira.time2.ZonedTime;
 import org.junit.Test;
 
-import java.time.LocalDate;
 import java.time.LocalTime;
 import java.time.ZoneId;
 import java.time.ZonedDateTime;