Open4

Vitestのテクニック

じょうげんじょうげん
expect(screen.getAllByRole("alert")).some.toHaveTextContent("notice")

expect(screen.getAllByRole("alert")).every.toHaveTextContent("notice")

このようなJest / Vitest Matcherが欲しい

じょうげんじょうげん

https://github.com/vitest-dev/vitest/issues/7629

ここで提案したところ、このような使い方を教えてもらえた。

expect(array).toEqual(expect.arrayContaining([expect.toHaveTextContent('expected')]))

expect.arrayContainingにmatcherをstaticな形式で渡すと配列のいずれかがmatcherにマッチする場合にテストに通るsomeのようなものを表現可能なようです。
実際に走らせて成功と失敗を確認しました。
expect.arrayContainingは知っていましたが、それ以外のmatcherもstaticに呼び出せることを知りませんでした…!
asymmetric matcherというそうです。

じょうげんじょうげん

flakyなテストが通過することを確認する

test.for(Array(10))("testcase", () => {})

.for(Array(10))の部分を足して数字の部分を変えて実行することで確認できる。

じょうげんじょうげん

Vitest Browser Modeで再書き込みができないモジュールをMockする

以下はwindow.location.assign()をモック化する例

vite.config.ts
const mockLocationPlugin: Plugin = {
  name: "mock-location",
  transform: (code, id) => {
    if (id.includes("/node_modules/")) return;
    return code.replaceAll("window.location", "__MOCK__LOCATION__");
  },
};

export default defineConfig(({ mode }) => {
          plugins:[...(mode === "test" ? [mockLocationPlugin] : []),],
          test:{...},
}
test.ts
const assign = vi.fn();
vi.stubGlobal("__MOCK__LOCATION__", { location: { assign } });

expect(assign).toHaveBeenCalledWith("https://example.com");

browser APIの中にはプロパティへの書き込みが禁止されており、モック化関数を使えないものがある。
そのような関数の呼び出しを確認するテストを書きたい場合のハック。
Viteのプラグインとして、実装側のコードを書き換えるものを用意し、テストの時だけ実行する。
このようにすることでテスト時にstub化が可能になる!