T-CREATOR

5 分で導入!Vite × Vitest 型付きユニットテスト環境の最短手順

5 分で導入!Vite × Vitest 型付きユニットテスト環境の最短手順

現代のフロントエンド開発において、高速なビルドツールと効率的なテスト環境は欠かせません。Vite と Vitest の組み合わせは、そんな理想的な開発環境を驚くほど簡単に構築できる方法です。本記事では、わずか 5 分で TypeScript 対応のユニットテスト環境を構築する最短手順をご紹介します。

背景

従来のテスト環境構築では、設定ファイルの複雑な調整や依存関係の解決に多くの時間を要していました。特に TypeScript プロジェクトでは、型定義の設定やトランスパイルの設定など、初心者には難しい作業が必要でした。

Vite と Vitest の組み合わせは、この問題を解決します。Vite の高速な開発サーバーと Vitest のシンプルな設定により、最小限の労力で本格的なテスト環境を構築できるのです。

mermaidflowchart LR
  developer[開発者] -->|5分で設定| vite[Vite プロジェクト]
  vite -->|統合| vitest[Vitest テスト環境]
  vitest -->|型安全| typescript[TypeScript サポート]
  typescript -->|高速実行| test_result[テスト結果]

図で理解できる要点:

  • Vite プロジェクトから始めて、Vitest を統合する流れ
  • TypeScript サポートが標準で含まれる
  • 5 分という短時間で完全な環境が構築される

課題

多くの開発者が直面するテスト環境構築の課題は以下の通りです:

課題従来の方法Vite × Vitest
設定の複雑さJest + Babel の複雑な設定最小限の設定で動作
起動時間遅いテスト起動高速な起動とホットリロード
TypeScript 対応追加設定が必要標準でサポート
開発体験設定に時間を取られる即座にテスト開発に集中

これらの課題を解決するため、Vite × Vitest の組み合わせが注目されています。

解決策

以下の 5 つのステップで、型付きユニットテスト環境を構築します。

mermaidflowchart TD
  step1[Step1: プロジェクト初期化] -->|1分| step2[Step2: Vitest設定]
  step2 -->|2分| step3[Step3: TypeScript設定]
  step3 -->|1分| step4[Step4: テスト実行確認]
  step4 -->|1分| complete[完成]

  step1 -.->|並行作業| pkg[パッケージ導入]
  step2 -.->|設定ファイル| config[vite.config.ts]
  step3 -.->|型定義| types[テスト用型定義]

この流れにより、わずか 5 分で本格的なテスト環境が完成します。

プロジェクトセットアップ(1 分)

Vite プロジェクトの初期化

まず、Vite を使って TypeScript プロジェクトを作成します。以下のコマンドを実行してください。

typescriptyarn create vite my-test-project --template vanilla-ts

このコマンドにより、TypeScript 対応の Vite プロジェクトが作成されます。プロジェクト名は my-test-project としていますが、お好みの名前に変更可能です。

作成後、プロジェクトディレクトリに移動します。

bashcd my-test-project

必要パッケージのインストール

次に、基本的な依存関係をインストールします。

bashyarn install

続いて、Vitest とテストに必要なパッケージを追加します。

bashyarn add -D vitest @vitest/ui jsdom @testing-library/jest-dom

各パッケージの役割は以下の通りです:

  • vitest: テストランナー本体
  • @vitest​/​ui: テスト結果の UI 表示
  • jsdom: ブラウザ環境のシミュレーション
  • @testing-library​/​jest-dom: DOM 要素のマッチャー拡張

Vitest 設定(2 分)

vite.config.ts の設定

プロジェクトルートにある vite.config.ts ファイルを以下のように設定します。

typescriptimport { defineConfig } from 'vite';

export default defineConfig({
  // 開発サーバーの設定
  server: {
    port: 3000,
  },
});

次に、Vitest 用の設定を追加します。同じファイルを以下のように更新してください。

typescript/// <reference types="vitest" />
import { defineConfig } from 'vite';

export default defineConfig({
  // 開発サーバーの設定
  server: {
    port: 3000,
  },
  // テスト設定
  test: {
    globals: true,
    environment: 'jsdom',
    setupFiles: ['./src/test/setup.ts'],
  },
});

test 用設定の追加

テストのセットアップファイルを作成します。src​/​test​/​setup.ts ファイルを作成してください。

bashmkdir -p src/test
touch src/test/setup.ts

作成したファイルに以下の内容を記述します。

typescriptimport '@testing-library/jest-dom';

// グローバルなテスト設定をここに記述
global.console = {
  ...console,
  // テスト実行時の不要なログを抑制
  log: jest.fn(),
  debug: jest.fn(),
  info: jest.fn(),
  warn: jest.fn(),
};

この設定により、テスト実行時のより良い開発体験が提供されます。

TypeScript 型定義設定(1 分)

tsconfig.json の調整

既存の tsconfig.json を確認し、テスト用の設定を追加します。

json{
  "compilerOptions": {
    "target": "ES2020",
    "useDefineForClassFields": true,
    "module": "ESNext",
    "lib": ["ES2020", "DOM", "DOM.Iterable"],
    "skipLibCheck": true,
    "moduleResolution": "bundler",
    "allowImportingTsExtensions": true,
    "resolveJsonModule": true,
    "isolatedModules": true,
    "noEmit": true,
    "strict": true,
    "noUnusedLocals": true,
    "noUnusedParameters": true,
    "noFallthroughCasesInSwitch": true
  }
}

