import ZonedDateTime from "ts-time/ZonedDateTime";
Comprises a specific instant bound to a specific time zone. In other words, this is a tuple of (Instant, ZoneId). Unambiguously identifies an OffsetDateTime, i.e. LocalDateTime and ZoneOffset.
Typically you don't construct ZonedDateTime directly, but create it from other data structures:
ZonedDateTime.ofInstant(instant, zone); // From Instant in a given ZoneId instant.atZone(zone); // Equivalent ZonedDateTime.ofDateTime(dateTime, zone); // From LocalDateTime in a given ZoneId dateTime.atZone(zone); // Equivalent offsetDateTime.instant.atZone(zone); // From OffsetDateTime in a given ZoneId, preserving instant component offsetDateTime.dateTime.atZone(zone); // From OffsetDateTime in a given ZoneId, preserving dateTime component
Please notice that:
const zone = ZoneId.of("America/New_York"); const instant = Instant.parse("2022-06-14T00:00:00.000Z"); console.log(instant.atZone(zone)); // "2022-06-13T20:00:00.000-04:00[America/New_York]"It happens, because ZonedDateTime preserves its instant component in this case, not dateTime:
console.log(instant.atZone(zone).instant); // "2022-06-14T00:00:00.000Z" console.log(instant.atZone(zone).dateTime); // "2022-06-13T20:00:00.000"
const dateTime = LocalDateTime.parse("2022-06-14T00:00:00.000"); console.log(dateTime.atZone(zone)); // "2022-06-14T00:00:00.000-04:00[America/New_York]" console.log(dateTime.atZone(zone).dateTime); // "2022-06-14T00:00:00.000" console.log(dateTime.atZone(zone).instant); // "2022-06-14T04:00:00.000Z"
As opposed to Java API, there's no common way to get the current instance of ZonedDateTime in ts-time, because ts-time doesn't have a concept of default time zone. Instead, you must get the current Instant and convert it to an object that you need, taking time zone into consideration.
Instant.now().atZone(UTC); // Current ZonedDateTime in UTC Instant.now().atZone(LOCAL_ZONE_ID); // Current ZonedDateTime in the local time zone Instant.now().atZone(zone); // Current ZonedDateTime in a given ZoneId/ZoneOffset
It makes ts-time API more robust. It leaves less room for a mistake.
A common way to convert a native JavaScript Date object to a ts-time object is to call fromNative* static method:
Instant.fromNative(date).atZone(zone); // ZonedDateTime from a given Date in a given ZoneId/ZoneOffset
A common way to parse an ISO 8601 compliant string in ts-time is to call parse static method. For example, the following ZonedDateTime instance represents 18 hours, 30 minutes, 15 seconds, 225 milliseconds on 15th of February, 2022 in New York:
ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]");
The library doesn't yet support parsing non-compliant strings.
In the following example, we inspect various properties of a ZonedDateTime object. Please notice the difference in return value types:
const zonedDateTime = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); const year = zonedDateTime.year; // 2022 const month = zonedDateTime.month; // FEBRUARY const monthValue = zonedDateTime.month.value; // 2 const dayOfMonth = zonedDateTime.dayOfMonth; // 15 const dayOfWeek = zonedDateTime.dayOfWeek; // TUESDAY const dayOfWeekValue = zonedDateTime.dayOfWeek.value; // 2 const hour = zonedDateTime.hour; // 18 const minute = zonedDateTime.minute; // 30 const second = zonedDateTime.second; // 15 const ms = zonedDateTime.ms; // 225 const zone = zonedDateTime.zone; // Instance of ZoneId const zoneId = zonedDateTime.zone.id; // "America/New_York" const offset = zonedDateTime.offset; // Instance of ZoneOffset const offsetHours = zonedDateTime.offset.hours; // -5 const offsetMinutes = zonedDateTime.offset.minutes; // 0 const offsetSeconds = zonedDateTime.offset.seconds; // 0
Other sophisticated features for ZonedDateTime inspection: epochMs, era, yearOfEra, weekBasedYear, weekOfWeekBasedYear, dayOfYear, dayOfWeekBasedYear, epochDay, quarterOfYear, isLeapYear, lengthOfYear.
A common way to compare objects in ts-time is to call equals, compareTo methods:
const d1 = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); const d2 = ZonedDateTime.parse("2022-02-15T18:30:15.226-05:00[America/New_York]"); d1.equals(d2); // false d1.compareTo(d2); // -1
The objects are first compared by instant, and then by zone text identifier.
For nullable objects, use static methods instead. Null and undefined are considered less than anything, except each other:
const d1: ZonedDateTime = null; const d2 = ZonedDateTime.parse("2022-02-15T18:30:15.226-05:00[America/New_York]"); ZonedDateTime.equal(d1, d2); // false ZonedDateTime.compare(d1, d2); // -1
As opposed to the majority of objects in ts-time, ZonedDateTime doesn't have isBefore and isAfter methods. You must explicitly specify which component you want to compare: instant or dateTime.
const d1 = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); const d2 = ZonedDateTime.parse("2022-02-15T20:30:15.226+01:00[Europe/Berlin]"); d1.instant.isBefore(d2.instant); // false d1.dateTime.isBefore(d2.dateTime); // true
Every object in ts-time is immutable. Therefore every manipulation returns a new object.
To add/subtract a Period, call plusPeriod/minusPeriod method:
const zonedDateTime = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); const d1 = zonedDateTime.plusPeriod(DAY_PERIOD); // 18:30:15.225 on 16th of February, 2022 in New York const d2 = zonedDateTime.plusPeriod(Period.ofDays(2)); // 18:30:15.225 on 17th of February, 2022 in New York const d3 = zonedDateTime.minusPeriod(MONTH_PERIOD); // 18:30:15.225 on 15th of January, 2022 in New York
The algorithm respects dateTime to align periods, not instant. In the following example, zonedDateTime is the 1st of March in Berlin, but still 28th of February in UTC. When adding a month, the library considers zonedDateTime to be the 1st of March, so it adds 31 days, not 28:
const zonedDateTime = ZonedDateTime.parse("2022-03-01T00:00:00.000+01:00[Europe/Berlin]"); const d1 = zonedDateTime.plusPeriod(MONTH_PERIOD); // Midnight on 1st of April, 2022 in Berlin
If you expect a month to be added in UTC, convert the instant explicitly to UTC first:
const d2 = zonedDateTime.instant.atZone(UTC).plusPeriod(MONTH_PERIOD); // 23:00 on 28th of March, 2022, UTC
If the date/time jumps over daylight saving borderline, the result will have a different offset:
const winterTime = ZonedDateTime.parse("2022-03-01T00:00:00.000+01:00[Europe/Berlin]"); const summerTime = winterTime.plusPeriod(Period.ofMonths(3)); console.log(summerTime); // "2022-06-01T00:00:00.000+02:00[Europe/Berlin]"
The same may happen in rare cases of historical time zone rule changes (i.e. regulations of local governments).
To add/subtract a Duration, call plusDuration/minusDuration method:
const zonedDateTime = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); const d1 = zonedDateTime.plusDuration(MINUTE_DURATION); // 18:31:15.225 on 15th of February in New York const d2 = zonedDateTime.plusDuration(Duration.ofHours(10)); // 04:30:15.225 on 16th of February in New York const d3 = zonedDateTime.minusDuration(Duration.ofSeconds(30)); // 18:29:45.225 on 15th of February in New York
For difference between Period and Duration, see their documentation. When manipulating ZonedDateTime, this difference is important to understand.
To change one of the components, preserving all the rest, call with* methods:
const zonedDateTime = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); const d1 = zonedDateTime.withYear(2025); // 18:30:15.225 on 15th of February, 2025 in New York const d2 = zonedDateTime.withMonth(APRIL); // 18:30:15.225 on 15th of April, 2022 in New York const d3 = zonedDateTime.withDayOfMonth(10); // 18:30:15.225 on 10th of February, 2022 in New York const d4 = zonedDateTime.withDayOfWeek(SUNDAY); // 18:30:15.225 on 20th of February, 2022, Sunday in New York const d5 = zonedDateTime.withHour(20); // 20:30:15.225 on 15th of February, 2022 in New York const d6 = zonedDateTime.withMinute(20); // 18:20:15.225 on 15th of February, 2022 in New York const d7 = zonedDateTime.withSecond(20); // 18:30:20.225 on 15th of February, 2022 in New York const d8 = zonedDateTime.withMs(20); // 18:30:15.020 on 15th of February, 2022 in New York
For manipulating zone component, see Convert.
The library doesn't yet support ZonedDateTime truncating. Truncate its dateTime component instead.
Another sophisticated feature for ZonedDateTime manipulation: withDayOfYear.
You can convert ZonedDateTime to other kinds of objects via its properties:
const zonedDateTime = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); zonedDateTime.instant; // To Instant: 2022-02-15T23:30:15.225Z zonedDateTime.date; // To LocalDate: 2022-02-15 zonedDateTime.time; // To LocalTime: 18:30:15.225 zonedDateTime.dateTime; // To LocalDateTime: 2022-02-15T18:30:15.225 zonedDateTime.instant.atOffset(offset); // To OffsetDateTime in a given ZoneOffset, preserving instant component: 2022-02-16T03:30:15.225+04:00 zonedDateTime.dateTime.atOffset(offset); // To OffsetDateTime in a given ZoneOffset, preserving dateTime component: 2022-02-15T18:30:15.225+04:00 zonedDateTime.instant.atZone(zone); // To ZonedDateTime with another ZoneId, preserving instant component: 2022-02-16T00:30:15.225+01:00[Europe/Berlin] zonedDateTime.dateTime.atZone(zone); // To ZonedDateTime with another ZoneId, preserving dateTime component: 2022-02-15T18:30:15.225+01:00[Europe/Berlin]
Please notice that all conversions result in a partial data loss (date, time, original time zone).
You can as well convert ZonedDateTime to a native JavaScript Date:
const zonedDateTime = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); zonedDateTime.native; // Date representing 23:30:15.225 on 15th of February, 2022 (UTC)
Please notice that native Date is always stored in UTC or local time zone, so you can see a different date/time when printing it as a string. It will be the same instant, just a different time zone.
For backward conversion, see Construct.
Every class in ts-time has ISO 8601 compliant toString method:
const zonedDateTime = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); zonedDateTime.toString(); // "2022-02-15T18:30:15.225-05:00[America/New_York]"
For more sophisticated string formatting, add ts-time-format library to your list of dependencies:
npm install --save ts-time-format
Now you can construct an instance of ZonedDateTimeFormatter in order to format arbitrary ZonedDateTime instances:
const formatter = ZonedDateTimeFormatter.ofPattern("dd.MMM''yy, hh:mm a ('UTC'x, V)"); const zonedDateTime = ZonedDateTime.parse("2022-02-15T18:30:15.225-05:00[America/New_York]"); formatter.format(zonedDateTime); // "15.Feb'22, 06:30 PM (UTC-05, America/New_York)"
You can define a custom context object to internationalize the formatted strings:
const context = {monthShortNames: ["Янв", "Фев", "Мар"]}; formatter.format(zonedDateTime, context); // "15.Фев'22, 06:30 PM (UTC-05, America/New_York)"
readonly date: LocalDate
readonly time: LocalTime
readonly native: Date
readonly epochMs: number
readonly era: Era
readonly year: number
readonly weekBasedYear: number
By definition, the 1st week of week based year contains the 1st Thursday of the year, and the week based year starts from the Monday of this week.
readonly month: Month
readonly weekOfWeekBasedYear: number
By definition, the 1st week of week based year contains the 1st Thursday of the year, and the week based year starts from the Monday of this week.
readonly dayOfYear: number
readonly dayOfWeekBasedYear: number
By definition, the 1st week of week based year contains the 1st Thursday of the year, and the week based year starts from the Monday of this week.
readonly dayOfMonth: number
readonly dayOfWeek: DayOfWeek
readonly epochDay: number
readonly quarterOfYear: number
readonly isLeapYear: boolean
readonly lengthOfYear: number
readonly hour: number
readonly minute: number
readonly second: number
readonly ms: number
(other: ZonedDateTime): number
Note that a method call on null or undefined always leads to an error. So, if your variable may contain null or undefined, use the respective static method instead.
(other: ZonedDateTime): boolean
Note that a method call on null or undefined always leads to an error. So, if your variable may contain null or undefined, use the respective static method instead.
(duration: Duration): ZonedDateTime
(period: Period): ZonedDateTime
(duration: Duration): ZonedDateTime
(period: Period): ZonedDateTime
(year: number): ZonedDateTime
(month: number | Month): ZonedDateTime
(dayOfMonth: number): ZonedDateTime
(dayOfWeek: number | DayOfWeek): ZonedDateTime
(dayOfYear: number): ZonedDateTime
(hour: number): ZonedDateTime
(minute: number): ZonedDateTime
(second: number): ZonedDateTime
(ms: number): ZonedDateTime
(): string
(instant: Instant, zone: ZoneId): ZonedDateTime
(localDateTime: LocalDateTime, zone: ZoneId): ZonedDateTime
(str: string): ZonedDateTime throws TemporalParsingError
(x: ZonedDateTime, y: ZonedDateTime): number
(x: ZonedDateTime, y: ZonedDateTime): boolean