Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

refactor(date): Dateの章のリファクタリング #1515

Merged
merged 3 commits into from
Nov 5, 2022
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
40 changes: 25 additions & 15 deletions source/basic/date/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ description: "日付や時刻を扱うビルトインオブジェクトのDate
`Date`オブジェクトのインスタンスではなく現在の時刻の時刻値だけが欲しい場合には、`Date.now`メソッドの返り値を使います。
作成したインスタンスが持つ時刻値は、`getTime`メソッドで取得できます。
また、`toISOString`メソッドを使うと、その時刻をUTCにおける[ISO 8601][]形式の文字列に変換できます。
ISO 8601とは国際規格となっている文字列の形式で、`2006-01-02T15:04:05.999+09:00`のように時刻を表現します
ISO 8601とは国際規格となっている文字列の形式で、`2006-01-02T15:04:05.999+09:00`のように時刻とタイムゾーン情報を表現します
人間が見てもわかりやすい文字列であるため、広く利用されています。

{{book.console}}
Expand Down Expand Up @@ -56,8 +56,8 @@ console.log(now.toISOString());

1つめは、コンストラクタ関数にミリ秒を表す数値型の引数を渡したときに適用されます。
渡した数値をUTCの1970年1月1日0時0分0秒を基準とした時刻値として扱います。
この方法は実行環境による挙動の違いが起きないので安全です
また、時刻値を直接指定するので、他の2つの方法と違ってタイムゾーンを考慮する必要がありません。
この方法は基準となる時刻とタイムゾーンが固定されているため、実行環境のタイムゾーンによる違いが起きないので安全です
そのため、他の2つの方法と違ってタイムゾーンを考慮する必要がありません。
Comment on lines -59 to +60
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

同じことを言ってる感じがしたので、ちょっとタイムゾーンと明確にした。
実行環境の時計でずれるとかはあるため。


{{book.console}}
```js
Expand All @@ -68,7 +68,7 @@ const date = new Date(1136214245999);
console.log(date.toISOString()); // => "2006-01-02T15:04:05.999Z"
```

2つめは文字列型の引数を渡したときに適用されます
2つめは、文字列型の引数を渡したときに適用されます
[RFC2822][]や[ISO 8601][]の形式に従った文字列を渡すと、
その文字列をパースして得られる時刻値を使って、`Date`のインスタンスを作成します。

Expand Down Expand Up @@ -96,15 +96,18 @@ console.log(inLocal.toISOString()); // "2006-01-02T06:04:05.999Z" (Asia/Tokyoの
new Date(year, month, day, hour, minutes, seconds, milliseconds);
```

コンストラクタ関数に2つ以上の引数を渡すと、このオーバーロードが適用されます。
日を表す第三引数から後ろの引数は省略可能ですが、日付だけはデフォルトで1が設定され、そのほかには0が設定されます。
また、月を表す第二引数は0から11までの数値で指定することにも注意しましょう。
コンストラクタ関数に2つ以上の引数を渡すと、この方法で`Date`インスタンスが作成されます。
月内の日を表す第三引数(`day`)から後ろの引数は省略可能です。
省略した場合のそれぞれの引数の初期値は`0`ですが、日(`day`)を表す第三引数だけは`1`がデフォルト値となります。
また、月(`month`)を表す第二引数は`0`が1月に対応し、`0`から`11`までの数値で月を指定することにも注意しましょう。
Comment on lines -99 to +102
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

全体的に引数を明示するようにした。

日付だけはデフォルトで1が設定され

というのがよくわからなかったけど、多分 day のことかな? @lacolaco

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

多分そうですね


先述した2つの方法と違い、この方法はタイムゾーンを指定できません。
渡した数値は常にローカルのタイムゾーンにおける時刻とみなされます。

<!-- textlint-disable -->
結果が実行環境に依存してしまうため、基本的にこの方法は使うべきではありません。
<!-- textlint-enable -->

時刻を部分ごとに指定したい場合は、[Date.UTC][]メソッドを使うとよいでしょう。
渡す引数の形式は同じですが、`Date.UTC`メソッドは渡された数値をUTCにおける時刻として扱い、その時刻値を返します。

Expand All @@ -131,14 +134,16 @@ console.log(date2.toISOString()); // => "2006-01-02T15:04:05.999Z"
const invalid = new Date("");
console.log(invalid.getTime()); // => NaN
console.log(invalid.toString()); // => "Invalid Date"
// 不正なDateインスタンスかを判定
console.log(Number.isNaN(invalid.getTime())); // => true
```

