npm软件包链接:https://www.npmjs.com/package/zoned-date
术语
关于日期时间:
- 壁挂式:您的墙壁,日历中显示的值,即:年,月,日期,日(工作日),小时,分钟,第二,毫秒,时区偏移。
- 时代:时间轴流中的一个点,由历史上特定时间的秒数识别。
理由
在JavaScript中,所有Wallclock方法均基于运行时的配置返回不同的结果。 date.getHours()
在客户端浏览器,服务器和您的本地开发机中运行时返回不同的结果(对于具有相同date.getTime()
值的日期对象)。
完美解决与约会有关的问题
我最近在JavaScript中发布zoned-date所有与日期有关的问题。
安装
yarn add zoned-date
import {ZonedDate, OffsetDate} from 'zoned-date'
// or
import ZonedDate from 'zoned-date/ZonedDate'
import OffsetDate from 'zoned-date/OffsetDate'
用法
ZonedDate
和OffsetDate
在额外的时区支持下实现所有日期的方法。
-
OffsetDate
:当您知道时区的偏移时。强烈建议您参加此课程。它只是数学和纯日期对象,并且总是有效。 -
ZonedDate
:您以其名称指定时区。该库在内部使用Intl
来得出偏移。特别是,ZonedDate
明确支持DST,并全力支持Termporal proposal定义的歧义选项
注意:OffsetDate
是Date
的子类(new OffsetDate instanceof Date
是true
),而ZonedDate
不是(new ZonedDate instanceof Date
是false
)。
样本使用
const date = new OffsetDate('2020-01-01T03:00:00.000Z', {offset: 9})
console.log(date.hours) // return hours at GMT+9: 12
date.hours = 10 // set hours at GMT+9
date.hours = h => h - 1 // decrease by 1
console.log(date.toISOString()) // 2020-01-01T00:00:00.000Z
date.withMonth(1).withYear(y => y + 1) // returns a new OffsetDate object
时区转换
const date = new ZonedDate('2021-09-04T05:19:52.001', {timezone: 'Asia/Tokyo'}) // GMT+9
console.log(date.hours === 5)
date.timezone = 'Asia/Bangkok' // GMT+7
console.log(date.hours === 5 - 9 + 7)
date.timezone = 'UTC'
console.log(date.hours === 5 - 9 + 24)
date.timezone = 'America/New_York' // GMT-4
console.log(date.hours === 5 - 9 + -4 + 24)
DST支持
for (const [timezone, wallclock, disambiguation, expected] of [
// positive dst
// forward, dst starts
['Australia/ACT', '2023-10-01T02:00:00.000', undefined, 11],
['Australia/ACT', '2023-10-01T02:30:00.000', undefined, 11],
['Australia/ACT', '2023-10-01T02:30:00.000', 'compatible', 11],
['Australia/ACT', '2023-10-01T02:30:00.000', 'earlier', 10],
['Australia/ACT', '2023-10-01T02:30:00.000', 'later', 11],
// backward, dst ends
['Australia/ACT', '2023-04-02T02:00:00.000', undefined, 11],
['Australia/ACT', '2023-04-02T02:30:00.000', undefined, 11],
['Australia/ACT', '2023-04-02T02:30:00.000', 'compatible', 11],
['Australia/ACT', '2023-04-02T02:30:00.000', 'earlier', 11],
['Australia/ACT', '2023-04-02T02:30:00.000', 'later', 10],
// negative dst
// forward, dst starts
['America/Los_Angeles', '2023-03-12T02:00:00.000', undefined, -7],
['America/Los_Angeles', '2023-03-12T02:30:00.000', undefined, -7],
['America/Los_Angeles', '2023-03-12T02:30:00.000', 'compatible', -7],
['America/Los_Angeles', '2023-03-12T02:30:00.000', 'earlier', -8],
['America/Los_Angeles', '2023-03-12T02:30:00.000', 'later', -7],
// backward, dst ends
['America/Los_Angeles', '2023-11-05T01:00:00.000', undefined, -7],
['America/Los_Angeles', '2023-11-05T01:30:00.000', undefined, -7],
['America/Los_Angeles', '2023-11-05T01:30:00.000', 'compatible', -7],
['America/Los_Angeles', '2023-11-05T01:30:00.000', 'earlier', -7],
['America/Los_Angeles', '2023-11-05T01:30:00.000', 'later', -8],
]) {
const date = new ZonedDate(wallclock, {timezone, disambiguation})
console.assert(date.offset === expected)
console.log('ok')
}
for (const [timezone, wallclock, disambiguation, expected] of [
['Australia/ACT', '2023-10-01T02:30:00.000', 'reject'],
['Australia/ACT', '2023-04-02T02:30:00.000', 'reject'],
['America/Los_Angeles', '2023-03-12T02:00:00.000', 'reject'],
['America/Los_Angeles', '2023-11-05T01:00:00.000', 'reject'],
]) {
const date = new ZonedDate(wallclock, {timezone, disambiguation})
try {
date.time
} catch (e) {
console.log('ok')
continue
}
console.log('failed')
}