@northguild/gmt 1.18.0 → 1.19.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (593) hide show
  1. package/README.md +55 -2920
  2. package/dist/calendar/calculate/bucketRange.d.ts +10 -2
  3. package/dist/calendar/calculate/bucketRange.js +18 -61
  4. package/dist/calendar/calculate/floorToZone.d.ts +10 -2
  5. package/dist/calendar/calculate/floorToZone.js +15 -7
  6. package/dist/calendar/hours/addOperatingTime.d.ts +6 -0
  7. package/dist/calendar/hours/addOperatingTime.js +7 -1
  8. package/dist/calendar/hours/isOpenAt.d.ts +6 -0
  9. package/dist/calendar/hours/isOpenAt.js +6 -0
  10. package/dist/calendar/hours/nextCloseAt.d.ts +6 -0
  11. package/dist/calendar/hours/nextCloseAt.js +7 -1
  12. package/dist/calendar/hours/nextOpenAt.d.ts +6 -0
  13. package/dist/calendar/hours/nextOpenAt.js +7 -1
  14. package/dist/calendar/hours/operatingIntervals.d.ts +5 -0
  15. package/dist/calendar/hours/operatingIntervals.js +5 -0
  16. package/dist/calendar/hours/operatingTimeBetween.d.ts +5 -0
  17. package/dist/calendar/hours/operatingTimeBetween.js +5 -0
  18. package/dist/calendar/hours/recurringWindows.d.ts +8 -1
  19. package/dist/calendar/hours/recurringWindows.js +12 -4
  20. package/dist/duration/calculate/durationFromUnits.d.ts +47 -0
  21. package/dist/duration/calculate/durationFromUnits.js +67 -0
  22. package/dist/duration/calculate/getDurationUnit.d.ts +2 -2
  23. package/dist/duration/calculate/getDurationUnit.js +2 -2
  24. package/dist/duration/calculate/index.d.ts +3 -1
  25. package/dist/duration/calculate/index.js +3 -1
  26. package/dist/duration/calculate/negateDuration.d.ts +1 -1
  27. package/dist/duration/calculate/negateDuration.js +1 -1
  28. package/dist/duration/calculate/{durationAs.d.ts → totalDuration.d.ts} +25 -19
  29. package/dist/duration/calculate/{durationAs.js → totalDuration.js} +25 -19
  30. package/dist/duration/calculate/totalUnits.d.ts +49 -0
  31. package/dist/duration/calculate/totalUnits.js +73 -0
  32. package/dist/duration/compare/compareDurations.d.ts +1 -1
  33. package/dist/duration/compare/compareDurations.js +1 -1
  34. package/dist/duty/calculate/dutyDayFor.d.ts +38 -0
  35. package/dist/duty/calculate/dutyDayFor.js +71 -0
  36. package/dist/duty/calculate/dutyTotals.d.ts +24 -0
  37. package/dist/duty/calculate/dutyTotals.js +41 -0
  38. package/dist/duty/calculate/dutyViolations.d.ts +74 -0
  39. package/dist/duty/calculate/dutyViolations.js +65 -0
  40. package/dist/duty/calculate/evaluateDutyLog.d.ts +77 -0
  41. package/dist/duty/calculate/evaluateDutyLog.js +75 -0
  42. package/dist/duty/calculate/index.d.ts +7 -0
  43. package/dist/duty/calculate/index.js +7 -0
  44. package/dist/duty/calculate/longestRun.d.ts +28 -0
  45. package/dist/duty/calculate/longestRun.js +54 -0
  46. package/dist/duty/calculate/qualifyingRestPairs.d.ts +37 -0
  47. package/dist/duty/calculate/qualifyingRestPairs.js +58 -0
  48. package/dist/duty/calculate/qualifyingRests.d.ts +27 -0
  49. package/dist/duty/calculate/qualifyingRests.js +49 -0
  50. package/dist/duty/index.d.ts +3 -0
  51. package/dist/duty/index.js +4 -0
  52. package/dist/duty/validate/index.d.ts +1 -0
  53. package/dist/duty/validate/index.js +1 -0
  54. package/dist/duty/validate/isValidDutyLog.d.ts +24 -0
  55. package/dist/duty/validate/isValidDutyLog.js +34 -0
  56. package/dist/index.d.ts +1 -0
  57. package/dist/index.js +1 -0
  58. package/dist/instant/convert/classifyLocal.d.ts +5 -1
  59. package/dist/instant/convert/classifyLocal.js +16 -6
  60. package/dist/instant/convert/fromOffsetInstant.d.ts +4 -0
  61. package/dist/instant/convert/fromOffsetInstant.js +6 -1
  62. package/dist/instant/convert/resolveLocal.d.ts +7 -2
  63. package/dist/instant/convert/resolveLocal.js +16 -8
  64. package/dist/instant/convert/toOffsetInstant.d.ts +12 -8
  65. package/dist/instant/convert/toOffsetInstant.js +19 -11
  66. package/dist/instant/index.d.ts +1 -0
  67. package/dist/instant/index.js +1 -0
  68. package/dist/instant/validate/index.d.ts +1 -0
  69. package/dist/instant/validate/index.js +1 -0
  70. package/dist/instant/validate/isValidUtcOffset.d.ts +32 -0
  71. package/dist/instant/validate/isValidUtcOffset.js +35 -0
  72. package/dist/intermodal/calculate/chargeableDays.d.ts +6 -0
  73. package/dist/intermodal/calculate/chargeableDays.js +12 -4
  74. package/dist/intermodal/calculate/freeTimeExpiry.d.ts +7 -0
  75. package/dist/intermodal/calculate/freeTimeExpiry.js +15 -4
  76. package/dist/intermodal/calculate/index.d.ts +1 -0
  77. package/dist/intermodal/calculate/index.js +1 -0
  78. package/dist/intermodal/calculate/multimodalETA.d.ts +76 -0
  79. package/dist/intermodal/calculate/multimodalETA.js +145 -0
  80. package/dist/intermodal/format/bolTimestamp.d.ts +76 -0
  81. package/dist/intermodal/format/bolTimestamp.js +78 -0
  82. package/dist/intermodal/format/formatEdifactDate.d.ts +34 -0
  83. package/dist/intermodal/format/formatEdifactDate.js +42 -0
  84. package/dist/intermodal/format/formatEdifactDatePeriod.d.ts +35 -0
  85. package/dist/intermodal/format/formatEdifactDatePeriod.js +43 -0
  86. package/dist/intermodal/format/formatEdifactDateTime.d.ts +37 -0
  87. package/dist/intermodal/format/formatEdifactDateTime.js +45 -0
  88. package/dist/intermodal/format/formatEdifactDateTimePeriod.d.ts +40 -0
  89. package/dist/intermodal/format/formatEdifactDateTimePeriod.js +48 -0
  90. package/dist/intermodal/format/formatEdifactOffsetDateTime.d.ts +62 -0
  91. package/dist/intermodal/format/formatEdifactOffsetDateTime.js +70 -0
  92. package/dist/intermodal/format/formatEdifactTime.d.ts +35 -0
  93. package/dist/intermodal/format/formatEdifactTime.js +43 -0
  94. package/dist/intermodal/format/formatEpcisEvent.d.ts +47 -0
  95. package/dist/intermodal/format/formatEpcisEvent.js +79 -0
  96. package/dist/intermodal/format/formatX12Date.d.ts +35 -0
  97. package/dist/intermodal/format/formatX12Date.js +43 -0
  98. package/dist/intermodal/format/formatX12DateRange.d.ts +37 -0
  99. package/dist/intermodal/format/formatX12DateRange.js +45 -0
  100. package/dist/intermodal/format/formatX12DateTime.d.ts +39 -0
  101. package/dist/intermodal/format/formatX12DateTime.js +47 -0
  102. package/dist/intermodal/format/formatX12DateTimeRange.d.ts +40 -0
  103. package/dist/intermodal/format/formatX12DateTimeRange.js +48 -0
  104. package/dist/intermodal/format/formatX12Time.d.ts +42 -0
  105. package/dist/intermodal/format/formatX12Time.js +50 -0
  106. package/dist/intermodal/format/formatX12TimeElement.d.ts +46 -0
  107. package/dist/intermodal/format/formatX12TimeElement.js +54 -0
  108. package/dist/intermodal/format/index.d.ts +14 -0
  109. package/dist/intermodal/format/index.js +14 -0
  110. package/dist/intermodal/index.d.ts +3 -0
  111. package/dist/intermodal/index.js +3 -0
  112. package/dist/intermodal/parse/classifyEdifactDtmFormat.d.ts +48 -0
  113. package/dist/intermodal/parse/classifyEdifactDtmFormat.js +55 -0
  114. package/dist/intermodal/parse/classifyX12DateTimePeriodFormat.d.ts +50 -0
  115. package/dist/intermodal/parse/classifyX12DateTimePeriodFormat.js +57 -0
  116. package/dist/intermodal/parse/classifyX12TimeCode.d.ts +46 -0
  117. package/dist/intermodal/parse/classifyX12TimeCode.js +57 -0
  118. package/dist/intermodal/parse/index.d.ts +18 -0
  119. package/dist/intermodal/parse/index.js +18 -0
  120. package/dist/intermodal/parse/parseEdifactDate.d.ts +37 -0
  121. package/dist/intermodal/parse/parseEdifactDate.js +45 -0
  122. package/dist/intermodal/parse/parseEdifactDatePeriod.d.ts +43 -0
  123. package/dist/intermodal/parse/parseEdifactDatePeriod.js +51 -0
  124. package/dist/intermodal/parse/parseEdifactDateTime.d.ts +43 -0
  125. package/dist/intermodal/parse/parseEdifactDateTime.js +51 -0
  126. package/dist/intermodal/parse/parseEdifactDateTimePeriod.d.ts +45 -0
  127. package/dist/intermodal/parse/parseEdifactDateTimePeriod.js +53 -0
  128. package/dist/intermodal/parse/parseEdifactOffsetDateTime.d.ts +60 -0
  129. package/dist/intermodal/parse/parseEdifactOffsetDateTime.js +68 -0
  130. package/dist/intermodal/parse/parseEdifactTime.d.ts +37 -0
  131. package/dist/intermodal/parse/parseEdifactTime.js +45 -0
  132. package/dist/intermodal/parse/parseEpcisEvent.d.ts +95 -0
  133. package/dist/intermodal/parse/parseEpcisEvent.js +102 -0
  134. package/dist/intermodal/parse/parseX12Date.d.ts +39 -0
  135. package/dist/intermodal/parse/parseX12Date.js +47 -0
  136. package/dist/intermodal/parse/parseX12DateAndTime.d.ts +52 -0
  137. package/dist/intermodal/parse/parseX12DateAndTime.js +61 -0
  138. package/dist/intermodal/parse/parseX12DateRange.d.ts +44 -0
  139. package/dist/intermodal/parse/parseX12DateRange.js +52 -0
  140. package/dist/intermodal/parse/parseX12DateTime.d.ts +45 -0
  141. package/dist/intermodal/parse/parseX12DateTime.js +53 -0
  142. package/dist/intermodal/parse/parseX12DateTimeRange.d.ts +46 -0
  143. package/dist/intermodal/parse/parseX12DateTimeRange.js +54 -0
  144. package/dist/intermodal/parse/parseX12Time.d.ts +65 -0
  145. package/dist/intermodal/parse/parseX12Time.js +77 -0
  146. package/dist/intermodal/parse/x12TimeCodeOffset.d.ts +57 -0
  147. package/dist/intermodal/parse/x12TimeCodeOffset.js +110 -0
  148. package/dist/intermodal/parse/x12TimeCodeZone.d.ts +57 -0
  149. package/dist/intermodal/parse/x12TimeCodeZone.js +105 -0
  150. package/dist/intermodal/validate/index.d.ts +18 -0
  151. package/dist/intermodal/validate/index.js +18 -0
  152. package/dist/intermodal/validate/isValidEdifactDate.d.ts +26 -0
  153. package/dist/intermodal/validate/isValidEdifactDate.js +28 -0
  154. package/dist/intermodal/validate/isValidEdifactDatePeriod.d.ts +28 -0
  155. package/dist/intermodal/validate/isValidEdifactDatePeriod.js +30 -0
  156. package/dist/intermodal/validate/isValidEdifactDateTime.d.ts +30 -0
  157. package/dist/intermodal/validate/isValidEdifactDateTime.js +32 -0
  158. package/dist/intermodal/validate/isValidEdifactDateTimePeriod.d.ts +28 -0
  159. package/dist/intermodal/validate/isValidEdifactDateTimePeriod.js +30 -0
  160. package/dist/intermodal/validate/isValidEdifactDtmFormat.d.ts +39 -0
  161. package/dist/intermodal/validate/isValidEdifactDtmFormat.js +42 -0
  162. package/dist/intermodal/validate/isValidEdifactOffsetDateTime.d.ts +36 -0
  163. package/dist/intermodal/validate/isValidEdifactOffsetDateTime.js +38 -0
  164. package/dist/intermodal/validate/isValidEdifactTime.d.ts +28 -0
  165. package/dist/intermodal/validate/isValidEdifactTime.js +30 -0
  166. package/dist/intermodal/validate/isValidEpcisEvent.d.ts +41 -0
  167. package/dist/intermodal/validate/isValidEpcisEvent.js +58 -0
  168. package/dist/intermodal/validate/isValidEpcisEventTime.d.ts +33 -0
  169. package/dist/intermodal/validate/isValidEpcisEventTime.js +48 -0
  170. package/dist/intermodal/validate/isValidEpcisTimeZoneOffset.d.ts +30 -0
  171. package/dist/intermodal/validate/isValidEpcisTimeZoneOffset.js +38 -0
  172. package/dist/intermodal/validate/isValidX12Date.d.ts +28 -0
  173. package/dist/intermodal/validate/isValidX12Date.js +30 -0
  174. package/dist/intermodal/validate/isValidX12DateAndTime.d.ts +32 -0
  175. package/dist/intermodal/validate/isValidX12DateAndTime.js +35 -0
  176. package/dist/intermodal/validate/isValidX12DateRange.d.ts +29 -0
  177. package/dist/intermodal/validate/isValidX12DateRange.js +31 -0
  178. package/dist/intermodal/validate/isValidX12DateTime.d.ts +30 -0
  179. package/dist/intermodal/validate/isValidX12DateTime.js +32 -0
  180. package/dist/intermodal/validate/isValidX12DateTimePeriodFormat.d.ts +43 -0
  181. package/dist/intermodal/validate/isValidX12DateTimePeriodFormat.js +46 -0
  182. package/dist/intermodal/validate/isValidX12DateTimeRange.d.ts +31 -0
  183. package/dist/intermodal/validate/isValidX12DateTimeRange.js +33 -0
  184. package/dist/intermodal/validate/isValidX12Time.d.ts +38 -0
  185. package/dist/intermodal/validate/isValidX12Time.js +40 -0
  186. package/dist/intermodal/validate/isValidX12TimeCode.d.ts +38 -0
  187. package/dist/intermodal/validate/isValidX12TimeCode.js +41 -0
  188. package/dist/internal/businessCalendar.js +4 -9
  189. package/dist/internal/dutyEngine.d.ts +125 -0
  190. package/dist/internal/dutyEngine.js +1746 -0
  191. package/dist/internal/dutyLog.d.ts +27 -0
  192. package/dist/internal/dutyLog.js +47 -0
  193. package/dist/internal/dutyPeriods.d.ts +135 -0
  194. package/dist/internal/dutyPeriods.js +369 -0
  195. package/dist/internal/dutyRules.d.ts +197 -0
  196. package/dist/internal/dutyRules.js +484 -0
  197. package/dist/internal/ediDateTimeFields.d.ts +97 -0
  198. package/dist/internal/ediDateTimeFields.js +288 -0
  199. package/dist/internal/ediDateTimeWriter.d.ts +92 -0
  200. package/dist/internal/ediDateTimeWriter.js +298 -0
  201. package/dist/internal/ediGrammar.d.ts +158 -0
  202. package/dist/internal/ediGrammar.js +384 -0
  203. package/dist/internal/englishCalendarNames.d.ts +3 -1
  204. package/dist/internal/englishCalendarNames.js +3 -1
  205. package/dist/internal/freeTimeLedger.d.ts +5 -0
  206. package/dist/internal/freeTimeLedger.js +11 -2
  207. package/dist/internal/index.d.ts +5 -2
  208. package/dist/internal/index.js +9 -2
  209. package/dist/internal/intervalNanoseconds.js +2 -1
  210. package/dist/internal/isObject.d.ts +13 -6
  211. package/dist/internal/isObject.js +14 -7
  212. package/dist/internal/isoYearString.d.ts +21 -0
  213. package/dist/internal/isoYearString.js +27 -0
  214. package/dist/internal/maxPieces.js +2 -1
  215. package/dist/internal/normalizeTimeZone.d.ts +4 -1
  216. package/dist/internal/normalizeTimeZone.js +4 -1
  217. package/dist/internal/operatingSchedule.d.ts +13 -4
  218. package/dist/internal/operatingSchedule.js +146 -58
  219. package/dist/internal/patternToken.d.ts +10 -3
  220. package/dist/internal/patternToken.js +31 -12
  221. package/dist/internal/readDurationUnits.d.ts +34 -0
  222. package/dist/internal/readDurationUnits.js +78 -0
  223. package/dist/internal/readSetFields.d.ts +50 -0
  224. package/dist/internal/readSetFields.js +179 -0
  225. package/dist/internal/resolveRelativeUnit.d.ts +1 -1
  226. package/dist/internal/resolveRelativeUnit.js +1 -1
  227. package/dist/internal/resolveUnixIntervalPair.d.ts +8 -2
  228. package/dist/internal/resolveUnixIntervalPair.js +11 -7
  229. package/dist/internal/startOrEndOfUnix.d.ts +2 -1
  230. package/dist/internal/startOrEndOfUnix.js +9 -6
  231. package/dist/internal/twoDigitYear.d.ts +19 -0
  232. package/dist/internal/twoDigitYear.js +22 -0
  233. package/dist/internal/unixEpochValue.js +3 -2
  234. package/dist/internal/unixWallClock.d.ts +24 -0
  235. package/dist/internal/unixWallClock.js +35 -0
  236. package/dist/internal/utcWallClock.d.ts +20 -0
  237. package/dist/internal/utcWallClock.js +32 -0
  238. package/dist/internal/yearWindowStart.d.ts +28 -0
  239. package/dist/internal/yearWindowStart.js +52 -0
  240. package/dist/internal/zoneBucketCap.d.ts +18 -0
  241. package/dist/internal/zoneBucketCap.js +64 -0
  242. package/dist/internal/zoneFrame.d.ts +180 -0
  243. package/dist/internal/zoneFrame.js +221 -0
  244. package/dist/internal/zonedNowUnitValue.d.ts +7 -4
  245. package/dist/internal/zonedNowUnitValue.js +8 -4
  246. package/dist/internal/zonedWallClockDifference.js +4 -4
  247. package/dist/internal/zonedWallClockOperations.d.ts +5 -2
  248. package/dist/internal/zonedWallClockOperations.js +7 -10
  249. package/dist/plain/calculate/addDate.js +4 -7
  250. package/dist/plain/calculate/addDateTime.js +4 -7
  251. package/dist/plain/calculate/addTime.js +4 -7
  252. package/dist/plain/calculate/endOfTime.d.ts +1 -1
  253. package/dist/plain/calculate/setDate.d.ts +20 -3
  254. package/dist/plain/calculate/setDate.js +27 -7
  255. package/dist/plain/calculate/setDateTime.d.ts +15 -3
  256. package/dist/plain/calculate/setDateTime.js +22 -7
  257. package/dist/plain/calculate/setTime.d.ts +13 -1
  258. package/dist/plain/calculate/setTime.js +21 -6
  259. package/dist/plain/calculate/startOfTime.d.ts +1 -1
  260. package/dist/plain/calculate/subtractDate.js +4 -7
  261. package/dist/plain/calculate/subtractDateTime.js +4 -7
  262. package/dist/plain/calculate/subtractTime.js +4 -7
  263. package/dist/plain/format/formatCalendar.js +2 -1
  264. package/dist/plain/format/formatRelativeDate.js +2 -1
  265. package/dist/plain/format/formatRelativeDateTime.js +2 -1
  266. package/dist/plain/format/formatRelativeTime.js +2 -1
  267. package/dist/plain/format/{formatSql.d.ts → formatSqlDateTime.d.ts} +7 -7
  268. package/dist/plain/format/{formatSql.js → formatSqlDateTime.js} +7 -7
  269. package/dist/plain/format/index.d.ts +1 -1
  270. package/dist/plain/format/index.js +1 -1
  271. package/dist/plain/get/getNowUnit.d.ts +2 -0
  272. package/dist/plain/get/getNowUnit.js +2 -0
  273. package/dist/plain/get/getYear.d.ts +2 -0
  274. package/dist/plain/get/getYear.js +4 -3
  275. package/dist/plain/interval/intervalXorAllDate.js +2 -2
  276. package/dist/plain/interval/intervalXorAllDateTime.js +2 -2
  277. package/dist/plain/interval/intervalXorAllTime.js +2 -2
  278. package/dist/plain/interval/mergeIntervalsDate.js +2 -2
  279. package/dist/plain/interval/mergeIntervalsDateTime.js +2 -2
  280. package/dist/plain/interval/mergeIntervalsTime.js +2 -2
  281. package/dist/plain/parse/index.d.ts +1 -1
  282. package/dist/plain/parse/index.js +1 -1
  283. package/dist/plain/parse/parseDateTimeWithPattern.d.ts +16 -3
  284. package/dist/plain/parse/parseDateTimeWithPattern.js +20 -5
  285. package/dist/plain/parse/parseDateWithPattern.d.ts +17 -3
  286. package/dist/plain/parse/parseDateWithPattern.js +21 -5
  287. package/dist/plain/parse/{parseSql.d.ts → parseSqlDateTime.d.ts} +8 -8
  288. package/dist/plain/parse/{parseSql.js → parseSqlDateTime.js} +8 -8
  289. package/dist/plain/parse/parseTimeWithPattern.js +1 -0
  290. package/dist/plain/parse/parseUnitFromDate.d.ts +3 -0
  291. package/dist/plain/parse/parseUnitFromDate.js +5 -1
  292. package/dist/plain/parse/parseUnitFromDateTime.d.ts +3 -0
  293. package/dist/plain/parse/parseUnitFromDateTime.js +5 -1
  294. package/dist/plain/parse/parseYearFromDate.d.ts +5 -2
  295. package/dist/plain/parse/parseYearFromDate.js +7 -3
  296. package/dist/plain/parse/parseYearFromDateTime.d.ts +4 -2
  297. package/dist/plain/parse/parseYearFromDateTime.js +6 -3
  298. package/dist/plain/validate/index.d.ts +1 -0
  299. package/dist/plain/validate/index.js +1 -0
  300. package/dist/plain/validate/isValidSqlDateTime.d.ts +33 -0
  301. package/dist/plain/validate/isValidSqlDateTime.js +36 -0
  302. package/dist/precision/convert/fromNanoseconds.d.ts +9 -3
  303. package/dist/precision/convert/fromNanoseconds.js +9 -3
  304. package/dist/regex/epcis.d.ts +60 -0
  305. package/dist/regex/epcis.js +60 -0
  306. package/dist/regex/http-date.d.ts +6 -4
  307. package/dist/regex/http-date.js +6 -4
  308. package/dist/regex/index.d.ts +1 -0
  309. package/dist/regex/index.js +1 -0
  310. package/dist/regex/rfc-2822.d.ts +2 -0
  311. package/dist/regex/rfc-2822.js +2 -0
  312. package/dist/regex/rfc-3339.d.ts +3 -1
  313. package/dist/regex/rfc-3339.js +3 -1
  314. package/dist/regex/sql-date-time.d.ts +2 -1
  315. package/dist/regex/sql-date-time.js +2 -1
  316. package/dist/regex/time-zone-like.d.ts +3 -2
  317. package/dist/regex/time-zone-like.js +3 -2
  318. package/dist/regex/utc-offset.d.ts +2 -1
  319. package/dist/regex/utc-offset.js +2 -1
  320. package/dist/transport/calculate/crossingTime.d.ts +6 -1
  321. package/dist/transport/calculate/crossingTime.js +6 -1
  322. package/dist/transport/calculate/cutoffAt.d.ts +6 -1
  323. package/dist/transport/calculate/cutoffAt.js +2 -0
  324. package/dist/transport/calculate/cutoffSchedule.d.ts +6 -1
  325. package/dist/transport/calculate/cutoffSchedule.js +2 -0
  326. package/dist/transport/calculate/dwellTime.d.ts +6 -1
  327. package/dist/transport/calculate/dwellTime.js +6 -1
  328. package/dist/transport/calculate/scheduleDelivery.d.ts +13 -5
  329. package/dist/transport/calculate/scheduleDelivery.js +6 -1
  330. package/dist/transport/convert/etaAtZone.d.ts +6 -1
  331. package/dist/transport/convert/etaAtZone.js +6 -1
  332. package/dist/types/business-calendar.d.ts +5 -4
  333. package/dist/types/duty.d.ts +777 -0
  334. package/dist/types/duty.js +0 -0
  335. package/dist/types/edi.d.ts +407 -0
  336. package/dist/types/edi.js +0 -0
  337. package/dist/types/epcis.d.ts +25 -0
  338. package/dist/types/epcis.js +0 -0
  339. package/dist/types/exact-duration-unit.d.ts +8 -0
  340. package/dist/types/exact-duration-unit.js +0 -0
  341. package/dist/types/free-time-options.d.ts +4 -3
  342. package/dist/types/index.d.ts +5 -0
  343. package/dist/types/index.js +5 -0
  344. package/dist/types/operating-schedule.d.ts +3 -2
  345. package/dist/types/two-digit-year.d.ts +23 -0
  346. package/dist/types/two-digit-year.js +0 -0
  347. package/dist/types/zone-bucket-unit.d.ts +1 -1
  348. package/dist/unix/calculate/addUnix.d.ts +11 -2
  349. package/dist/unix/calculate/addUnix.js +14 -11
  350. package/dist/unix/calculate/diffUnix.d.ts +10 -2
  351. package/dist/unix/calculate/diffUnix.js +11 -6
  352. package/dist/unix/calculate/diffUnixAsDuration.d.ts +10 -2
  353. package/dist/unix/calculate/diffUnixAsDuration.js +10 -5
  354. package/dist/unix/calculate/endOfQuarterForUnix.d.ts +10 -2
  355. package/dist/unix/calculate/endOfQuarterForUnix.js +6 -0
  356. package/dist/unix/calculate/endOfUnix.d.ts +11 -2
  357. package/dist/unix/calculate/endOfUnix.js +7 -0
  358. package/dist/unix/calculate/isBetweenUnix.d.ts +3 -2
  359. package/dist/unix/calculate/isBetweenUnix.js +3 -3
  360. package/dist/unix/calculate/roundUnix.d.ts +10 -2
  361. package/dist/unix/calculate/roundUnix.js +13 -6
  362. package/dist/unix/calculate/setUnix.d.ts +25 -5
  363. package/dist/unix/calculate/setUnix.js +33 -12
  364. package/dist/unix/calculate/startOfQuarterForUnix.d.ts +10 -2
  365. package/dist/unix/calculate/startOfQuarterForUnix.js +6 -0
  366. package/dist/unix/calculate/startOfUnix.d.ts +11 -2
  367. package/dist/unix/calculate/startOfUnix.js +7 -0
  368. package/dist/unix/calculate/subtractUnix.d.ts +10 -2
  369. package/dist/unix/calculate/subtractUnix.js +13 -11
  370. package/dist/unix/compare/areUnixEqualBy.d.ts +11 -2
  371. package/dist/unix/compare/areUnixEqualBy.js +7 -0
  372. package/dist/unix/convert/convertUnixToPlainDate.d.ts +5 -2
  373. package/dist/unix/convert/convertUnixToPlainDate.js +5 -4
  374. package/dist/unix/convert/convertUnixToPlainDateTime.d.ts +5 -2
  375. package/dist/unix/convert/convertUnixToPlainDateTime.js +5 -4
  376. package/dist/unix/convert/convertUnixToPlainTime.d.ts +5 -2
  377. package/dist/unix/convert/convertUnixToPlainTime.js +5 -4
  378. package/dist/unix/convert/convertUnixToZoned.d.ts +5 -1
  379. package/dist/unix/convert/convertUnixToZoned.js +5 -1
  380. package/dist/unix/format/formatCalendarUnix.d.ts +6 -2
  381. package/dist/unix/format/formatCalendarUnix.js +6 -1
  382. package/dist/unix/format/formatRelativeUnix.d.ts +11 -3
  383. package/dist/unix/format/formatRelativeUnix.js +13 -5
  384. package/dist/unix/format/formatUnix.d.ts +7 -2
  385. package/dist/unix/format/formatUnix.js +4 -0
  386. package/dist/unix/get/getUnixDay.d.ts +1 -3
  387. package/dist/unix/get/getUnixDay.js +5 -12
  388. package/dist/unix/get/getUnixHour.d.ts +1 -3
  389. package/dist/unix/get/getUnixHour.js +5 -12
  390. package/dist/unix/get/getUnixMicrosecond.d.ts +1 -3
  391. package/dist/unix/get/getUnixMicrosecond.js +4 -11
  392. package/dist/unix/get/getUnixMillisecond.d.ts +1 -3
  393. package/dist/unix/get/getUnixMillisecond.js +5 -12
  394. package/dist/unix/get/getUnixMinute.d.ts +1 -3
  395. package/dist/unix/get/getUnixMinute.js +5 -12
  396. package/dist/unix/get/getUnixMonth.d.ts +1 -3
  397. package/dist/unix/get/getUnixMonth.js +5 -12
  398. package/dist/unix/get/getUnixNanosecond.d.ts +1 -3
  399. package/dist/unix/get/getUnixNanosecond.js +4 -11
  400. package/dist/unix/get/getUnixNowUnit.d.ts +2 -0
  401. package/dist/unix/get/getUnixNowUnit.js +2 -0
  402. package/dist/unix/get/getUnixSecond.d.ts +1 -3
  403. package/dist/unix/get/getUnixSecond.js +5 -12
  404. package/dist/unix/get/getUnixYear.d.ts +3 -3
  405. package/dist/unix/get/getUnixYear.js +5 -12
  406. package/dist/unix/interval/intervalCountUnix.d.ts +11 -2
  407. package/dist/unix/interval/intervalCountUnix.js +7 -0
  408. package/dist/unix/interval/intervalFromDurationUnix.d.ts +10 -2
  409. package/dist/unix/interval/intervalFromDurationUnix.js +12 -7
  410. package/dist/unix/interval/intervalLengthUnix.d.ts +10 -2
  411. package/dist/unix/interval/intervalLengthUnix.js +6 -0
  412. package/dist/unix/interval/intervalOverlappingDaysUnix.d.ts +10 -2
  413. package/dist/unix/interval/intervalOverlappingDaysUnix.js +10 -5
  414. package/dist/unix/interval/splitIntervalByUnitUnix.d.ts +10 -2
  415. package/dist/unix/interval/splitIntervalByUnitUnix.js +12 -6
  416. package/dist/unix/parse/parseDateFromUnix.d.ts +4 -2
  417. package/dist/unix/parse/parseDateFromUnix.js +3 -3
  418. package/dist/unix/parse/parseDayFromUnix.d.ts +4 -2
  419. package/dist/unix/parse/parseDayOfWeekFromUnix.d.ts +4 -2
  420. package/dist/unix/parse/parseDayOfWeekFromUnix.js +2 -2
  421. package/dist/unix/parse/parseHourFromUnix.d.ts +4 -2
  422. package/dist/unix/parse/parseMicrosecondFromUnix.d.ts +4 -2
  423. package/dist/unix/parse/parseMillisecondFromUnix.d.ts +4 -2
  424. package/dist/unix/parse/parseMinuteFromUnix.d.ts +4 -2
  425. package/dist/unix/parse/parseMonthFromUnix.d.ts +4 -2
  426. package/dist/unix/parse/parseNanosecondFromUnix.d.ts +4 -2
  427. package/dist/unix/parse/parseSecondFromUnix.d.ts +4 -2
  428. package/dist/unix/parse/parseTimeFromUnix.d.ts +5 -2
  429. package/dist/unix/parse/parseTimeFromUnix.js +4 -3
  430. package/dist/unix/parse/parseUnitFromUnix.d.ts +9 -3
  431. package/dist/unix/parse/parseUnitFromUnix.js +21 -14
  432. package/dist/unix/parse/parseWeekFromUnix.d.ts +3 -2
  433. package/dist/unix/parse/parseWeekFromUnix.js +4 -4
  434. package/dist/unix/parse/parseYearFromUnix.d.ts +8 -3
  435. package/dist/unix/parse/parseYearFromUnix.js +4 -1
  436. package/dist/unix/validate/isValidUnixUnit.d.ts +1 -1
  437. package/dist/utc/calculate/addUtc.js +4 -7
  438. package/dist/utc/calculate/setUtc.d.ts +16 -3
  439. package/dist/utc/calculate/setUtc.js +22 -8
  440. package/dist/utc/calculate/subtractUtc.js +4 -7
  441. package/dist/utc/convert/convertUtcToPlainDate.d.ts +8 -2
  442. package/dist/utc/convert/convertUtcToPlainDate.js +10 -7
  443. package/dist/utc/convert/convertUtcToPlainDateTime.d.ts +9 -2
  444. package/dist/utc/convert/convertUtcToPlainDateTime.js +12 -13
  445. package/dist/utc/convert/convertUtcToPlainTime.d.ts +5 -2
  446. package/dist/utc/convert/convertUtcToPlainTime.js +7 -6
  447. package/dist/utc/convert/convertUtcToZoned.d.ts +5 -1
  448. package/dist/utc/convert/convertUtcToZoned.js +5 -1
  449. package/dist/utc/format/formatCalendarUtc.d.ts +6 -2
  450. package/dist/utc/format/formatCalendarUtc.js +6 -1
  451. package/dist/utc/format/{formatHttp.d.ts → formatHttpDate.d.ts} +7 -7
  452. package/dist/utc/format/{formatHttp.js → formatHttpDate.js} +7 -7
  453. package/dist/utc/format/formatRelativeUtc.d.ts +11 -3
  454. package/dist/utc/format/formatRelativeUtc.js +13 -5
  455. package/dist/utc/format/formatUtc.d.ts +7 -2
  456. package/dist/utc/format/formatUtc.js +4 -0
  457. package/dist/utc/format/index.d.ts +1 -1
  458. package/dist/utc/format/index.js +1 -1
  459. package/dist/utc/get/getUtcDay.d.ts +1 -3
  460. package/dist/utc/get/getUtcDay.js +5 -12
  461. package/dist/utc/get/getUtcHour.d.ts +1 -3
  462. package/dist/utc/get/getUtcHour.js +5 -12
  463. package/dist/utc/get/getUtcMicrosecond.d.ts +1 -3
  464. package/dist/utc/get/getUtcMicrosecond.js +4 -11
  465. package/dist/utc/get/getUtcMillisecond.d.ts +1 -3
  466. package/dist/utc/get/getUtcMillisecond.js +5 -12
  467. package/dist/utc/get/getUtcMinute.d.ts +1 -3
  468. package/dist/utc/get/getUtcMinute.js +5 -12
  469. package/dist/utc/get/getUtcMonth.d.ts +1 -3
  470. package/dist/utc/get/getUtcMonth.js +5 -12
  471. package/dist/utc/get/getUtcNanosecond.d.ts +1 -3
  472. package/dist/utc/get/getUtcNanosecond.js +4 -11
  473. package/dist/utc/get/getUtcNow.d.ts +1 -3
  474. package/dist/utc/get/getUtcNow.js +2 -9
  475. package/dist/utc/get/getUtcNowUnit.d.ts +2 -0
  476. package/dist/utc/get/getUtcNowUnit.js +2 -0
  477. package/dist/utc/get/getUtcSecond.d.ts +1 -3
  478. package/dist/utc/get/getUtcSecond.js +5 -12
  479. package/dist/utc/get/getUtcYear.d.ts +3 -3
  480. package/dist/utc/get/getUtcYear.js +5 -12
  481. package/dist/utc/interval/intervalXorAllUtc.js +2 -2
  482. package/dist/utc/interval/mergeIntervalsUtc.js +2 -2
  483. package/dist/utc/parse/index.d.ts +1 -1
  484. package/dist/utc/parse/index.js +1 -1
  485. package/dist/utc/parse/parseDateFromUtc.d.ts +4 -2
  486. package/dist/utc/parse/parseDateFromUtc.js +2 -2
  487. package/dist/utc/parse/parseDayFromUtc.d.ts +4 -2
  488. package/dist/utc/parse/parseDayFromUtc.js +2 -2
  489. package/dist/utc/parse/parseDayOfWeekFromUtc.d.ts +4 -2
  490. package/dist/utc/parse/parseDayOfWeekFromUtc.js +4 -4
  491. package/dist/utc/parse/parseHourFromUtc.d.ts +4 -2
  492. package/dist/utc/parse/parseHourFromUtc.js +2 -2
  493. package/dist/utc/parse/{parseHttp.d.ts → parseHttpDate.d.ts} +12 -12
  494. package/dist/utc/parse/{parseHttp.js → parseHttpDate.js} +12 -12
  495. package/dist/utc/parse/parseMicrosecondFromUtc.d.ts +4 -2
  496. package/dist/utc/parse/parseMicrosecondFromUtc.js +2 -2
  497. package/dist/utc/parse/parseMillisecondFromUtc.d.ts +4 -2
  498. package/dist/utc/parse/parseMillisecondFromUtc.js +2 -2
  499. package/dist/utc/parse/parseMinuteFromUtc.d.ts +4 -2
  500. package/dist/utc/parse/parseMinuteFromUtc.js +2 -2
  501. package/dist/utc/parse/parseMonthFromUtc.d.ts +4 -2
  502. package/dist/utc/parse/parseMonthFromUtc.js +2 -2
  503. package/dist/utc/parse/parseNanosecondFromUtc.d.ts +4 -2
  504. package/dist/utc/parse/parseNanosecondFromUtc.js +2 -2
  505. package/dist/utc/parse/parseSecondFromUtc.d.ts +4 -2
  506. package/dist/utc/parse/parseSecondFromUtc.js +2 -2
  507. package/dist/utc/parse/parseTimeFromUtc.d.ts +5 -2
  508. package/dist/utc/parse/parseTimeFromUtc.js +5 -4
  509. package/dist/utc/parse/parseUnitFromUtc.d.ts +10 -3
  510. package/dist/utc/parse/parseUnitFromUtc.js +11 -5
  511. package/dist/utc/parse/parseWeekFromUtc.d.ts +4 -2
  512. package/dist/utc/parse/parseWeekFromUtc.js +4 -4
  513. package/dist/utc/parse/parseYearFromUtc.d.ts +8 -4
  514. package/dist/utc/parse/parseYearFromUtc.js +8 -5
  515. package/dist/utc/validate/index.d.ts +2 -0
  516. package/dist/utc/validate/index.js +2 -0
  517. package/dist/utc/validate/isValidHttpDate.d.ts +35 -0
  518. package/dist/utc/validate/isValidHttpDate.js +38 -0
  519. package/dist/utc/validate/isValidUtc.d.ts +4 -0
  520. package/dist/utc/validate/isValidUtc.js +4 -0
  521. package/dist/utc/validate/isValidUtcTimestamp.d.ts +43 -0
  522. package/dist/utc/validate/isValidUtcTimestamp.js +48 -0
  523. package/dist/zoned/calculate/addZoned.js +4 -7
  524. package/dist/zoned/calculate/setZoned.d.ts +19 -5
  525. package/dist/zoned/calculate/setZoned.js +26 -9
  526. package/dist/zoned/calculate/subtractZoned.js +4 -7
  527. package/dist/zoned/convert/convertPlainDateTimeToZoned.d.ts +4 -1
  528. package/dist/zoned/convert/convertPlainDateTimeToZoned.js +4 -1
  529. package/dist/zoned/convert/convertZonedToZoned.d.ts +5 -1
  530. package/dist/zoned/convert/convertZonedToZoned.js +5 -1
  531. package/dist/zoned/format/formatCalendarZoned.js +2 -1
  532. package/dist/zoned/format/formatRelativeZoned.js +2 -1
  533. package/dist/zoned/format/formatTimeZoneName.d.ts +5 -1
  534. package/dist/zoned/format/formatTimeZoneName.js +5 -1
  535. package/dist/zoned/get/getDstTransitions.d.ts +5 -3
  536. package/dist/zoned/get/getDstTransitions.js +12 -7
  537. package/dist/zoned/get/getSystemTimeZone.d.ts +3 -1
  538. package/dist/zoned/get/getSystemTimeZone.js +5 -2
  539. package/dist/zoned/get/getTimeZoneOffset.d.ts +10 -2
  540. package/dist/zoned/get/getTimeZoneOffset.js +18 -5
  541. package/dist/zoned/get/getZonedDay.d.ts +2 -1
  542. package/dist/zoned/get/getZonedDay.js +6 -7
  543. package/dist/zoned/get/getZonedDayOfWeek.d.ts +2 -1
  544. package/dist/zoned/get/getZonedDayOfWeek.js +6 -5
  545. package/dist/zoned/get/getZonedHour.d.ts +2 -1
  546. package/dist/zoned/get/getZonedHour.js +6 -7
  547. package/dist/zoned/get/getZonedMicrosecond.d.ts +2 -1
  548. package/dist/zoned/get/getZonedMicrosecond.js +6 -5
  549. package/dist/zoned/get/getZonedMillisecond.d.ts +2 -1
  550. package/dist/zoned/get/getZonedMillisecond.js +6 -7
  551. package/dist/zoned/get/getZonedMinute.d.ts +2 -1
  552. package/dist/zoned/get/getZonedMinute.js +6 -7
  553. package/dist/zoned/get/getZonedMonth.d.ts +2 -1
  554. package/dist/zoned/get/getZonedMonth.js +6 -7
  555. package/dist/zoned/get/getZonedNanosecond.d.ts +2 -1
  556. package/dist/zoned/get/getZonedNanosecond.js +6 -5
  557. package/dist/zoned/get/getZonedNow.d.ts +5 -1
  558. package/dist/zoned/get/getZonedNow.js +5 -1
  559. package/dist/zoned/get/getZonedNowUnit.d.ts +6 -3
  560. package/dist/zoned/get/getZonedNowUnit.js +10 -7
  561. package/dist/zoned/get/getZonedSecond.d.ts +2 -1
  562. package/dist/zoned/get/getZonedSecond.js +6 -7
  563. package/dist/zoned/get/getZonedToday.d.ts +2 -1
  564. package/dist/zoned/get/getZonedToday.js +6 -5
  565. package/dist/zoned/get/getZonedWeekOfYear.d.ts +2 -1
  566. package/dist/zoned/get/getZonedWeekOfYear.js +6 -5
  567. package/dist/zoned/get/getZonedYear.d.ts +4 -1
  568. package/dist/zoned/get/getZonedYear.js +9 -7
  569. package/dist/zoned/interval/intervalXorAllZoned.js +2 -2
  570. package/dist/zoned/interval/mergeIntervalsZoned.js +2 -2
  571. package/dist/zoned/parse/parseUnitFromZoned.d.ts +4 -1
  572. package/dist/zoned/parse/parseUnitFromZoned.js +5 -1
  573. package/dist/zoned/parse/parseYearFromZoned.d.ts +4 -2
  574. package/dist/zoned/parse/parseYearFromZoned.js +6 -3
  575. package/dist/zoned/validate/hasDaylightSaving.d.ts +4 -2
  576. package/dist/zoned/validate/hasDaylightSaving.js +13 -7
  577. package/dist/zoned/validate/index.d.ts +2 -0
  578. package/dist/zoned/validate/index.js +2 -0
  579. package/dist/zoned/validate/isValidRfc2822DateTime.d.ts +32 -0
  580. package/dist/zoned/validate/isValidRfc2822DateTime.js +35 -0
  581. package/dist/zoned/validate/isValidRfc3339DateTime.d.ts +31 -0
  582. package/dist/zoned/validate/isValidRfc3339DateTime.js +34 -0
  583. package/dist/zoned/validate/isValidTimeZone.d.ts +5 -1
  584. package/dist/zoned/validate/isValidTimeZone.js +6 -2
  585. package/package.json +50 -1
  586. package/skills/gmt-arithmetic/SKILL.md +99 -12
  587. package/skills/gmt-basics/SKILL.md +57 -15
  588. package/skills/gmt-integration/SKILL.md +24 -9
  589. package/skills/gmt-timezone/SKILL.md +134 -29
  590. package/dist/internal/unixZonedDateTime.d.ts +0 -22
  591. package/dist/internal/unixZonedDateTime.js +0 -32
  592. package/dist/internal/utcZonedDateTime.d.ts +0 -19
  593. package/dist/internal/utcZonedDateTime.js +0 -31
