JA Testing Testing Strategy - hiraishikentaro/rails-factorybot-jump GitHub Wiki
テスト: テスト戦略
テスト哲学
Rails FactoryBot Jump は、信頼性、保守性、現実的なテスト環境を重視する包括的なテスト戦略に従います。戦略は、分離されたコンポーネントのユニットテストと VSCode API インタラクションのインテグレーションテストのバランスを取ります。
テストフレームワークアーキテクチャ
コアテストスタック
プライマリフレームワーク: Mocha 10.8.2
- 柔軟なテスト構成を持つ JavaScript テストフレームワーク
- 非同期テストのサポート
- 豊富なアサーションライブラリ統合
- VSCode 操作用のカスタムタイムアウト処理
VSCode テスト環境: @vscode/test-electron 2.4.1
- 実際の VSCode Extension Development Host でテストを実行
- テスト中の完全な VSCode API アクセス
- ファイルシステム統合を含む現実的なテスト環境
- クロスプラットフォームテストサポート
モックフレームワーク: Sinon 17.0.1
- 包括的なモックとスタブ機能
- 分離されたユニットテスト用の VSCode API モック
- ファイルシステム操作モック
- 呼び出し検証と動作テスト
テスト環境設定
テストランナーセットアップ (src/test/runTest.ts
):
import { runTests } from "@vscode/test-electron";
async function main() {
const extensionDevelopmentPath = path.resolve(__dirname, "../../");
const extensionTestsPath = path.resolve(__dirname, "./suite/index");
await runTests({
extensionDevelopmentPath,
extensionTestsPath,
});
}
利点:
- 実際の VSCode 環境でのテスト
- 実際の拡張機能アクティベーションと非アクティベーション
- 真のファイルシステム操作
- 本物のユーザーインタラクションシミュレーション
ソース: src/test/runTest.ts
テストレベル
1. ユニットテスト
スコープ: 分離された個別のコンポーネントと関数
ターゲットコンポーネント:
- ファクトリー検出正規表現パターン(
src/utils/regexPatterns.ts
) - キャッシュ管理操作(
src/services/cacheManager.ts
) - 設定解析ロジック(
src/services/configurationManager.ts
) - リンク生成アルゴリズム
- データモデル(
src/models/factory.ts
,location.ts
,trait.ts
) - ファクトリーパーサー(
src/services/factoryParser.ts
)
モック戦略:
// 例: VSCode ワークスペース API をモック
const mockWorkspace = {
findFiles: sinon.stub(),
getConfiguration: sinon.stub(),
createFileSystemWatcher: sinon.stub(),
};
// 例: ファイルシステム操作をモック
const mockFs = {
readFile: sinon.stub(),
stat: sinon.stub(),
};
分離の利点:
- 高速なテスト実行
- 予測可能なテスト条件
- 特定のロジックの簡単なデバッグ
- 明確な失敗の帰属
2. インテグレーションテスト
スコープ: VSCode API とファイルシステムとのコンポーネントインタラクション
統合ポイント:
- ドキュメントリンクプロバイダー登録
- ファイルシステムウォッチャー機能
- 設定変更処理
- コマンド実行ワークフロー
実環境テスト:
// 例: 実際の VSCode ドキュメントでテスト
const document = await vscode.workspace.openTextDocument(testFileUri);
const provider = new FactoryLinkProvider();
const links = provider.provideDocumentLinks(document);
統合の利点:
- 現実的な API 動作テスト
- クロスコンポーネントインタラクション検証
- エンドツーエンドワークフロー検証
- プラットフォーム固有の動作テスト
3. システムテスト
スコープ: 現実的なシナリオでの完全な拡張機能
テストシナリオ:
- 拡張機能アクティベーションと非アクティベーション
- ファクトリーファイル検出と解析
- リンク生成とナビゲーション
- 設定更新とキャッシュ更新
ユーザーワークフローシミュレーション:
// 完全なユーザーワークフローをシミュレート
await activateExtension();
await openRubyTestFile();
await hoverOverFactoryCall();
await clickFactoryLink();
await verifyNavigationToFactory();
テストカテゴリ
1. コア機能テスト
ファクトリー検出テスト:
suite("ファクトリー検出", () => {
test("基本的なファクトリー呼び出しを検出", () => {
const text = "user = create(:user)";
const matches = detectFactoryCalls(text);
assert.strictEqual(matches.length, 1);
assert.strictEqual(matches[0].factoryName, "user");
});
test("トレイト付きファクトリー呼び出しを検出", () => {
const text = "admin = create(:user, :admin, :verified)";
const matches = detectFactoryCalls(text);
assert.strictEqual(matches[0].factoryName, "user");
assert.deepStrictEqual(matches[0].traits, ["admin", "verified"]);
});
});
キャッシュ管理テスト:
suite("キャッシュ管理", () => {
test("ファイルからファクトリーキャッシュを構築", async () => {
const provider = new FactoryLinkProvider();
await provider.initializeFactoryFiles();
const cache = provider.getFactoryCache();
assert.ok(cache.has("user"));
assert.ok(cache.has("post"));
});
test("ファイル変更時にキャッシュを更新", async () => {
// キャッシュ無効化と再構築をテスト
});
});
2. 設定テスト
設定処理テスト:
suite("設定", () => {
test("デフォルトファクトリーパスを使用", () => {
const config = getDefaultConfiguration();
assert.deepStrictEqual(config.factoryPaths, ["spec/factories/**/*.rb"]);
});
test("カスタムファクトリーパスを尊重", async () => {
await updateConfiguration({
factoryPaths: ["test/factories/**/*.rb", "lib/factories/**/*.rb"],
});
const provider = new FactoryLinkProvider();
const paths = provider.getFactoryPaths();
assert.strictEqual(paths.length, 2);
});
});
3. エッジケーステスト
エラーハンドリングテスト:
suite("エラーハンドリング", () => {
test("ファクトリーファイル不足を適切に処理", async () => {
// ファイルシステムが空の結果を返すようモック
const provider = new FactoryLinkProvider();
await provider.initializeFactoryFiles();
// エラーを投げるべきではない
});
test("不正なファクトリーファイルを処理", async () => {
// 無効な Ruby 構文でテスト
});
test("権限エラーを処理", async () => {
// ファイルシステム権限エラーをモック
});
});
パフォーマンステスト:
suite("パフォーマンス", () => {
test("大量のファクトリーファイルを処理", async () => {
// 100+ ファクトリーファイルでテスト
const startTime = Date.now();
await provider.initializeFactoryFiles();
const duration = Date.now() - startTime;
assert.ok(duration < 5000, "初期化は5秒以内に完了すべき");
});
test("大きなドキュメントのリンクを効率的に提供", () => {
// 大きなテストファイルでテスト
});
});
この包括的なテスト戦略により、拡張機能は、サポートされるすべてのプラットフォームとユースケースで高品質、信頼性、パフォーマンスを維持します。