技術とかの雑なToday I Learnedメモ

propsのnull、テストでシステム時間を固定する

propsのnull、テストでシステム時間を固定する

propsのnull

Date | null型の値をpropsで受け取ろうとして以下のように書いた。

props: {
  date: {
    type: Date as PropType<Date | null>,
    required: true
  }
}

だがこれ、テストでnullを渡したときに怒られたんですよね。

Invalid prop: type check failed for prop ... Expected Date, got Null.

たぶんだけど、prop.dateをnullにしたい場合は親からは渡さずにdefault: nullを指定しないといけないんだと思うんだけど、nullという値をpropsで渡したい場合はどうするのだろうか。

そもそもnullをpropsとして渡す設計自体がおかしい……?

テストでシステム時間を固定する

Jestでテストするときに時間を固定しておきたかったので調べた。

テストを実行するたびに時間が変わるというやつ、色々問題があると思うけどすんなり言語化はできないので調べたり考えたりしてまとめておきたい。

jestで現在時刻を固定化する - Qiita

タイマーモック · Jest

こういうのがあるのか。知らなかった。

jest.useFakeTimers()jest.setSystemTime(testDate)でシステム時間を固定でき、これをテスト後に開放するのにjest.useRealTimers()を使うらしい。

JavaScriptを単体テストする流行りのフレームワークJestを試してみる - Qiita

ただこれを見ると、

setSystemTimeで偽の時間を指定することができます。ただし、これはuseFakeTimersでmodernを指定した時のみ有効です。

と書いてあった。

結論、指定してもしなくても動かなかったので自分の手元の環境に問題がありそう。

【Jest】new Date()をモック化する方法 - Qiita

これの方法2のgolablのDateをspyにすることで解決した。

const dateSpy = jest.spyOn(global, 'Date')
beforeAll(() => {
  dateSpy.mockImplementation(() => mockDate as unknown as string)
})

afterAll(() => {
  dateSpy.mockRestore()
})

こんな感じ。

1/26mockRestore()のことをメモっていたので助かった。

なぜsetSystemTimeがうまく動かなかったのかは今後調べたいし、あとmockDate as unknown as stringの書き方(type assertionつなげるやつ)も見慣れてなくて戸惑った。