如何在JavaScript中ISO 8601格式化带有时区偏移量的日期?

目标:找到 ,然后按以下格式构造 URL。local timeUTC time offset

网址示例:/Actions/Sleep?duration=2002-10-10T12:00:00−05:00

该格式基于 W3C 建议。文档说:

例如,2002-10-10T12:00:00−05:00(2002 年 10 月 10 日中午,美国中部夏令时和东部标准时间)等于 2002-10-10T17:00:00Z,比 2002-10-10T12:00:00Z 晚五个小时。

因此,根据我的理解,我需要找到我的本地时间,然后使用函数来计算差值,然后将其附加到字符串的末尾。new Date()getTimezoneOffset()

  1. 获取本地时间format

    var local = new Date().format("yyyy-MM-ddThh:mm:ss"); // 2013-07-02T09:00:00
    
  2. 获取按小时偏移的 UTC 时间

    var offset = local.getTimezoneOffset() / 60; // 7
    
  3. 构造 URL(仅限时间部分)

    var duration = local + "-" + offset + ":00"; // 2013-07-02T09:00:00-7:00
    

以上输出表示我的本地时间为 2013/07/02 9am,与 UTC 的差异为 7 小时(UTC 比当地时间早 7 小时)

到目前为止,它似乎有效,但如果返回负值如-120怎么办?getTimezoneOffset()

我想知道在这种情况下格式应该是什么样子,因为我无法从W3C文档中找出答案。


答案 1

这是一个简单的帮助程序函数,它将为您格式化JS日期。

function toIsoString(date) {
  var tzo = -date.getTimezoneOffset(),
      dif = tzo >= 0 ? '+' : '-',
      pad = function(num) {
          return (num < 10 ? '0' : '') + num;
      };

  return date.getFullYear() +
      '-' + pad(date.getMonth() + 1) +
      '-' + pad(date.getDate()) +
      'T' + pad(date.getHours()) +
      ':' + pad(date.getMinutes()) +
      ':' + pad(date.getSeconds()) +
      dif + pad(Math.floor(Math.abs(tzo) / 60)) +
      ':' + pad(Math.abs(tzo) % 60);
}

var dt = new Date();
console.log(toIsoString(dt));

答案 2

getTimezoneOffset()返回您引用的规范所需的格式的相反符号。

这种格式也称为ISO8601,或者更准确地说是RFC3339

在此格式中,UTC 用 a 表示,而所有其他格式都用 UTC 的偏移量表示。含义与JavaScript相同,但减法的顺序是颠倒的,因此结果带有相反的符号。Z

此外,在名为 的本机对象上没有方法,因此 #1 中的函数将失败,除非您使用库来实现此目的。请参阅此文档Dateformat

如果您正在寻找可以直接使用此格式的库,我建议您尝试一下.js。实际上,这是默认格式,因此您可以简单地执行以下操作:

var m = moment();    // get "now" as a moment
var s = m.format();  // the ISO format is the default so no parameters are needed

// sample output:   2013-07-01T17:55:13-07:00

这是一个经过良好测试的跨浏览器解决方案,并具有许多其他有用的功能。