Skip to content

formatZonedToParts

formatZonedToParts(value: string, locale?: string | string[], options?: DateTimeFormatOptions): { type: string; value: string; }[]

Return the locale-formatted parts of a ZonedDateTime.

  • This is GMT’s substitute for a token formatter (Luxon toFormat, date-fns format). A token pattern hard-codes field order and ships US ordering to every locale; formatToParts gives the caller full control over presentation while the locale keeps control of order.
  • Each part is { type, value } where type can be: "era", "year", "relatedYear", "yearName", "month", "day", "weekday", "hour", "minute", "second", "fractionalSecond", "dayPeriod", "timeZoneName", "literal".
  • A lunisolar calendar adds two more: zh-u-ca-chinese and ko-u-ca-dangi emit "relatedYear" (the Gregorian year the cycle falls in) and "yearName" (the sexagenary cycle name) in place of, or beside, "year". Code that looks up a "year" part must handle their absence.
  • The caller should iterate the array as returned; reassembling in a fixed order reintroduces exactly the bug formatToParts exists to avoid.
  • With no date/time field and no dateStyle/timeStyle, year, month, day, hour, minute and second default to "numeric" and timeZoneName to "short" unless given (ECMA-402 as amended by Temporal). The parts, joined, are the text formatZonedDateTime returns for the same arguments before its whitespace normalisation.
  • A ZonedDateTime is formatted in its own zone: a timeZone option returns [], as ZonedDateTime#toLocaleString throws a TypeError for one.
  • The literal before the day period depends on the runtime. CLDR 42 (ICU 72) put U+202F NARROW NO-BREAK SPACE there for en-US; Node 22 and 24 return it in the parts, and Node 26 returns an ordinary space (U+0020) instead. Both were checked on those runtimes. The examples show the Node 22 and 24 form, written as "\u202f" so the difference is visible. Treat the two characters as equal when you compare parts.
  • Returns [] for invalid input.
  • Compatibility: before 1.16.0 a call with no field options returned only the date parts, with no time zone name. Pass { year: "numeric", month: "numeric", day: "numeric" } to keep that output. Before 1.16.0 a timeZone option re-rendered the instant in that zone; formatUtc with its timeZone option gives that text.
  • options null returns [], as ECMA-402’s CoerceOptionsToObject rejects it (a string or number options value formats with the defaults, as Intl.DateTimeFormat does).
ParameterTypeDescription
valuestringzoned ISO 8601 datetime string
localestring | string[]optional locale tag (e.g. “en-US”), or a preference list of tags (ECMA-402)

options

optional Intl.DateTimeFormatOptions

Type: DateTimeFormatOptions.

OptionTypeDefaultDescription
…Intl.DateTimeFormatOptions——Every field of DateTimeFormatOptions, as ECMA-402 defines it.

array of { type, value } parts, or [] on invalid input

Members of each item

MemberTypeDescription
typestringThe kind of part, named as ECMA-402 Intl.DateTimeFormat.prototype.formatToParts names it: a field such as "year", "month" or "day", or "literal" for the separator text between fields.
valuestringThe text of the part in the requested locale, exactly as the formatter wrote it. Joining every value in array order gives the whole formatted text.
import { formatZonedToParts } from "@northguild/gmt/zoned/format";
formatZonedToParts("2024-03-15T14:30:00.000-04:00[America/New_York]", "en-US") // [{ type: "month", value: "3" }, { type: "literal", value: "/" }, { type: "day", value: "15" }, { type: "literal", value: "/" }, { type: "year", value: "2024" }, { type: "literal", value: ", " }, { type: "hour", value: "2" }, { type: "literal", value: ":" }, { type: "minute", value: "30" }, { type: "literal", value: ":" }, { type: "second", value: "00" }, { type: "literal", value: "\u202f" }, { type: "dayPeriod", value: "PM" }, { type: "literal", value: " " }, { type: "timeZoneName", value: "EDT" }]
output 

zoned/format/formatZonedToParts.ts