What is the main purpose of the new interface java.time.InstantSource over existing abstract class Clock?
Asked Answered
R

1

10

A new interface java.time.InstantSource was added in Java 17. What is the use case of that additional abstraction if all implementations of that interface are Clock implementations too anyway?

Rew answered 15/9, 2021 at 20:59 Comment(3)
Look at the JDK-8266847 to see if it answer your question: bugs-stage.openjdk.java.net/browse/JDK-8266847 ?Extrasensory
But anyway to create an object with the type of InstantSource we use Clock factory methods explicitly or under the hood (Clock with UTC). So anyway we operate specific timezone. There is example in javadocs where InstantSource used as pluggable injected object. What can be injected in that case?Mallorie
Please clarify your specific problem or provide additional details to highlight exactly what you need. As it's currently written, it's hard to tell exactly what you're asking.Hebbel
C
13

With thanks to NoDataFound for the link in the comment (link repeated at the bottom of this answer). The “bug” report by Stephen Colebourne (original developer of java.time) says:

Problem

Since java.time was first added in Java 8, it has become apparent that there is a missing concept - a source of Instant independent of time zone. Put simply, if the only thing you want is an Instant, then Clock isn't the right API because it forces you to think about time zones.

A good architectural design for time-based code would have a separation between the abstraction of the OS clock (dependency injected for unit testing), and the time zone linked to user localization. Passing these two things around separately is key. To achieve this as it stands, developers must either write their own TimeSource or InstantSource interface, or use Clock and "hold their nose" to ignore the time zone held within.

A Supplier<Instant> obviously performs similar functionality, but it lacks discoverability and understandability. Plus, injecting generified interfaces tends to be painful.

In my words: The Clock class was introduced as a source of the current time. Conceptually a source of the current time should be independent of time zone. The Clock nevertheless has a time zone. Possibly for practical purposes so that you can draw all sorts of date-time objects from it: LocalDate, ZonedDateTime, LocalTime, etc.

The InstantSource interface asked about realizes the clock concept that I just described: a source of the current time that is independent of time zone. For when a clock with time zone is too heavyweight for your purpose.

One of the purposes of both Clock and InstantSource is testability: With those you can control which time is considered “the current time” when your tests are run, which is often required when you want reproducible tests.

… if anyway all implementations of that interface are Clock implementations also?

I haven’t checked whether all InstantSource implementations shipped with Java 17 are Clock subclasses. Even if this is the case, (1) it is not the point, and (2) there’s no one stopping you implementing an InstantSource that is not a Clock. Abstraction is a key concept in programming. If you want only Instants, then you want to program against a simple interface that can give you only Instants. InstantSource abstracts away the fact that the object you are using would also be able to play the rôle of a Clock in some other context. The InstantSource interface is a school example of applying the well-respected Façade design pattern (link below). With Stephen Colebourne’s descriptive words from the bug system, the interface frees the programmer from „holding their nose” while obtaining Instants.

Links

Centimeter answered 10/10, 2021 at 11:44 Comment(1)
Interesting - for NodaTime, our IClock interface is equivalent to InstantSource... and then we have a ZonedClock class which accepts an IClock and a IDateTimeZone for the sake of convenience.Atomism

© 2022 - 2025 — McMap. All rights reserved.