@xiaobu-utils/world-time
v1.0.2
Published
A world time calculation utility with IANA timezone and DST support.
Maintainers
Readme
@xiaobu-utils/world-time
基于 IANA 时区的世界时间计算工具库。正确处理夏令时(DST),提供完整 TypeScript 类型,支持 ESM + CJS 双格式,零运行时依赖。
📖 简介
@xiaobu-utils/world-time 是一个零依赖、类型安全的世界时间计算工具库。它基于原生 Intl.DateTimeFormat 和 IANA 时区数据库,能够将任意时刻准确地转换到全球任意时区,并自动处理夏令时(DST)切换、跨日期、跨月份等边界情况。
✨ 特性
- 🌍 支持任意 IANA 时区:如
Asia/Shanghai、America/New_York等 - ⏱️ 正确处理夏令时(DST):基于
Intl.DateTimeFormat反向推导偏移,比手动加减小时更可靠 - 📅 完整时间信息:返回日期、时间、周几和完整字符串
- 🧩 支持自定义预设:可注入自己的国家/地区列表,便于测试或裁剪数据
- 🎯 无时区字符串自动适配:避免被运行环境本地时区污染
- 📦 双格式产物:同时输出 ESM 和 CJS,兼容各种构建工具
- 🔒 完整 TypeScript 类型:所有 API 和返回值均有完整类型定义
- 🪶 零运行时依赖:不依赖任何第三方库,包体积极小
📦 安装
# pnpm(推荐)
pnpm add @xiaobu-utils/world-time
# npm
npm install @xiaobu-utils/world-time
# yarn
yarn add @xiaobu-utils/world-time环境要求
- Node.js ≥ 18.0.0(内置完整 ICU 数据)
- 浏览器:所有现代浏览器(Chrome 71+、Firefox 65+、Safari 14+、Edge 79+)
🚀 快速开始
import { worldTime } from "@xiaobu-utils/world-time";
// 获取当前时间在美国、日本的当地时间
const result = worldTime.getWorldTimes(
new Date(), // 当前时间
"CN", // 以中国为基准
["US", "JP"] // 目标国家
);
console.log(result.current.full);
// "2026-09-24 20:00:00 星期四"
console.log(result.targets);
// [
// { code: "US", name: "美国 - 纽约", tz: "America/New_York", full: "2026-09-24 08:00:00 星期四", ... },
// { code: "JP", name: "日本 - 东京", tz: "Asia/Tokyo", full: "2026-09-24 21:00:00 星期四", ... }
// ]📘 完整使用指南
1. 使用默认单例
内置的 worldTime 单例已经预置了常见国家/地区的数据,开箱即用。
import { worldTime } from "@xiaobu-utils/world-time";
const result = worldTime.getWorldTimes(new Date(), "CN");2. 指定目标国家
通过第三个参数传入目标国家的 ISO 3166-1 alpha-2 代码数组:
const result = worldTime.getWorldTimes(
new Date(),
"CN",
["US", "JP", "GB", "DE"]
);
result.targets.forEach((entry) => {
console.log(`${entry.name}: ${entry.full}`);
});不传第三个参数时,返回所有内置国家/地区的时间:
const all = worldTime.getWorldTimes(new Date(), "CN");
console.log(all.targets.length); // 内置国家数量3. 按国家代码去重
某些国家拥有多个时区(如美国、俄罗斯),COUNTRY_PRESETS 中可能包含多条记录。通过第四个参数 uniqueByCode 可以只保留每个国家的第一条记录:
const result = worldTime.getWorldTimes(
new Date(),
"CN",
["US", "RU"],
true // 每个国家只保留第一个匹配项
);4. 使用自定义预设
如果你只想支持部分国家,或想使用自己的数据源,可以自行构造 WorldTime 实例:
import { WorldTime } from "@xiaobu-utils/world-time";
const customPresets = [
{ name: "中国 - 北京", tz: "Asia/Shanghai", code: "CN" },
{ name: "美国 - 洛杉矶", tz: "America/Los_Angeles", code: "US" },
{ name: "澳大利亚 - 悉尼", tz: "Australia/Sydney", code: "AU" },
];
const customWorldTime = new WorldTime(customPresets);
const result = customWorldTime.getWorldTimes("2026-09-14 20:00:00", "CN");5. 解析无时区字符串
当传入的字符串不带时区信息时(如 "2026-09-14 20:00:00"),库会按照 currentCountryCode 对应的时区解析,而不是运行环境的本地时区,避免服务端与客户端结果不一致:
// 服务端时区是 UTC,但业务上这个时间应该是中国时间
const result = worldTime.getWorldTimes(
"2026-09-14 20:00:00",
"CN" // 按 Asia/Shanghai 解析
);如果字符串已带时区信息(如 "2026-09-14T20:00:00+08:00" 或 "...Z"),则直接交给原生 Date 解析,保持绝对时间语义。
6. 传入时间戳
const result = worldTime.getWorldTimes(
Date.now(), // 毫秒时间戳
"CN",
["US"]
);7. 单独使用工具函数
除了 WorldTime 类,库还导出了一些独立的工具函数,方便按需使用:
import {
parseDateInput,
parseInTimeZone,
formatDateTime,
} from "@xiaobu-utils/world-time";
// 按指定时区解析无时区字符串
const date = parseInTimeZone("2026-09-14 20:00:00", "Asia/Shanghai");
// 格式化到任意时区
const formatted = formatDateTime(date, "America/New_York");
console.log(formatted.full);
// "2026-09-14 08:00:00 星期一"
// 统一解析入口,自动识别字符串是否带时区
const date2 = parseDateInput("2026-09-14T20:00:00+08:00", "Asia/Shanghai");8. 扩展现有预设
import { COUNTRY_PRESETS, WorldTime } from "@xiaobu-utils/world-time";
const extended = new WorldTime([
...COUNTRY_PRESETS,
{ name: "新西兰 - 奥克兰", tz: "Pacific/Auckland", code: "NZ" },
{ name: "巴西 - 圣保罗", tz: "America/Sao_Paulo", code: "BR" },
]);
const result = extended.getWorldTimes(new Date(), "CN", ["NZ", "BR"]);9. 处理多时区国家
对于美国、俄罗斯等拥有多个时区的国家,可以手动构造包含多个时区条目的预设:
import { WorldTime } from "@xiaobu-utils/world-time";
const multiTzPresets = [
{ name: "美国 - 纽约(东部)", tz: "America/New_York", code: "US" },
{ name: "美国 - 芝加哥(中部)", tz: "America/Chicago", code: "US" },
{ name: "美国 - 丹佛(山地)", tz: "America/Denver", code: "US" },
{ name: "美国 - 洛杉矶(太平洋)", tz: "America/Los_Angeles", code: "US" },
];
const wt = new WorldTime(multiTzPresets);
// 不去重:返回所有 4 条美国记录
const all = wt.getWorldTimes(new Date(), "US");
// 去重:只返回第一条美国记录
const deduped = wt.getWorldTimes(new Date(), "US", undefined, true);📚 API 文档
WorldTime 类
构造函数
new WorldTime(presets?: CountryPreset[])创建一个世界时间计算器实例。默认使用内置的 COUNTRY_PRESETS。
getWorldTimes
getWorldTimes(
currentTime: DateInput,
currentCountryCode: string,
targetCountryCodes?: string[],
uniqueByCode?: boolean
): WorldTimesResult获取当前国家和目标国家的当地时间、日期和周几。
| 参数 | 类型 | 默认值 | 说明 |
| ---- | ---- | ------ | ---- |
| currentTime | DateInput | - | 当前时间,支持 Date、时间戳、字符串 |
| currentCountryCode | string | - | 当前国家的 ISO 3166-1 alpha-2 代码,如 "CN" |
| targetCountryCodes | string[] | undefined | 目标国家代码数组;不传则返回所有国家/地区 |
| uniqueByCode | boolean | false | 是否按国家代码去重(多时区国家只保留第一个) |
返回值:WorldTimesResult
异常:当 currentTime 无法解析为有效日期时,抛出 Error("Invalid date")。
🧬 类型定义
CountryPreset
interface CountryPreset {
/** 显示名称,如 "中国 - 北京" */
name: string;
/** IANA 时区,如 "Asia/Shanghai" */
tz: string;
/** ISO 3166-1 alpha-2 国家/地区代码,如 "CN" */
code: string;
}WorldTimesResult
interface WorldTimesResult {
/** 当前国家/地区时间 */
current: WorldTimeEntry;
/** 目标国家/地区时间列表 */
targets: WorldTimeEntry[];
}WorldTimeEntry
interface WorldTimeEntry extends FormattedDateTime {
/** ISO 3166-1 alpha-2 国家/地区代码 */
code: string;
/** 显示名称 */
name: string;
/** IANA 时区 */
tz: string;
}DateInput
type DateInput = Date | number | string;💡 使用场景
页面顶部展示全球城市时间
import { worldTime } from "@xiaobu-utils/world-time";
const cities = ["CN", "US", "JP", "GB", "AU"];
const result = worldTime.getWorldTimes(new Date(), "CN", cities, true);
result.targets.forEach((city) => {
console.log(`${city.name} · ${city.time} · ${city.weekday}`);
});跨时区预约时间转换
import { parseInTimeZone, formatDateTime } from "@xiaobu-utils/world-time";
// 用户在纽约选择了 "2026-12-25 09:00:00"
const date = parseInTimeZone("2026-12-25 09:00:00", "America/New_York");
// 转换到中国时间展示
const cnTime = formatDateTime(date, "Asia/Shanghai");
console.log(`对应的中国时间:${cnTime.full}`);❓ 常见问题
JavaScript 原生的 new Date("2026-09-14 20:00:00") 会按运行环境的本地时区解析。这会导致服务端与客户端结果不一致。本库通过显式指定 fallbackTimeZone,让无时区字符串的语义变得确定。
内部实现通过 "UTC 猜测 → 反查目标时区实际值 → 计算偏移 → 修正" 的方式,每次调用时动态计算偏移,因此能自动适应夏令时切换。
本库零运行时依赖,构建产物经过 tsup 压缩后,ESM 格式约 2KB(gzip 后约 1KB)。所有时间计算依赖浏览器/Node.js 原生 Intl API。
📄 许可证
MIT © xiaobu
