search
LoginSignup
18

More than 3 years have passed since last update.

posted at

updated at

JavaScript の Date 型を扱うときに気をつけること

日付の形式

状況

例えば JavaScript で new Date("2013-07-08 20:38:08") とすると以下のようにブラウザごとでバラバラの結果が返ってきます:

:frowning: Chrome, Opera, Vivaldi:

// 地方時
> new Date("2013-07-08 20:38:08")
< Mon Jul 08 2013 20:38:08 GMT+0900 (JST)

:anguished: Firefox:

// 協定世界時
> new Date("2013-07-08 20:38:08");
< Date 2013-07-08T03:00:00.000Z

:scream: Safari:

> new Date("2013-07-08 20:38:08")
< Invalid Date = $1

原因

このように invliad になってしまう原因としては new Date() is working in Chrome but not Firefox | StackOverlow で以下のように書かれている通りです:

the EMCAScript specification requires exactly one date format (i.e., YYYY-MM-DDTHH:\mm:\ss.sssZ) but custom date formats may be freely supported by an implementation: "If the String does not conform to that [ECMAScript-defined] format the function may fall back to any implementation-specific heuristics or implementation-specific date formats." Chrome and FF simply have different "implementation-specific date formats."

http://www.ecma-international.org/ecma-262/5.1/#sec-15.9.1.15 ECMAScript の仕様では YYYY-MM-DDTHH:mm:ss.sssZ つまり ISO 8601 方式しか定義されていません。その他のフォーマットについてはブラウザに依存しているので先ほどのようにバラバラの結果になります。

処理方法チートシート

API にもよりますが取得した値が 2013-07-08 20:38:08 といった形式の場合以下のようなメソッドで修正する:

// MySQL から返ってくる日付の値を ISO 8601 に変換
function replaceDate(dateStr) {
  const regexp = /^([0-9]{2,4})-([0-1][0-9])-([0-3][0-9])(?:( [0-2][0-9]):([0-5][0-9]):([0-5][0-9]))?$/;
  return dateStr.replace(regexp, (match, year, month, day, hour, minutes, seconds) => {
    return `${year}-${month}-${ day}T${hour}:${minutes}:${seconds}.000+09:00`;
  });
}

参照

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
What you can do with signing up
18