[threeten-dev] j.u.Date/Calendrical/GregorianCalendar

Xueming Shen xueming.shen at oracle.com
Wed Dec 5 09:34:59 PST 2012


To implement DateTimeAccessor on Date/GregorianCalendar will not make
the migration easier, it will actually prevent from migrating the old code to
new one. My experience indicates in most cases, developer will simply pass
around the old Date and GregorianC into the new date/time based code, if
they can.

Sure the spec of DateTimeAccessor does not say it should be implemented
as mutable and yes, we have that "DateTimeBuilder" around. But I think
one of the design goals of threeten is to have all date/time around immutable,
and this has been one of major reasons lots of suggestions have been
rejected in the past year, why we want to open the door now for two
well-known mutable date/time types from the "old" world. I don't see any
reason why developer would be upset if they have to do date.toInstant()/
cal.toZonedDateTime() before pass their old date/time into the new system.
Performance might be a concern for some apps, but this might just motivate
them to go up level a little to see if those Date and GregorianCalendar should
be Instant and ZDT at first place.

-Sherman

On 12/05/2012 07:15 AM, Stephen Colebourne wrote:
> On 5 December 2012 06:13, Xueming Shen<xueming.shen at oracle.com>  wrote:
>> Date<->  Instant appears to be a must, in which it provides the
>> connection/conversion
>> at the bottom between two different systems, so we don't need Date<->  ODT
>> for
>> example.
>>
>> How to support the Date<->  Instant?
>>
>> I believe we only need ONE straightforward/direct conversion, don't need to
>> provide
>> multiple convenient vehicles here, developer should just use this entry
>> point to convert
>> between these two types. As you suggested, use nio.file as an example, a
>> simple pair
>> of File.toPath() and Path.toFile() should be good enough.
>>
>> Date.toInstant() and "util.Date must support the same fields as Instant -
>> INSTANT_SECONDS and the three fractional seconds fields" are obviously
>> redundant.
>> With this, now you can do
>>
>> Date date = ...;
>> Instant instant = date.toInstant();
>> or
>> Instant instant = Instant.from(date);
>>
>> If we don't need two, which one is better? DateTimeAccessor appears to be
>> convenient, with this, you can also do OffsetDateTime.from(date), and any
>> "extended"
>> date/time that knows INSTANT_SECONDS+fractional sec fields can work with
>> u.Date
>> as well. But it also brings us the biggest problem, all of the sudden,
>> j.u.Date can fly
>> freely inside the new JSR310 system. Conveniently, our datetime formatter
>> also magically
>> work with j.u.Date. Is this something you want to see? It appears to be an
>> integration
>> of two systems, not a bridge. Sure, it provides convenience, but it also has
>> the
>> consequence, you now have a mutable DateTimeAccessor running around your
>> JSR310
>> code.
> DateTimeAccessor has always been known to be possibly mutable. Its an
> interface, so nothing there can really be controlled. Having a
> java.util.Date (or Calendar) work with the new immutable formatter
> seems like a good thing - easy for developers to fix thread-unsafe
> static formatters in their current code.
>
> Integration is essentially what the system has been designed for.
> Previous designs did it in different ways, but they all were planned
> such that the old classes would implement the new interface, allowing
> general use.
>
>> So personally I think a simple Date.toInstant() is the best choice, it
>> provide a "single"
>> entry point for all those "old" date/time. The code that uses JSR310
>> date/time should
>> just work with new date/time, old date/time need to be converted into new
>> types to
>> get in.
>>
>> A Instant.toDate() will be a little confusing, I would suggest just do
>> Date.fromInstant().
> Clearly, this satisfies the basic problem, but its not what was
> intended in the design (which was DateTimeAccessor).
>
> There are actually four sensible options:
>
> A) toInstant() and from(Instant), j.u.Date not implement DateTimeAccessor
> B) toInstant() and from(DateTimeAccessor), j.u.Date not implement
> DateTimeAccessor
> C) from(DateTimeAccessor), j.u.Date implements DateTimeAccessor
> D) toInstant() and from(DateTimeAccessor), j.u.Date implements DateTimeAccessor
>
> I'd always intended (D), as it best matches the rest fo 310.
>
> Note that (B), (C), (D) allow j.u.Date.from(zoneDateTime) or
> from(offsetDateTime), which (A) does not, and these seem like useful
> conversions.
>
> OffsetDateTime.from(j.u.Date) will not work in any option, as there is
> no offset.
>
>> In theory, it's doable to bridge the conversion of GregorianCalendar and ZDT
>> by
>>
>>       GregorianCalendar<->  Date<->  Instant<->  ZDT,
>>
>> but obviously the "zone" is missing, it's probably not desirable to use
>> "default". So, it
>> appears GregorianCalendar<->  ZDT is another candidate. For same reason I
>> mentioned
>> above, I don't think you want to "integrate" GregorianCalendar into the new
>> system, stop
>> it by forcing it to be the immutable ZDT before any new code can touch it.
>> Otherwise,
>> the worse thing is that, not like j.u.Date, those "setting" methods of
>> GregorianCalendar
>> are not deprecated.
> Again, this works but isn't ideal. My aim was to provide an easy
> migration, not a hard one.
>
> Stephen



More information about the threeten-dev mailing list