### Dateのインスタンスメソッド {#instance-method}

`Date`オブジェクトのインスタンスは多くのメソッドを持っていますが、
ほとんどは`getHours`と`setHours`のような、時刻の各部分を取得・更新するためのメソッドです。

次の例は、日付を決まった形式の文字列に変換しています。
次のコードは、日付を決まった形式の文字列に変換しています。
`getMonth`メソッドや`setMonth`メソッドのように月を数値で扱うメソッドは、0から11の数値で指定することに注意しましょう。ある`Date`のインスタンスの時刻が何月かを表示するには、`getMonth`メソッドの返り値に1を足す必要があります。

{{book.console}}
Expand Down Expand Up @@ -179,22 +184,24 @@ console.log(`Hours in UTC: ${now.getHours() + timezoneOffsetInHours}`);
- 任意の書式の文字列から時刻に変換するメソッドがない
- 「時刻を1時間進める」のように時刻を前後にずらす操作を提供するメソッドがない
- 任意のタイムゾーンにおける時刻を計算するメソッドがない
- `YYYY/MM/DD`のようなフォーマットに基づいた文字列への変換を提供するメソッドがない
- `YYYY/MM/DD HH:mm`のようなフォーマットに基づいた文字列への変換を提供するメソッドがない

そのため、JavaScriptにおける日付・時刻の処理は、標準のDateではなくライブラリを使うことが一般的になっています。
代表的なライブラリとしては、[moment.js][]や[js-joda][]、[date-fns][]などがあります。
代表的なライブラリとしては、[Day.js][]、[date-fns][]、[js-joda][]、[moment.js][]の後継である[Luxon][]などがあります。
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

moment.jsはdeprecatedなのでLuxonを追加。
Day.jsも一応入れた


<!-- momentが参照できない -->
<!-- Day.jsが参照できない -->
<!-- doctest:disable -->
```js
// moment.jsで現在時刻のmomentオブジェクトを作る
const now = moment();
// Day.jsで現在時刻のDay.jsオブジェクトを作る
const now = dayjs();
Comment on lines -190 to +196
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ここもDay.jsにした。メソッドが一番momentに感覚が近いので。

// addメソッドで10分進める
const future = now.add(10, "minutes");
const future = now.add(10, "minute");
// formatメソッドで任意の書式の文字列に変換する
console.log(future.format("YYYY/MM/DD"));
console.log(future.format("YYYY/MM/DD HH:mm"));
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

これ 10分進めてるのに mm がなかったので

```

<!-- ECMA-402 と Temporalについてを書く -->
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

これどうしようかすごい迷う。
[ECMA-402][] で国際化が進められているのと、temporalはすごい微妙な時期。

ライブラリにずっと依存してるんじゃなくて、仕様としてもDateを直そうと進んでいるよって雰囲気を書きたいけど、Proposal段階だからどうするかなーという感じ。
名前を出すべきかどうか。

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

#1495 (comment)
次のミーティングアジェンダに入れた


## まとめ {#conclusion}

この章では、Dateオブジェクトについて学びました。
Expand All @@ -212,5 +219,8 @@ console.log(future.format("YYYY/MM/DD"));
[RFC2822]: https://www.rfc-editor.org/rfc/rfc2822#section-3.3
[ISO 8601]: https://ja.wikipedia.org/wiki/ISO_8601
[moment.js]: https://momentjs.com/
[Luxon]: https://github.com/moment/luxon/
[js-joda]: https://github.com/js-joda/js-joda
[Day.js]: https://day.js.org/
[date-fns]: https://date-fns.org/
[ECMA-402]: https://www.ecma-international.org/publications-and-standards/standards/ecma-402/