adr-rubber-duck
ADR(Architecture Decision Record)の壁打ち相手としてヒアリングを通じて意思決定を整理し、ADRドラフトを作成する
テスト実行速度を分析し、遅いテストのリファクタリング提案を行います
> /plugin marketplace add classmethod/tsumiki > /plugin install tsumiki@tsumiki
How it fires
How this command gets triggered: by you, by Claude, or both.
/test-performance-analysisContext preview
What this command does when you run it.
テスト実行速度を分析し、遅いテストのリファクタリング提案を行います
description: テスト実行速度を分析し、遅いテストのリファクタリング提案を行います
テストスイート全体の実行速度を分析し、遅いテスト(2秒以上)を特定してリファクタリング提案を行います。
**全体の実行時間計測**:
# Jest の場合 npm test -- --verbose --runInBand 2>&1 | tee test-timing-before.log # その他のテストランナーの場合 # pytest: pytest -v --durations=0 # go test: go test -v -timeout 30s ./...
テスト結果から以下の情報を収集:
実行時間を記録し、以下の基準で分類:
**Task tool (subagent_type: Explore, thoroughness: medium)** を使用して、🔴遅いテスト(2秒以上)のファイルを探索し、以下の観点で分析:
1. **データベースアクセス**
2. **ファイルI/O**
3. **外部依存**
4. **非同期処理**
5. **セットアップ/ティアダウン**
6. **テストデータ**
分析結果に基づき、適用可能なリファクタリングパターンを提案:
**適用条件**: beforeEach でデータのクリア・再投入を行っている
**提案**:
// Before
beforeEach(async () => {
await db.query('DELETE FROM users');
await db.query('INSERT INTO users ...');
});
// After: トランザクションでロールバック
let transaction;
beforeEach(async () => {
transaction = await db.transaction();
});
afterEach(async () => {
await transaction.rollback();
});**適用条件**: fs.readFile, fs.writeFile などの実ファイル操作
**提案**:
// Before
await fs.writeFile('./config.json', data);
// After: モック化
jest.mock('fs/promises');
const fs = require('fs/promises');
fs.writeFile.mockResolvedValue();**適用条件**: fetch, axios などの外部HTTP通信
**提案**:
// Before
const data = await fetch('https://api.example.com/users');
// After: MSWでモック
import { setupServer } from 'msw/node';
import { rest } from 'msw';
const server = setupServer(
rest.get('https://api.example.com/users', (req, res, ctx) => {
return res(ctx.json([{id: 1, name: 'Test'}]));
})
);**適用条件**: 読み取り専用のテストでデータを変更しない
**提案**:
// Before
beforeEach(async () => {
testData = await generateComplexData(); // 各テストで実行
});
// After: 一度だけ実行
beforeAll(async () => {
testData = await generateComplexData(); // 一度だけ
});**適用条件**: setTimeout, sleep などの固定待機時間
**提案**:
// Before
await new Promise(resolve => setTimeout(resolve, 5000));
// After: 条件ベースの待機
await waitFor(async () => {
const status = await getStatus();
return status === 'completed';
}, {timeout: 5000, interval: 100});**適用条件**: 複雑なデータ構造を毎回生成している
**提案**:
// Before
const user = {
id: 1, name: 'Test', email: 'test@example.com',
address: { /* 詳細 */ }, preferences: { /* 詳細 */ }
};
// After: ファクトリー関数
function createUser(overrides = {}) {
return { id: 1, name: 'Test', ...overrides };
}
const user = createUser({ name: 'Custom' });**AskUserQuestion** ツールを使用して、以下を確認:
提案されたパターンを1つずつ適用:
1. **1つのテストファイルを選択** 2. **提案されたパターンを適用** 3. **テストを実行して確認**
npm test -- <test-file>
4. **実行時間を記録** 5. **次のファイルへ**
各改善後:
# 改善後の実行時間を計測 npm test -- --verbose --runInBand 2>&1 | tee test-timing-after.log
改善前後を比較:
改善レポートを作成し、以下の情報を記録:
# テスト実行速度改善レポート ## 改善サマリー - 改善前の総実行時間: XX.X秒 - 改善後の総実行時間: XX.X秒 - 短縮時間: XX.X秒(XX%削減) - 改善対象テスト数: XX個 ## 遅いテストの詳細 ### 1. `test/user.test.js` - 15.2秒 → 2.1秒(86%削減) - **原因**: 各テストでDB接続・切断を繰り返し - **適用パターン**: トランザクショナルテスト - **改善内容**: - beforeEach でトランザクション開始 - afterEach でロールバック - **効果**: 13.1秒短縮 ### 2. `test/file-processor.test.js` - 8.5秒 → 0.3秒(96%削減) - **原因**: 実ファイルへの書き込み - **適用パターン**: ファイルI/Oのモック化 - **改善内容**: - mock-fs を使用 - メモリ上でファイル操作 - **効果**: 8.2秒短縮 ## まだ遅いテスト(2秒以上) ### 1. `test/integration.test.js` - 5.3秒 - **原因**: 統合テストとして複数の処理を実行 - **推奨**: E2Eテストとして分離を検討 - **優先度**: 中 ## 推奨される次のステップ 1. 統合テストのE2E化の検討 2. テストデータファクトリーの導入 3. 並列実行の最適化(--maxWorkers調整) ## 適用したリファクタリングパターン 1. データベーストランザクション: 3ファイル 2. ファイルI/Oのモック化: 2ファイル 3. 外部APIのモック化: 1ファイル 4. beforeEach → beforeAll: 2ファイル
レポートを以下のファイルに保存:
これらは別のテストスイート(`test:e2e`, `test:integration`)として分離を推奨
TsumikiはAI駆動開発のためのフレームワークです。要件定義から実装まで、AIを活用した効率的な開発プロセスを提供します。 基本的にClaude Codeをサポートしますが、それ以外のツールでも使用できます。Claude Code以外のツールでtsumikiを使用する を参照してください。
Repo: classmethod/tsumiki
ADR(Architecture Decision Record)の壁打ち相手としてヒアリングを通じて意思決定を整理し、ADRドラフトを作成する
テストエラーを解消するための自動デバッグプロセス。全テストケースの確認からエラー原因の調査、修正まで段階的に実行し、テストケースの成功率向上を目指します。
ビルドエラー(コンパイルエラー、型エラー、依存パッケージ未解決)を自動的に分析・修正します。auto-debugから委譲される他、ユーザが直接呼び出すことも可能です。
システムの各レイヤーにおける包括的なエッジケース・エラー状態を詳細に分析し、見落としがちな異常系シナリオを洗い出します