npx claudepluginhub caphtech/claude-marketplace --plugin mobile-pluginWant just this skill?
Then install: npx claudepluginhub u/[userId]/[slug]
XCTest/XCUITestを用いたiOSアプリのテスト設計支援スキル。テスト戦略立案、モック/スタブ設計、テストデータ管理、カバレッジ分析を包括的にサポート。Use when: iOSテスト設計、XCTest実装、UITest作成、テストカバレッジ向上、テスト戦略立案、テストダブル設計。
This skill uses the workspace's default tool permissions.
references/test-data.mdreferences/test-doubles.mdreferences/xctest-patterns.mdreferences/xcuitest-patterns.mdiOS Test Design(iOSテスト設計支援)
概要
XCTestおよびXCUITestを活用したiOSアプリケーションのテスト設計を支援するスキル。 デトロイト学派寄りのアプローチを採用し、実際のコンポーネント連携をテストすることで、信頼性の高いテストスイートを構築する。
対象範囲
- Unit Test: XCTestによる単体テスト設計
- Integration Test: コンポーネント間連携テスト
- UI Test: XCUITestによるUIテスト設計
- テストダブル: モック/スタブ/フェイク/スパイの設計
- テストデータ: フィクスチャ、ファクトリ、シード管理
実行条件
以下の状況でこのスキルを起動する:
- iOSアプリのテスト設計・実装を行う時
- 既存テストのリファクタリングを検討する時
- テストカバレッジを向上させたい時
- テストダブル(モック/スタブ)の設計を相談したい時
- テスト戦略を立案したい時
- テストの保守性・可読性を改善したい時
プロセス
Phase 1: テスト対象の分析
1.1 対象コードの理解
- テスト対象のクラス/構造体/関数を特定
- 依存関係を洗い出す
- 公開インターフェースを確認
- 副作用(ネットワーク、永続化、通知等)を特定
1.2 テスト可能性の評価
| 評価項目 | 確認内容 |
|---|---|
| 依存性注入 | コンストラクタ/プロパティ経由で差し替え可能か |
| 副作用の分離 | I/O操作がプロトコル経由で抽象化されているか |
| 状態の観測 | 内部状態の変化を外部から検証可能か |
| 決定論性 | 同一入力に対して同一出力が保証されるか |
Phase 2: テスト戦略の策定
2.1 テストピラミッドの設計
╱╲
╱ ╲ E2E Test(XCUITest): 主要シナリオのみ
╱────╲
╱ ╲ Integration Test: コンポーネント間連携
╱────────╲
╱ ╲ Unit Test: ビジネスロジック中心
╱────────────╲
2.2 テストレベル別の方針
| レベル | 対象 | テストダブル | 実行頻度 |
|---|---|---|---|
| Unit | ビジネスロジック、ViewModel、Utility | スタブ/モック | 常時 |
| Integration | UseCase + Repository、View + ViewModel | スタブ(外部境界のみ) | PR/CI |
| UI | 主要ユーザーフロー | なし(実環境に近づける) | デイリー/リリース |
Phase 3: XCTestによるUnitテスト設計
詳細は references/xctest-patterns.md を参照。
3.1 テストケースの構造
final class SampleTests: XCTestCase {
// MARK: - Properties
private var sut: SystemUnderTest!
private var mockDependency: MockDependency!
// MARK: - Setup/Teardown
override func setUp() {
super.setUp()
mockDependency = MockDependency()
sut = SystemUnderTest(dependency: mockDependency)
}
override func tearDown() {
sut = nil
mockDependency = nil
super.tearDown()
}
// MARK: - Tests
func test_methodName_condition_expectedBehavior() {
// Given(前提条件)
let input = ...
// When(実行)
let result = sut.method(input)
// Then(検証)
XCTAssertEqual(result, expected)
}
}
3.2 命名規則
test_<対象メソッド>_<条件>_<期待される振る舞い>
例:
test_login_withValidCredentials_returnsSuccess
test_fetchUser_whenNetworkError_throwsError
test_calculate_withNegativeInput_returnsZero
Phase 4: テストダブルの設計
詳細は references/test-doubles.md を参照。
4.1 テストダブルの種類と使い分け
| 種類 | 用途 | 実装例 |
|---|---|---|
| Stub | 事前定義した値を返す | stub.returnValue = expectedData |
| Mock | 呼び出しを検証する | XCTAssertTrue(mock.didCallMethod) |
| Fake | 軽量な実装 | InMemoryUserRepository |
| Spy | 呼び出し履歴を記録 | spy.calledArguments |
4.2 プロトコルベースのテストダブル
// 抽象化されたプロトコル
protocol UserRepositoryProtocol {
func fetch(id: String) async throws -> User
}
// 本番実装
final class UserRepository: UserRepositoryProtocol { ... }
// テストダブル
final class MockUserRepository: UserRepositoryProtocol {
var fetchResult: Result<User, Error> = .success(User.stub)
var fetchCallCount = 0
var lastFetchedId: String?
func fetch(id: String) async throws -> User {
fetchCallCount += 1
lastFetchedId = id
return try fetchResult.get()
}
}
Phase 5: XCUITestによるUIテスト設計
詳細は references/xcuitest-patterns.md を参照。
5.1 Page Objectパターン
// Page Object
final class LoginPage {
private let app: XCUIApplication
var emailField: XCUIElement { app.textFields["email"] }
var passwordField: XCUIElement { app.secureTextFields["password"] }
var loginButton: XCUIElement { app.buttons["login"] }
init(app: XCUIApplication) {
self.app = app
}
func login(email: String, password: String) -> HomePage {
emailField.tap()
emailField.typeText(email)
passwordField.tap()
passwordField.typeText(password)
loginButton.tap()
return HomePage(app: app)
}
}
5.2 Accessibility Identifierの設計
| 要素 | 命名規則 | 例 |
|---|---|---|
| 画面 | <screen>_screen | login_screen |
| ボタン | <action>_button | submit_button |
| テキストフィールド | <field>_field | email_field |
| ラベル | <content>_label | error_label |
| セル | <item>_cell_<index> | user_cell_0 |
Phase 6: テストデータ管理
詳細は references/test-data.md を参照。
6.1 Factoryパターン
enum UserFactory {
static func make(
id: String = UUID().uuidString,
name: String = "Test User",
email: String = "test@example.com",
isActive: Bool = true
) -> User {
User(id: id, name: name, email: email, isActive: isActive)
}
static var activeUser: User { make(isActive: true) }
static var inactiveUser: User { make(isActive: false) }
}
6.2 フィクスチャファイル
Tests/
├── Fixtures/
│ ├── JSON/
│ │ ├── user_response.json
│ │ └── error_response.json
│ └── Stubs/
│ └── UserStub.swift
Phase 7: テストカバレッジ分析
7.1 カバレッジ目標
| レベル | 目標 | 説明 |
|---|---|---|
| 行カバレッジ | 80%以上 | 実行された行の割合 |
| 分岐カバレッジ | 70%以上 | if/switch分岐の網羅 |
| 重要パス | 100% | ビジネスクリティカルなパス |
7.2 Xcodeでのカバレッジ確認
- スキーム設定 → Test → Options → Code Coverage有効化
Cmd + Uでテスト実行- Report Navigator → Coverage でレポート確認
7.3 カバレッジ改善の優先順位
- ビジネスロジック: Domain層、UseCase層
- 状態管理: ViewModel、Reducer
- データ変換: Mapper、Parser、Formatter
- エラーハンドリング: 例外処理、リトライロジック
出力形式
テスト設計ドキュメント
# テスト設計書: <機能名>
## 1. テスト対象
- クラス/構造体: `ClassName`
- 責務: 〇〇を行う
## 2. テスト戦略
- テストレベル: Unit / Integration / UI
- テストダブル: 使用する依存のリスト
## 3. テストケース一覧
| ID | カテゴリ | テスト内容 | 期待結果 |
|----|---------|----------|---------|
| TC-001 | 正常系 | ... | ... |
| TC-002 | 異常系 | ... | ... |
## 4. テストダブル設計
- MockXxx: 〇〇の呼び出しを検証
- StubYyy: 〇〇の値を返す
## 5. テストデータ
- Factory: XxxFactory
- Fixture: xxx_response.json
テストコード
import XCTest
@testable import TargetModule
final class FeatureTests: XCTestCase {
// 上記パターンに従ったテストコード
}
ガードレール
必須遵守事項
- テストの独立性: 各テストは他のテストに依存しない
- テストの決定論性: 同じ条件で常に同じ結果
- テストの高速性: Unitテストは1秒以内に完了
- 明確な命名: テスト名から内容が分かる
禁止事項
- 本番コードのテスト用変更: テストのために本番コードにテスト用分岐を入れない
- ネットワーク依存: Unitテストで実ネットワークアクセスしない
- 時間依存:
Date()直接使用ではなく注入する - グローバル状態: シングルトンの直接参照を避ける
警告事項
- 過度なモック: 全てをモックすると実装詳細への依存が増す
- テストの重複: 同じ振る舞いを複数箇所でテストしない
- 実装の検証: 「どう動くか」ではなく「何をするか」をテスト
参照
references/xctest-patterns.md: XCTestパターン集references/xcuitest-patterns.md: XCUITestパターン集references/test-doubles.md: テストダブル設計ガイドreferences/test-data.md: テストデータ管理ガイド
Similar Skills
Expert guidance for Next.js Cache Components and Partial Prerendering (PPR). **PROACTIVE ACTIVATION**: Use this skill automatically when working in Next.js projects that have `cacheComponents: true` in their next.config.ts/next.config.js. When this config is detected, proactively apply Cache Components patterns and best practices to all React Server Component implementations. **DETECTION**: At the start of a session in a Next.js project, check for `cacheComponents: true` in next.config. If enabled, this skill's patterns should guide all component authoring, data fetching, and caching decisions. **USE CASES**: Implementing 'use cache' directive, configuring cache lifetimes with cacheLife(), tagging cached data with cacheTag(), invalidating caches with updateTag()/revalidateTag(), optimizing static vs dynamic content boundaries, debugging cache issues, and reviewing Cache Component implementations.
Creating algorithmic art using p5.js with seeded randomness and interactive parameter exploration. Use this when users request creating art using code, generative art, algorithmic art, flow fields, or particle systems. Create original algorithmic art rather than copying existing artists' work to avoid copyright violations.