Jestとは?
JestはFacebookが開発したJavaScriptのテスティングフレームワークで、Reactアプリケーションをはじめとする多くのJavaScriptプロジェクトで利用されています。設定が少なく、シンプルな構文でテストを書けることから、人気の高いテストツールです。
- 公式サイト: https://jestjs.io/
- 対応言語: JavaScript, TypeScript
特徴
- ✅ ゼロコンフィグで即利用可能
- ✅ テストの高速実行(並列処理)
- ✅ スナップショットテストによるUI検証
- ✅ 柔軟なモック機能
- ✅ TypeScript対応(
ts-jest
との併用)
Jestのインストール方法
JavaScriptプロジェクトの場合
$ npm install --save-dev jest
or
$ yarn add --dev jest
TypeScriptとの連携
TypeScriptを使っている場合、ts-jestを使って簡単に統合できます。
$ npm install --save-dev ts-jest @types/jest
$ npx ts-jest config:init
package.jsonの設定
{
"scripts": {
"test": "jest"
}
}
テストしてみる
ここでは、sum.js
ファイル内のsum
関数をテストしてみる
function sum(a, b) {
return a + b;
}
module.exports = sum;
const sum = require('./sum');
test('adds 1 + 2 to equal 3', () => {
expect(sum(1, 2)).toBe(3);
});
テストの実行
$ npm test
Jest基本構文(describe
, test
, expect
の使い方)
Jestでは、テストコードを読みやすく整理し、目的ごとにグルーピングして書けます。
1. describe
: テストのグルーピング
describe
ブロックは、テストをグループ化して意味のある単位にまとめるのに使います。
describe('配列の操作', () => {
test('配列に要素を追加できる', () => {
const arr = [];
arr.push(1);
expect(arr).toHaveLength(1);
});
test('配列から要素を削除できる', () => {
const arr = [1, 2];
arr.pop();
expect(arr).toEqual([1]);
});
});
✔ メリット
- テストの構造が明確になる
- テストの出力に階層構造が反映され、読みやすくなる
2. test
と it
: テストケースの定義
test('1 + 2 = 3になる', () => {
expect(1 + 2).toBe(3);
});
test と it は完全に同じ動作をします。好みに応じて使い分けられます。
it('1 + 2 = 3になる', () => {
expect(1 + 2).toBe(3);
});
it は「〇〇すべきだ(it should...)」というBDDスタイルで好まれる
3. expect
: アサーション(期待値)
expect は、ある値がどうなるべきかを定義するテストの核心部分です。
expect(actual).matcher(expected);
主な matcher 一覧
Matcher | 説明 | 例 |
---|---|---|
toBe(value) | 厳密な一致(===) | expect(1 + 2).toBe(3) |
toEqual(obj) | オブジェクト/配列の再帰的一致 | expect({a: 1}).toEqual({a: 1}) |
toContain(item) | 配列や文字列に含まれる | expect(['a', 'b']).toContain('a') |
toHaveLength(n) | .lengthが特定の値 | expect([1, 2]).toHaveLength(2) |
toBeTruthy() | trueとして扱われる | expect(value).toBeTruthy() |
toBeFalsy() | falseとして扱われる | expect('').toBeFalsy() |
toThrow() | 例外がスローされる | expect(() => fn()).toThrow() |
resolves, rejects | Promiseに対するアサーション | await expect(Promise.resolve(1)).resolves.toBe(1) |
4. 非同期テストの書き方
async/await を使う
test('データを非同期に取得', async () => {
const data = await fetchData();
expect(data).toBeDefined();
});
Promiseで書く
test('Promiseが成功する', () => {
return expect(Promise.resolve(5)).resolves.toBe(5);
});
5. beforeEach / afterEach などのフック
テストごとの事前・事後処理に使います。
beforeEach(() => {
// 各テストの前に実行
});
afterEach(() => {
// 各テストの後に実行
});
また、1回だけ実行したい場合は beforeAll / afterAll を使います。
✅ 実例:すべての構文をまとめたサンプル
describe('User モジュール', () => {
let users = [];
beforeEach(() => {
users = ['Taro', 'Hanako'];
});
test('ユーザーを追加できる', () => {
users.push('Ichiro');
expect(users).toContain('Ichiro');
});
test('ユーザーを削除できる', () => {
users.pop();
expect(users).not.toContain('Hanako');
});
});
スナップショットテスト
ReactなどのUIコンポーネントの出力が変化していないかを検証できます。
import renderer from 'react-test-renderer';
import MyComponent from './MyComponent';
test('snapshot test', () => {
const tree = renderer.create(<MyComponent />).toJSON();
expect(tree).toMatchSnapshot();
});
モックの使い方
関数やモジュールの動作をモック(偽の動作)に置き換えて、依存を排除してテストできます。
-
関数のモック
const fetchData = jest.fn(() => 'mocked data'); test('returns mocked data', () => { expect(fetchData()).toBe('mocked data'); });
-
モジュールのモック
jest.mock('./api'); import { fetchUser } from './api'; fetchUser.mockResolvedValue({ name: 'Taro' }); test('mock API response', async () => { const user = await fetchUser(); expect(user.name).toBe('Taro'); });