Next.js 12でJestの設定がかなり楽になった
Next.js 12 における Jest サポートの強化
2/18 に Next.js 12.1 がリリースされました。
本バージョンの新機能として「next/jest
プラグインを使った Zero-configuration Jest のサポート」が挙げられています。
この新機能自体は Next.js 12.0 の時点からベータ版として利用できるようにはなっていましたが、この度安定版がリリースされた形となります。
next/jest
プラグインを使って Next.js アプリのテスト環境を構築する
next/jest
プラグインを使う方法は以下の2点が挙げられます。
新規でアプリを作る際、時間がないときは1番の方法を取ってもいいでしょう。今回は2番の方法を紹介します。
(テンプレートが TS で書かれているのは地味に嬉しいポイント)
-
create-next-app
コマンドでテンプレートから新規アプリを作る -
next/jest
プラグインを使用する方法
サンプルアプリのリポジトリはこちら。
必要なライブラリのインストール
Jest/React Testing Library を入れないことには何も始まらないのでまずインストールします。
npm install --save-dev jest @testing-library/react @testing-library/jest-dom
# or
yarn add -D jest @testing-library/react @testing-library/jest-dom
従来の方法では babel を使ってきましたが、next/jest
プラグインでは使用しないため、インストール不要です。
また TS で Jest を使用する際は、ts-jest
や @types/jest
のインストールが必要になりますが、next/jest
プラグインを介す場合はこれらのインストールは不要です。
設定ファイルの作成
jest.config.js
を作成します。Next.js 12 に搭載されたSWCの恩恵で簡潔な記述が可能になりました。
基本は公式で書かれている以下の書き方で問題ありません。
const nextJest = require("next/jest");
const createJestConfig = nextJest({
// next.config.jsとテスト環境用の.envファイルが配置されたディレクトリをセット。基本は"./"で良い。
dir: "./",
});
// Jestのカスタム設定を設置する場所。従来のプロパティはここで定義。
const customJestConfig = {
// jest.setup.jsを作成する場合のみ定義。
// setupFilesAfterEnv: ["<rootDir>/jest.setup.js"],
moduleNameMapper: {
// aliasを定義 (tsconfig.jsonのcompilerOptions>pathsの定義に合わせる)
"^@/components/(.*)$": "<rootDir>/components/$1",
"^@/pages/(.*)$": "<rootDir>/pages/$1",
},
testEnvironment: "jest-environment-jsdom",
};
// createJestConfigを定義することによって、本ファイルで定義された設定がNext.jsの設定に反映されます
module.exports = createJestConfig(customJestConfig);
今回定義した `tsconfig.json`
{
"compilerOptions": {
"target": "es5",
"lib": ["dom", "dom.iterable", "esnext"],
"allowJs": true,
"skipLibCheck": true,
"strict": true,
"forceConsistentCasingInFileNames": true,
"noEmit": true,
"esModuleInterop": true,
"module": "esnext",
"moduleResolution": "node",
"resolveJsonModule": true,
"isolatedModules": true,
"jsx": "preserve",
"incremental": true,
"baseUrl": ".",
"paths": {
"@/components/*": ["components/*"],
"@/pages/*": ["pages/*"]
}
},
"include": ["next-env.d.ts", "**/*.ts", "**/*.tsx"],
"exclude": ["node_modules"]
}
next/jest
プラグインを使った場合の、jest.config.js
のメリットを簡単にまとめておくと、以下の点が挙げられます。
-
transform
の記載が不要(SWC が自動で transform してくれる) - css/scss ファイル/画像ファイルのモック化が自動で行われる
-
testPath
からnode_modules
/.next
フォルダがデフォルトで無視される -
transform
からnode_modules
フォルダがデフォルトで無視される
殆どのケースで設定しなければいけない内容を自動で処理してくれるおかげで、従来の babel を使用した場合と比べて、セットアップの負担の軽減が見て取れます。
テスト書いて動かしてみる
それでは、試しにコンポーネントのテストを書いてみましょう。書き方は従来どおりです。
export const Sample = () => {
return (
<main>
<h1>Nextjs+Jestのサンプルサプリ</h1>
<p>設定がすごく楽になりました。</p>
</main>
);
};
import { Sample } from "@/components/Sample";
import { render } from "@testing-library/react";
describe("Sampleコンポーネント", () => {
test("should first", () => {
const { getByText } = render(<Sample />);
expect(getByText("Nextjs+Jestのサンプルサプリ")).toBeTruthy();
expect(getByText("設定がすごく楽になりました。")).toBeTruthy();
});
});
そして package.json
の scripts も編集しておきましょう。
{
"scripts": {
"dev": "next dev",
"build": "next build",
"start": "next start",
+ "test": "jest --watch",
"lint": "next lint"
},
}
これで yarn(npm run) test
を叩ければ、テストが通ります 🎉。
トラブルがあったとき
ここまでメリットを紹介してきましたが、従来の babel を使用した方法から大きく変わる&登場したばかりの機能のため、まだトラブルがあったときのサポートが整ってるとは言い難いです。
Next.js はリポジトリに issues とは別に Discussion 機能が用意されており、next/jest
プラグインに関するスレッドが用意されています。何かあればここを参考にしてみるのもいいでしょう。
Discussion
参考にさせていただきました!ありがとうございます。
同じ内容で
yarn test
を実行すると下記のエラーになり実行できませんでした。jestのv28から
est-environment-jsdom
を別途インストールする必要があるようです。公式
余計なお世話であればすみません🙇♂️