@@ -0,0 +1,27 @@
1
+ /** TC39 Temporal `PadISOYear ( y )`, §3.5.10: a year from 0 to 9999 is written with four digits. */
2
+ const MAX_FOUR_DIGIT_YEAR = 9999;
3
+ /**
4
+ * Write an ISO year as Temporal writes it at the head of a date string (TC39 Temporal
5
+ * `PadISOYear ( y )`, §3.5.10): four digits from 0000 to 9999, otherwise a sign and six digits.
6
+ *
7
+ * A year written any other way does not read back. `"10000-01-01"` and `"00-5-01-01"` are not ISO
8
+ * 8601 or Temporal strings, and `isValidDate` rejects both; `"+010000-01-01"` and
9
+ * `"-000005-01-01"` are what `Temporal.PlainDate#toString` writes.
10
+ *
11
+ * - Every function that returns a year on its own writes it this way.
12
+ * - Where a Temporal value is at hand, let its own `toString` write the whole date. This is for a
13
+ * year on its own, or a date assembled from fields with no Temporal value behind them.
14
+ *
15
+ * @param year an ISO year, an integer
16
+ * @returns the year as `YYYY` or `±YYYYYY`
17
+ *
18
+ * @example isoYearString(2024) // "2024"
19
+ * @example isoYearString(5) // "0005"
20
+ * @example isoYearString(10000) // "+010000"
21
+ * @example isoYearString(-5) // "-000005"
22
+ */
23
+ export function isoYearString(year) {
24
+ return year < 0 || year > MAX_FOUR_DIGIT_YEAR
25
+ ? `${year < 0 ? "-" : "+"}${String(Math.abs(year)).padStart(6, "0")}`
26
+ : String(year).padStart(4, "0");
27
+ }
@@ -1,3 +1,4 @@
1
+ import { isObject } from "./isObject.js";
1
2
  /**
2
3
  * Default `maxPieces` for functions that return one array element per generated piece
3
4
  * (`splitIntervalByUnit*`, `intervalDivideEqually*`, `mapDatesInRange`, `mapZonedDatesInRange`).
@@ -27,7 +28,7 @@ export function resolveMaxPieces(options) {
27
28
  if (options === undefined) {
28
29
  return DEFAULT_MAX_PIECES;
29
30
  }
30
- if (typeof options !== "object" || options === null) {
31
+ if (!isObject(options)) {
31
32
  return null;
32
33
  }
33
34
  const { maxPieces } = options;
@@ -1,5 +1,8 @@
1
1
  /**
2
- * Resolve the `timeZone` option of every `unix/` and `utc/` function that takes one.
2
+ * Resolve the `timeZone` option of the `unix/` and `utc/` functions that hand the zone to
3
+ * `Intl.DateTimeFormat`, which takes a time zone identifier only. A function whose result names no
4
+ * zone reads its option with `normalizeZoneFrame` instead, which also accepts a stored UTC offset
5
+ * with seconds.
3
6
  *
4
7
  * - Omitted (`undefined`) → `"UTC"`. A Unix epoch and a UTC string name an instant, so no host
5
8
  * zone is read unless asked for.
@@ -1,7 +1,10 @@
1
1
  import { getSystemTimeZone } from "../zoned/get/getSystemTimeZone.js";
2
2
  import { isValidTimeZone } from "../zoned/validate/index.js";
3
3
  /**
4
- * Resolve the `timeZone` option of every `unix/` and `utc/` function that takes one.
4
+ * Resolve the `timeZone` option of the `unix/` and `utc/` functions that hand the zone to
5
+ * `Intl.DateTimeFormat`, which takes a time zone identifier only. A function whose result names no
6
+ * zone reads its option with `normalizeZoneFrame` instead, which also accepts a stored UTC offset
7
+ * with seconds.
5
8
  *
6
9
  * - Omitted (`undefined`) → `"UTC"`. A Unix epoch and a UTC string name an instant, so no host
7
10
  * zone is read unless asked for.
@@ -1,5 +1,6 @@
1
1
  import type { Disambiguation } from "../types/index.js";
2
2
  import { type IntervalNanoseconds } from "./intervalNanoseconds.js";
3
+ import { type ZoneFrame } from "./zoneFrame.js";
3
4
  /** A `LocalWindow` validated once: canonical PlainTime strings, and whether it wraps midnight. */