テスト用型定義の追加

tsconfig.json にテスト関連の型定義を追加します。

json{
  "compilerOptions": {
    // 既存の設定...
    "types": ["vitest/globals", "@testing-library/jest-dom"]
  },
  "include": [
    "src/**/*",
    "src/**/*.test.ts",
    "src/**/*.spec.ts"
  ]
}

この設定により、テストファイル内で Vitest の関数や型定義が正しく認識されるようになります。

初回テスト実行(1 分)

サンプルテストの作成

実際にテストが動作することを確認するため、サンプルファイルとテストを作成します。

まず、テスト対象となる関数を src​/​utils​/​math.ts に作成します。

typescript/**
 * 2つの数値を足し算する関数
 * @param a 第一引数
 * @param b 第二引数
 * @returns 足し算の結果
 */
export function add(a: number, b: number): number {
  return a + b;
}

/**
 * 2つの数値を掛け算する関数
 * @param a 第一引数
 * @param b 第二引数
 * @returns 掛け算の結果
 */
export function multiply(a: number, b: number): number {
  return a * b;
}

次に、対応するテストファイル src​/​utils​/​math.test.ts を作成します。

typescriptimport { describe, it, expect } from 'vitest';
import { add, multiply } from './math';

describe('Math Utils', () => {
  describe('add function', () => {
    it('should add two positive numbers correctly', () => {
      expect(add(2, 3)).toBe(5);
    });

    it('should handle negative numbers', () => {
      expect(add(-1, 1)).toBe(0);
      expect(add(-2, -3)).toBe(-5);
    });

    it('should handle zero', () => {
      expect(add(0, 5)).toBe(5);
      expect(add(10, 0)).toBe(10);
    });
  });

  describe('multiply function', () => {
    it('should multiply two positive numbers correctly', () => {
      expect(multiply(3, 4)).toBe(12);
    });

    it('should handle zero multiplication', () => {
      expect(multiply(5, 0)).toBe(0);
      expect(multiply(0, 10)).toBe(0);
    });
  });
});

テスト実行コマンドの確認

package.json にテスト実行用のスクリプトを追加します。

json{
  "scripts": {
    "dev": "vite",
    "build": "tsc && vite build",
    "preview": "vite preview",
    "test": "vitest",
    "test:ui": "vitest --ui",
    "test:run": "vitest run",
    "test:coverage": "vitest run --coverage"
  }
}

これで、以下のコマンドでテストを実行できます。

bash# ウォッチモードでテスト実行
yarn test

# UI付きでテスト実行
yarn test:ui

# 一回だけテスト実行
yarn test:run

実際にテストを実行して、正常に動作することを確認してください。

bashyarn test:run

成功すると、以下のような出力が表示されます:

scsssrc/utils/math.test.ts (5)
   ✓ Math Utils (5)
     ✓ add function (3)
       ✓ should add two positive numbers correctly
       ✓ should handle negative numbers
       ✓ should handle zero
     ✓ multiply function (2)
       ✓ should multiply two positive numbers correctly
       ✓ should handle zero multiplication

Test Files  1 passed (1)
Tests  5 passed (5)

具体例

実際の開発ワークフロー

構築した環境での実際の開発フローを示します。

mermaidsequenceDiagram
  participant dev as 開発者
  participant vite as Vite Dev Server
  participant vitest as Vitest
  participant ts as TypeScript

  dev ->>+ vite: yarn dev (開発サーバー起動)
  dev ->>+ vitest: yarn test (テストウォッチ開始)

  loop 開発サイクル
    dev ->>+ ts: コード変更
    ts -->>- vitest: 型チェック
    vitest -->>- dev: テスト結果表示
    vitest ->>+ vite: ホットリロード
    vite -->>- dev: 画面更新
  end

この流れにより、コード変更と同時にテストが実行され、即座にフィードバックを得られます。

高度なテストパターン

作成した環境では、以下のような高度なテストパターンも簡単に実装できます。

typescriptimport {
  describe,
  it,
  expect,
  vi,
  beforeEach,
} from 'vitest';

describe('Advanced Test Patterns', () => {
  beforeEach(() => {
    // 各テスト前の共通処理
    vi.clearAllMocks();
  });

  it('should handle async operations', async () => {
    const asyncFunction = async (delay: number) => {
      return new Promise((resolve) =>
        setTimeout(() => resolve('完了'), delay)
      );
    };

    const result = await asyncFunction(100);
    expect(result).toBe('完了');
  });

  it('should mock external dependencies', () => {
    const mockFn = vi.fn(() => 'モック結果');
    expect(mockFn()).toBe('モック結果');
    expect(mockFn).toHaveBeenCalledTimes(1);
  });
});

まとめ

Vite と Vitest を組み合わせることで、わずか 5 分という短時間で本格的な TypeScript 対応ユニットテスト環境を構築できました。

この環境の主な利点をまとめると以下の通りです:

  • 高速性: Vite の高速なビルドと Vitest のホットリロード
  • 型安全性: TypeScript の型チェックが標準で利用可能
  • 開発体験: 最小限の設定で最大限の機能を提供
  • 拡張性: 必要に応じて追加設定や機能拡張が容易

今回構築した環境は、小規模なプロジェクトから大規模な開発まで対応できる堅牢な基盤となります。ぜひ、日々の開発で Vite × Vitest の快適さを体験してみてください。

継続的なテスト実行により、コードの品質向上と開発効率の向上を実現できるでしょう。

関連リンク