4
5
  export type ResolvedWindow = {
5
6
  from: string;
@@ -8,7 +9,10 @@ export type ResolvedWindow = {
8
9
  };
9
10
  /** An `OperatingSchedule` reduced to the lookups the day walk needs. */
10
11
  export type ResolvedSchedule = {
12
+ /** The zone as the caller wrote it: a time zone identifier or a stored UTC offset. */
11
13
  timeZone: string;
14
+ /** How local time is read in that zone (`zoneFrame`). */
15
+ frame: ZoneFrame;
12
16
  /** Windows by ISO weekday; index 0 is unused. */
13
17
  weekly: readonly (readonly ResolvedWindow[])[];
14
18
  holidays: ReadonlySet<string>;
@@ -26,9 +30,12 @@ export declare const MAX_SCHEDULE_DAYS = 10000;
26
30
  */
27
31
  export declare const DEFAULT_OPERATING_HORIZON = "P1Y";
28
32
  /**
29
- * Parse `OperatingSchedule['weekly']`: an object whose own keys are ISO weekdays `"1"`–`"7"`,
30
- * each holding an array of `LocalWindow`s (or `undefined`, meaning closed). Any other key, or a
31
- * malformed window, returns `null`.
33
+ * Parse `OperatingSchedule['weekly']`: an object keyed by ISO weekday `"1"`–`"7"`, each holding an
34
+ * array of `LocalWindow`s (or `undefined`, meaning closed). Each weekday is read with an ordinary
35
+ * property get, as Temporal's `Get` reads a field list, so a non-enumerable or inherited weekday
36
+ * applies. Any other own enumerable key, string or symbol, or a malformed window, returns `null`;
37
+ * a non-enumerable one is not an entry, as `Object.assign` and spread do not copy it, so a
38
+ * function carrying the weekdays is read without its built-in `length` and `name`.
32
39
  */
33
40
  export declare function parseWeeklyPattern(value: unknown): ResolvedWindow[][] | null;
34
41
  /** Validate an `OperatingSchedule`, or `null` when any part of it is malformed. */
@@ -47,7 +54,7 @@ export declare function parseScheduleDisambiguation(options: unknown): Disambigu
47
54
  * that instant, since nothing after it can be answered. `null` when `within` is not a
48
55
  * non-negative ISO duration.
49
56
  */
50
- export declare function parseSearchHorizon(fromNs: bigint, within: unknown, timeZone: string): bigint | null;
57
+ export declare function parseSearchHorizon(fromNs: bigint, within: unknown, frame: ZoneFrame): bigint | null;
51
58
  /**
52
59
  * What the walk tells its caller.
53
60
  *
@@ -82,6 +89,8 @@ export type ScheduleWalk = {
82
89
  * - A window can start as early as the previous date's first instant (see `resolveDateWindows`),
83
90
  * so the walk settles one date behind: once a date is resolved, the first instant of the date
84
91
  * resolved before it is the `bound` no later window starts before.
92
+ * - A walk from the start of Temporal's range also resolves the date before its first, whose
93
+ * wrapping windows are still open when the range begins (`resolveWindowsBefore`).
85
94
  * - When the visitor stops the walk from `day`, or the last representable day is reached, the
86
95
  * runs still pending are handed over too.
87
96
  * - Returns `null` when a day bucket could not be found, or the walk would resolve a date
@@ -2,11 +2,11 @@ import { Temporal } from "@js-temporal/polyfill";
2
2
  import { resolveLocal } from "../instant/convert/resolveLocal.js";
3
3
  import { isValidDate } from "../plain/validate/isValidDate.js";
4
4
  import { isValidTime } from "../plain/validate/isValidTime.js";
5
- import { isValidTimeZone } from "../zoned/validate/isValidTimeZone.js";
6
5
  import { parseBusinessCalendar, parseHolidays } from "./businessCalendar.js";
7
6
  import { coalesceIntervalNanoseconds, } from "./intervalNanoseconds.js";
8
7
  import { isObject, isOptionsArgument } from "./isObject.js";
9
8
  import { nextZonedBucketStart, zonedUnitStart } from "./zonedBucket.js";
9
+ import { frameEpochNanoseconds, frameWallClock, frameZoned, zoneFrame, } from "./zoneFrame.js";
10
10
  const DISAMBIGUATIONS = [
11
11
  "compatible",
12
12
  "earlier",
@@ -81,9 +81,12 @@ function parseWindows(value) {
81
81
  return windows;
82
82
  }
83
83
  /**
84
- * Parse `OperatingSchedule['weekly']`: an object whose own keys are ISO weekdays `"1"`–`"7"`,
85
- * each holding an array of `LocalWindow`s (or `undefined`, meaning closed). Any other key, or a
86
- * malformed window, returns `null`.
84
+ * Parse `OperatingSchedule['weekly']`: an object keyed by ISO weekday `"1"`–`"7"`, each holding an
85
+ * array of `LocalWindow`s (or `undefined`, meaning closed). Each weekday is read with an ordinary
86
+ * property get, as Temporal's `Get` reads a field list, so a non-enumerable or inherited weekday
87
+ * applies. Any other own enumerable key, string or symbol, or a malformed window, returns `null`;
88
+ * a non-enumerable one is not an entry, as `Object.assign` and spread do not copy it, so a
89
+ * function carrying the weekdays is read without its built-in `length` and `name`.
87
90
  */
88
91
  export function parseWeeklyPattern(value) {
89
92
  if (!isObject(value) || Array.isArray(value)) {
@@ -92,13 +95,17 @@ export function parseWeeklyPattern(value) {
92
95
  const weekly = Array.from({ length: 8 }, () => []);
93
96
  const record = value;
94
97
  for (const key of Reflect.ownKeys(record)) {
95
- if (typeof key !== "string" || !WEEKDAY_KEYS.includes(key)) {
98
+ if ((typeof key !== "string" || !WEEKDAY_KEYS.includes(key)) &&
99
+ Object.prototype.propertyIsEnumerable.call(record, key)) {
96
100
  return null;
97
101
  }
98
- if (record[key] === undefined) {
102
+ }
103
+ for (const key of WEEKDAY_KEYS) {
104
+ const day = record[key];
105
+ if (day === undefined) {
99
106
  continue;
100
107
  }
101
- const windows = parseWindows(record[key]);
108
+ const windows = parseWindows(day);
102
109
  if (windows === null) {
103
110
  return null;
104
111
  }
@@ -148,7 +155,8 @@ export function parseOperatingSchedule(value) {
148
155
  return null;
149
156
  }
150
157
  const { timeZone, weekly, holidays, overrides } = value;
151
- if (typeof timeZone !== "string" || !isValidTimeZone(timeZone)) {
158
+ const frame = zoneFrame(timeZone);
159
+ if (typeof timeZone !== "string" || frame === null) {
152
160
  return null;
153
161
  }
154
162
  const weeklyWindows = parseWeeklyPattern(weekly);
@@ -161,6 +169,7 @@ export function parseOperatingSchedule(value) {
161
169
  }
162
170
  return {
163
171
  timeZone,
172
+ frame,
164
173
  weekly: weeklyWindows,
165
174
  holidays: holidayDates,
166
175
  overrides: overrideWindows,
@@ -192,7 +201,7 @@ export function parseScheduleDisambiguation(options) {
192
201
  * that instant, since nothing after it can be answered. `null` when `within` is not a
193
202
  * non-negative ISO duration.
194
203
  */
195
- export function parseSearchHorizon(fromNs, within, timeZone) {
204
+ export function parseSearchHorizon(fromNs, within, frame) {
196
205
  const text = within === undefined ? DEFAULT_OPERATING_HORIZON : within;
197
206
  if (typeof text !== "string") {
198
207
  return null;
@@ -207,18 +216,23 @@ export function parseSearchHorizon(fromNs, within, timeZone) {
207
216
  if (duration.sign < 0) {
208
217
  return null;
209
218
  }
210
- const from = Temporal.Instant.fromEpochNanoseconds(fromNs).toZonedDateTimeISO(timeZone);
211
- const horizon = clampedToRange(() => from.add(duration).epochNanoseconds);
212
- const cap = clampedToRange(() => from
219
+ const from = frameZoned(Temporal.Instant.fromEpochNanoseconds(fromNs), frame);
220
+ const horizon = clampedToRange(() => frameEpochNanoseconds(from.add(duration), frame));
221
+ const cap = clampedToRange(() => frameEpochNanoseconds(from
213
222
  .toPlainDate()
214
223
  .add({ days: MAX_SCHEDULE_DAYS + 1 })
215
- .toZonedDateTime(timeZone).epochNanoseconds - 1n);
224
+ .toZonedDateTime(frame.timeZone), frame) - 1n);
216
225
  return horizon < cap ? horizon : cap;
217
226
  }
218
227
  /** An instant computed by `instant`, or Temporal's last instant when it lies past the range. */
219
228
  function clampedToRange(instant) {
220
229
  try {
221
- return instant();
230
+ const nanoseconds = instant();
231
+ // At a seconds offset west of UTC the instant is later than the stand-in it was computed
232
+ // on (`frameZoned`), so it can pass the last instant without Temporal throwing.
233
+ return nanoseconds > MAX_INSTANT_NANOSECONDS
234
+ ? MAX_INSTANT_NANOSECONDS
235
+ : nanoseconds;
222
236
  }
223
237
  catch (error) {
224
238
  if (error instanceof RangeError) {
@@ -229,9 +243,7 @@ function clampedToRange(instant) {
229
243
  }
230
244
  /** The local date of an instant in the schedule's zone. */
231
245
  function localDateOf(schedule, ns) {
232
- return Temporal.Instant.fromEpochNanoseconds(ns)
233
- .toZonedDateTimeISO(schedule.timeZone)
234
- .toPlainDate();
246
+ return frameWallClock(Temporal.Instant.fromEpochNanoseconds(ns), schedule.frame).toPlainDate();
235
247
  }
236
248
  /**
237
249
  * The local date `days` after the one `fromNs` falls on, or `null` when that is past Temporal's
@@ -250,20 +262,34 @@ function dateLimit(schedule, fromNs, days) {
250
262
  }
251
263
  /**
252
264
  * The day bucket the walk starts in: the one holding the instant 72 hours before `fromNs`, or
253
- * Temporal's first instant when that is earlier. When the bucket's own start is not
254
- * representable, the walk starts at that instant instead, the earliest of its date there is.
265
+ * the earliest instant the schedule's frame can place when that is earlier. When the bucket's own
266
+ * start is not representable, the walk starts at that instant instead, the earliest of its date
267
+ * there is.
268
+ *
269
+ * The earliest instant is Temporal's first, except at an offset with seconds west of UTC: its
270
+ * stand-in sits the offset's seconds before the instant (`frameZoned`), so the first instant it
271
+ * can place is that many seconds after Temporal's first. A walk from before it throws
272
+ * `RangeError`, the caller's sentinel, rather than start after its own instant.
273
+ *
274
+ * `atRangeStart` is true when the walk starts at that earliest instant. No day bucket lies
275
+ * before it, so the windows of the local date before the bucket's own are not reached by walking
276
+ * back: the walk carries them in (`resolveWindowsBefore`).
255
277
  */
256
278
  function firstWalkBucket(schedule, fromNs) {
257
- const startNs = fromNs - LOOKBACK_NANOSECONDS < MIN_INSTANT_NANOSECONDS
258
- ? MIN_INSTANT_NANOSECONDS
259
- : fromNs - LOOKBACK_NANOSECONDS;
260
- const zoned = Temporal.Instant.fromEpochNanoseconds(startNs).toZonedDateTimeISO(schedule.timeZone);
279
+ const shift = schedule.frame.shiftNanoseconds;
280
+ const earliestNs = shift < 0n ? MIN_INSTANT_NANOSECONDS - shift : MIN_INSTANT_NANOSECONDS;
281
+ if (fromNs < earliestNs) {
282
+ throw new RangeError("the instant is before the first the frame can place");
283
+ }
284
+ const atRangeStart = fromNs - LOOKBACK_NANOSECONDS <= earliestNs;
285
+ const startNs = atRangeStart ? earliestNs : fromNs - LOOKBACK_NANOSECONDS;
286
+ const zoned = frameZoned(Temporal.Instant.fromEpochNanoseconds(startNs), schedule.frame);
261
287
  try {
262
- return zonedUnitStart(zoned, "day");
288
+ return { bucket: zonedUnitStart(zoned, "day"), atRangeStart };
263
289
  }
264
290
  catch (error) {
265
291
  if (error instanceof RangeError) {
266
- return zoned;
292
+ return { bucket: zoned, atRangeStart };
267
293
  }
268
294
  throw error;
269
295
  }
@@ -278,14 +304,16 @@ function windowsOn(schedule, date) {
278
304
  return schedule.holidays.has(key) ? [] : schedule.weekly[date.dayOfWeek];
279
305
  }
280
306
  /**
281
- * Resolve one window edge with `resolveLocal`. `local` is `null` for a wrap past Temporal's last
282
- * date. A wall time outside Temporal's range fails under every policy, so it resolves just
283
- * outside the range, on the side its date lies. `undefined` means `"reject"` refused it.
307
+ * Resolve one window edge with `resolveLocal`. An edge on a date Temporal cannot hold is already
308
+ * outside the range. A wall time outside Temporal's range fails under every policy, so it
309
+ * resolves just outside the range, on the side its date lies. `undefined` means `"reject"`
310
+ * refused it.
284
311
  */
285
- function resolveEdge(local, date, timeZone, disambiguation) {
286
- if (local === null) {
287
- return { ns: PAST_LAST_INSTANT, text: "" };
312
+ function resolveEdge(edge, timeZone, disambiguation) {
313
+ if (typeof edge === "bigint") {
314
+ return { ns: edge, text: "" };
288
315
  }
316
+ const local = `${edge.date.toString()}T${edge.time}`;
289
317
  const text = resolveLocal(local, timeZone, { disambiguation });
290
318
  if (text !== "") {
291
319
  return { ns: Temporal.Instant.from(text).epochNanoseconds, text };
@@ -294,14 +322,43 @@ function resolveEdge(local, date, timeZone, disambiguation) {
294
322
  return undefined;
295
323
  }
296
324
  return {
297
- ns: date.year > 0 ? PAST_LAST_INSTANT : BEFORE_FIRST_INSTANT,
325
+ ns: edge.date.year > 0 ? PAST_LAST_INSTANT : BEFORE_FIRST_INSTANT,
298
326
  text: "",
299
327
  };
300
328
  }
329
+ /** The local date after `date`, or `null` past Temporal's last date. */
330
+ function dateAfter(date) {
331
+ try {
332
+ return date.add({ days: 1 });
333
+ }
334
+ catch (error) {
335
+ if (error instanceof RangeError) {
336
+ return null;
337
+ }
338
+ throw error;
339
+ }
340
+ }
341
+ /** The local date before `date`, or `null` before Temporal's first date. */
342
+ function dateBefore(date) {
343
+ try {
344
+ return date.subtract({ days: 1 });
345
+ }
346
+ catch (error) {
347
+ if (error instanceof RangeError) {
348
+ return null;
349
+ }
350
+ throw error;
351
+ }
352
+ }
301
353
  /**
302
- * Resolve one date's windows to instants with `resolveLocal`. Each edge is resolved on its own
303
- * under `disambiguation`; a wrapping window's `to` is read on the next date. An edge pair that
304
- * resolves to an empty or inverted span (a window shorter than the gap it straddles) is dropped.
354
+ * Resolve the windows of one local date to instants with `resolveLocal`. Each edge is resolved on
355
+ * its own under `disambiguation`; a wrapping window's `to` is read on the next date. An edge pair
356
+ * that resolves to an empty or inverted span (a window shorter than the gap it straddles) is
357
+ * dropped.
358
+ *
359
+ * `date` is `null` for the date before Temporal's first, and `next` is `null` for the date after
360
+ * its last. A window is a rule about the local clock, so it still holds on the side of it that
361
+ * Temporal can reach: an edge on a date Temporal cannot hold lies just outside the range.
305
362
  *
306
363
  * Under `"earlier"`, an edge in a gap moves back by the gap's length (TC39
307
364
  * DisambiguatePossibleEpochNanoseconds), so a date whose midnight is skipped can open before its
@@ -312,31 +369,24 @@ function resolveEdge(local, date, timeZone, disambiguation) {
312
369
  * in `unresolved` as the widest span it could cover (its start read `"earlier"`, its end
313
370
  * `"later"`), so the caller can refuse an answer it might change and ignore it elsewhere.
314
371
  */
315
- function resolveDateWindows(schedule, date, disambiguation) {
372
+ function resolveDateWindows(schedule, windows, date, next, disambiguation) {
316
373
  const records = [];
317
374
  const unresolved = [];
318
375
  const { timeZone } = schedule;
319
- for (const window of windowsOn(schedule, date)) {
320
- let endDate = date;
321
- if (window.wraps) {
322
- try {
323
- endDate = date.add({ days: 1 });
324
- }
325
- catch (error) {
326
- if (!(error instanceof RangeError)) {
327
- throw error;
328
- }
329
- endDate = null;
330
- }
331
- }
332
- const startLocal = `${date.toString()}T${window.from}`;
333
- const endLocal = endDate === null ? null : `${endDate.toString()}T${window.to}`;
334
- const start = resolveEdge(startLocal, date, timeZone, disambiguation);
335
- const end = resolveEdge(endLocal, endDate ?? date, timeZone, disambiguation);
376
+ for (const window of windows) {
377
+ const startEdge = date === null ? BEFORE_FIRST_INSTANT : { date, time: window.from };
378
+ const endDate = window.wraps ? next : date;
379
+ const endEdge = endDate === null
380
+ ? window.wraps
381
+ ? PAST_LAST_INSTANT
382
+ : BEFORE_FIRST_INSTANT
383
+ : { date: endDate, time: window.to };
384
+ const start = resolveEdge(startEdge, timeZone, disambiguation);
385
+ const end = resolveEdge(endEdge, timeZone, disambiguation);
336
386
  if (start === undefined || end === undefined) {
337
387
  // "earlier" and "later" always resolve, so the widest span is always known.
338
- const earliest = resolveEdge(startLocal, date, timeZone, "earlier");
339
- const latest = resolveEdge(endLocal, endDate ?? date, timeZone, "later");
388
+ const earliest = resolveEdge(startEdge, timeZone, "earlier");
389
+ const latest = resolveEdge(endEdge, timeZone, "later");
340
390
  unresolved.push({
341
391
  start: earliest?.ns ?? BEFORE_FIRST_INSTANT,
342
392
  end: latest?.ns ?? PAST_LAST_INSTANT,
@@ -354,6 +404,38 @@ function resolveDateWindows(schedule, date, disambiguation) {
354
404
  }
355
405
  return { records, unresolved };
356
406
  }
407
+ /**
408
+ * Resolve the windows of the local date before `date`, the first date of a walk that starts at
409
+ * the earliest instant its frame can place.
410
+ *
411
+ * A window that opened on that date and wraps past midnight is still open on `date`, although
412
+ * the instant it opened at is before the range. The previous date follows its own override or
413
+ * holiday like any other. West of UTC the first date is Temporal's first, `-271821-04-19`, and
414
+ * the date before it cannot be held or named: no override or holiday can be written for it, so
415
+ * the weekly pattern applies, by the weekday before `date`'s.
416
+ */
417
+ function resolveWindowsBefore(schedule, date, disambiguation) {
418
+ const previous = dateBefore(date);
419
+ const windows = previous === null
420
+ ? schedule.weekly[date.dayOfWeek === 1 ? 7 : date.dayOfWeek - 1]
421
+ : windowsOn(schedule, previous);
422
+ return resolveDateWindows(schedule, windows, previous, date, disambiguation);
423
+ }
424
+ /**
425
+ * Resolve the windows a walk gains on reaching `date`: the date's own and, for the first date of
426
+ * a walk from the start of the range (`carryIn`), those of the date before it.
427
+ */
428
+ function resolveVisit(schedule, date, carryIn, disambiguation) {
429
+ const own = resolveDateWindows(schedule, windowsOn(schedule, date), date, dateAfter(date), disambiguation);
430
+ if (!carryIn) {
431
+ return own;
432
+ }
433
+ const before = resolveWindowsBefore(schedule, date, disambiguation);
434
+ return {
435
+ records: [...before.records, ...own.records],
436
+ unresolved: [...before.unresolved, ...own.unresolved],
437
+ };
438
+ }
357
439
  /**
358
440
  * Walk the schedule's local dates from a little before `fromNs`, handing the visitor each open
359
441
  * run as soon as no later window can extend it.
@@ -364,6 +446,8 @@ function resolveDateWindows(schedule, date, disambiguation) {
364
446
  * - A window can start as early as the previous date's first instant (see `resolveDateWindows`),
365
447
  * so the walk settles one date behind: once a date is resolved, the first instant of the date
366
448
  * resolved before it is the `bound` no later window starts before.
449
+ * - A walk from the start of Temporal's range also resolves the date before its first, whose
450
+ * wrapping windows are still open when the range begins (`resolveWindowsBefore`).
367
451
  * - When the visitor stops the walk from `day`, or the last representable day is reached, the
368
452
  * runs still pending are handed over too.
369
453
  * - Returns `null` when a day bucket could not be found, or the walk would resolve a date
@@ -386,7 +470,10 @@ export function walkSchedule(schedule, fromNs, disambiguation, visitor) {
386
470
  // The span a range or search may cover, plus the date after its last, which is resolved to
387
471
  // settle it because its windows can start before its own first instant.
388
472
  const limitDate = dateLimit(schedule, fromNs, MAX_SCHEDULE_DAYS + 2);
389
- let current = firstWalkBucket(schedule, fromNs);
473
+ const first = firstWalkBucket(schedule, fromNs);
474
+ let current = first.bucket;
475
+ // True until the first date is resolved, for a walk from the start of the range.
476
+ let carryIn = first.atRangeStart;
390
477
  let lastDate = null;
391
478
  let bound;
392
479
  for (let bucket = 0; bucket < MAX_SCHEDULE_BUCKETS; bucket++) {
@@ -416,7 +503,8 @@ export function walkSchedule(schedule, fromNs, disambiguation, visitor) {
416
503
  Temporal.PlainDate.compare(date, limitDate) >= 0) {
417
504
  return null;
418
505
  }
419
- const resolved = resolveDateWindows(schedule, date, disambiguation);
506
+ const resolved = resolveVisit(schedule, date, carryIn, disambiguation);
507
+ carryIn = false;
420
508
  for (const window of resolved.unresolved) {
421
509
  if (window.end > fromNs &&
422
510
  (unresolvedStart === undefined || window.start < unresolvedStart)) {
@@ -425,7 +513,7 @@ export function walkSchedule(schedule, fromNs, disambiguation, visitor) {
425
513
  }
426
514
  pending = coalesceIntervalNanoseconds([...pending, ...resolved.records]);
427
515
  lastDate = date;
428
- bound = current.epochNanoseconds;
516
+ bound = frameEpochNanoseconds(current, schedule.frame);
429
517
  }
430
518
  try {
431
519
  current = nextZonedBucketStart(current, "day");
@@ -40,7 +40,14 @@ export interface ParsedPatternFields {
40
40
  * fields, or `null` on malformed pattern / no match / invalid input.
41
41
  *
42
42
  * `null` here always means "return the sentinel" to the caller — it
43
- * never distinguishes malformed-pattern from no-match from invalid-input,
44
- * matching the shared never-throw / sentinel-return contract.
43
+ * never distinguishes malformed-pattern from no-match from invalid-input
44
+ * from a `yy` token with no window, matching the shared never-throw /
45
+ * sentinel-return contract.
46
+ *
47
+ * `options` is the caller's `TwoDigitYearOptions` bag, already accepted
48
+ * by `isOptionsArgument`. It is read lazily: only a matched `yy` token
49
+ * reads `yearWindow`, once, so a pattern without `yy` reads neither the
50
+ * option nor the clock. A bag that throws when read makes this function
51
+ * throw; every caller runs it inside `try`.
45
52
  */
46
- export declare function parseValueWithPattern(value: string, pattern: string, locale: LocalesArgument | undefined, allowedFields: ReadonlySet<PatternField>): ParsedPatternFields | null;
53
+ export declare function parseValueWithPattern(value: string, pattern: string, locale: LocalesArgument | undefined, allowedFields: ReadonlySet<PatternField>, options?: unknown): ParsedPatternFields | null;
@@ -1,4 +1,6 @@
1
1
  import { resolveLocale } from "./resolveLocale.js";
2
+ import { twoDigitYear } from "./twoDigitYear.js";
3
+ import { readYearWindowStart } from "./yearWindowStart.js";
2
4
  import { getLocaleEraNames } from "../plain/locale/getLocaleEraNames.js";
3
5
  import { getLocaleMeridiems } from "../plain/locale/getLocaleMeridiems.js";
4
6
  import { getLocaleMonthNames } from "../plain/locale/getLocaleMonthNames.js";
@@ -273,15 +275,24 @@ function compilePattern(pattern, allowedFields, locale) {
273
275
  }
274
276
  /**
275
277
  * Resolve a successful regex match's captures back into date/time field
276
- * values, applying the two-digit-year pivot, 12-hour-to-24-hour
277
- * conversion (via a matched meridiem), and BCE/CE year adjustment.
278
+ * values, resolving a two-digit year in the caller's window, converting
279
+ * 12-hour to 24-hour (via a matched meridiem), and adjusting a BCE year.
278
280
  *
279
281
  * This step only ever produces a *candidate* fields object — it does not
280
282
  * itself prove the fields form a real date/time. The caller is
281
283
  * responsible for handing the result to `Temporal.*.from(fields, {
282
284
  * overflow: "reject" })`, which is what actually validates it.
285
+ *
286
+ * `options` is the caller's `TwoDigitYearOptions` bag, unread. It is read
287
+ * only when a `yy` token matched, once (`readYearWindowStart`): a pattern
288
+ * with no `yy` never reads `yearWindow`, and so never reads the clock a
289
+ * `"rolling"` window needs. Returns `null` when a `yy` token matched and
290
+ * the bag names no valid window: no standard says which century a
291
+ * two-digit year belongs to, so without the caller's window the value
292
+ * cannot be read. Reading a hostile bag throws; the public function's
293
+ * `try` turns that into its sentinel.
283
294
  */
284
- function resolvePatternFields(match, tokens) {
295
+ function resolvePatternFields(match, tokens, options) {
285
296
  const groups = (match.groups ?? {});
286
297
  const fields = {};
287
298
  let hourIsTwelveHour = false;
@@ -296,11 +307,12 @@ function resolvePatternFields(match, tokens) {
296
307
  fields.year = Number.parseInt(raw, 10);
297
308
  break;
298
309
  case "yearShort": {
299
- // Two-digit year pivot: 00-68 -> 2000-2068, 69-99 -> 1969-1999.
300
- // Fixed rule (mirrors common strptime %y behavior) — not a
301
- // configurable/global setting.
302
- const numeric = Number.parseInt(raw, 10);
303
- fields.year = numeric <= 68 ? 2000 + numeric : 1900 + numeric;
310
+ // A pattern holds one year token at most (`compilePattern` rejects
311
+ // a repeated field), so this is the call's only read of the option.
312
+ const yearWindowStart = readYearWindowStart(options);
313
+ if (yearWindowStart === null)
314
+ return null;
315
+ fields.year = twoDigitYear(Number.parseInt(raw, 10), yearWindowStart);
304
316
  break;
305
317
  }
306
318
  case "monthNumber":
@@ -375,10 +387,17 @@ function resolvePatternFields(match, tokens) {
375
387
  * fields, or `null` on malformed pattern / no match / invalid input.
376
388
  *
377
389
  * `null` here always means "return the sentinel" to the caller — it
378
- * never distinguishes malformed-pattern from no-match from invalid-input,
379
- * matching the shared never-throw / sentinel-return contract.
390
+ * never distinguishes malformed-pattern from no-match from invalid-input
391
+ * from a `yy` token with no window, matching the shared never-throw /
392
+ * sentinel-return contract.
393
+ *
394
+ * `options` is the caller's `TwoDigitYearOptions` bag, already accepted
395
+ * by `isOptionsArgument`. It is read lazily: only a matched `yy` token
396
+ * reads `yearWindow`, once, so a pattern without `yy` reads neither the
397
+ * option nor the clock. A bag that throws when read makes this function
398
+ * throw; every caller runs it inside `try`.
380
399
  */
381
- export function parseValueWithPattern(value, pattern, locale, allowedFields) {
400
+ export function parseValueWithPattern(value, pattern, locale, allowedFields, options) {
382
401
  if (typeof value !== "string" || value.length === 0)
383
402
  return null;
384
403
  if (typeof pattern !== "string" || pattern.length === 0)
@@ -402,5 +421,5 @@ export function parseValueWithPattern(value, pattern, locale, allowedFields) {
402
421
  const match = value.match(compiled.regex);
403
422
  if (match === null)
404
423
  return null;
405
- return resolvePatternFields(match, compiled.tokens);
424
+ return resolvePatternFields(match, compiled.tokens, options);
406
425
  }
@@ -0,0 +1,34 @@
1
+ import type { DateTimeDurationUnit } from "../types/index.js";
2
+ /**
3
+ * Read a `units` argument, such as `{ minutes: 15 }`, the way Temporal reads a duration-like
4
+ * object, and return the amounts as a fresh plain object that holds only the caller's units.
5
+ *
6
+ * The check and the read are one pass, so nothing reaches Temporal that was not checked:
7
+ *
8
+ * - `units` must be an Object (`isObject`), a function included.
9
+ * - An own enumerable string key that `isAllowed` refuses returns `null`, whatever its value.
10
+ * This is the guard against a misspelt key, which Temporal on its own ignores. A symbol key and
11
+ * a non-enumerable key that is no unit name are not entries and are ignored.
12
+ * - Each of the ten unit names is read once with an ordinary property get, in the order Temporal's
13
+ * ToTemporalPartialDurationRecord reads them, so an inherited or non-enumerable unit applies.
14
+ * `undefined` means the unit is absent. Any other value must be a finite number; nothing is
15
+ * converted to one.
16
+ * - A unit `isAllowed` refuses returns `null` when its amount is not zero. Zero is no amount:
17
+ * Temporal too tells a calendar duration from an exact one by its nonzero fields.
18
+ * - No allowed unit present returns `null`.
19
+ *
20
+ * Whole numbers, one sign and the range are left to Temporal, which throws for each. A getter
21
+ * that throws is not caught here; the calling function's own catch returns its sentinel.
22
+ *
23
+ * @param units the caller's `units` argument
24
+ * @param isAllowed type guard for the units the calling function takes
25
+ * @returns a new plain object of the allowed units that were present, or null on invalid input
26
+ *
27
+ * @example readDurationUnits({ minutes: 15 }, isValidTimeDurationUnit) // { minutes: 15 }
28
+ * @example readDurationUnits({ minutes: 15, hours: undefined }, isValidTimeDurationUnit) // { minutes: 15 }
29
+ * @example readDurationUnits({ minutes: 15, hour: 1 }, isValidTimeDurationUnit) // null (unknown key)
30
+ * @example readDurationUnits(Object.create({ minutes: "15" }), isValidTimeDurationUnit) // null (not a number)
31
+ * @example readDurationUnits(Object.create({ days: 1 }), isValidTimeDurationUnit) // null (a unit outside the set)
32
+ * @example readDurationUnits({}, isValidTimeDurationUnit) // null
33
+ */
34
+ export declare function readDurationUnits<Unit extends DateTimeDurationUnit>(units: unknown, isAllowed: (unit: string) => unit is Unit): Partial<Record<Unit, number>> | null;