ユーザーは「続ける」ボタンをタップしても何も起こらないと報告します。コンポーネントテストはボタンを発見し、ハンドラーを呼び出し、期待どおりの画面をモックしたJavaScript環境で見ました。実機ではnative許可のダイアログ、キーボードの動作、アニメーション、プラットフォームAPI、実際のナビゲーションスタックを検証しませんでした。
チームは誤った自信を得るのです。 React Native テスト ライブラリ ユーザー インタラクションやコンポーネントのレンダリングをテストするのに適していますが、デバイス テストやパフォーマンス測定の代わりではありません。信頼できる戦略は、各レイヤーで暴露できるエラーを使用することです。
目次
- ユーザー センター テストがすべてを変える理由
- 実際に機能するインストールと設定
- コア API、クエリ、断言の説明
- コンポーネント、フック、ナビゲーション用の実用的なパターン
- デバッグ フラッキーテスト CI とパフォーマンス チェック
- すべてを組み合わせて進む
ユーザー センター テストがすべてを変える理由
テストが書かれる前に、テストが失敗するのはよくあることです。開発者はコンポーネントのプロパティを検査し、コンポーネントの状態にアクセスし、大きなスナップショットを比較するのは、簡単にアサートできるためです。テストは通過し、リファクタリングがコンポーネントの構造を変更した場合でも、ユーザーに視覚的に表示される結果は変わりません。さらに、テストはパスを続けながら、ユーザーに視覚的に表示される結果が間違っている場合でも、ユーザーに視覚的に表示される結果をアサートすることはないためです。
React Native テスト ライブラリはその逆のアプローチを採用します。コンポーネントをレンダリングし、ユーザーが操作できるコントロールを通じてコンポーネントと対話し、ユーザーが観察できる結果をアサートします。このアプローチは React Native テスト ライブラリのユーザー センターの例, React Native のテストガイドラインに従って、テストを短くし、各テストに 1 つのテスト対象を設定し、ビューの懸念事項とビジネスロジック、状態を分離し、内部実装詳細ではなく、可視化された出力またはアクセシビリティ ヘルパーを優先する。

ユーザーが依存する動作をテストする。
ログインフォームがリクエストが実行中のときにサブミットボタンを無効化する場合、脆弱なテストは特定のコンポーネントインスタンスを検査したり、状態変数が変更されたことを確認したりします。より強力なテストは、アクセシビリティの「サインイン」コントロールを押し、ローディングインジケータを待ち、エラーメッセージまたは目的の画面が表示されることを確認します。 disabled 2 番目のテストは、フォームがローカル状態、レデューサー、カスタムフック、または異なるボタン実装を使用しているかどうか気にしません。アプリが正しい結果を伝えることを気にします。
実践的なルール:
ユーザーが観察できないものは、コンポーネントの動作テストに含まれるべきではないかと疑問に思う。 アクセシビリティ ラベルとロールに基づくクエリも、より良い製品__CAPGO_KEEP_0__を強制します。意味のあるラベルを露出する画面は、アシスタントテクノロジーとテストで容易に使用できます。そうした接続は、より広範なアプリのユーザー体験を評価する際に重要です。
Queries based on accessibility labels and roles also force better product code. A screen that exposes meaningful labels is easier to use with assistive technology and easier to exercise in tests. That connection matters when you assess the broader 通過したテストは何も証明しない。テストの結果を理解するには、テストの結果を分析する必要があります。
テストの結果を分析することで、テストの結果を理解することができます。
A JavaScriptのユーザー中心のコンポーネントテストは、JavaScriptが期待どおりのbranchをレンダリングし、シミュレートされたクリックに反応することを証明できます。 しかし、バイオメトリックのプロンプトが正しく開くか、ネイティブカメラが利用可能な結果を返すか、プラットフォーム固有のライフサイクル動作によって結果が変わる可能性のある決済フローの場合には、それを証明することはできません。
RNTLを使用してコンポーネントの動作をテストし、ネイティブ統合、実際のナビゲーション、パーミッション、認証、決済、またはアプリのコア機能が結果を変える可能性のあるフローでは、デバイスベースのテストを予約してください。
実際に機能するインストールと設定
現代的なセットアップは、スコープパッケージから始まります。
@testing-library/react-native
古い react-native-testing-library npmパッケージ名は歴史的アーティファクトとして存在し続けていますが、現在のプロジェクトでは、Testing Libraryファミリー内で管理されているスコープパッケージを使用することをお勧めします。プロジェクトの GitHubリポジトリ は、React Nativeのユーティリティを提供し、良いテスト慣行を奨励することを目的としています。また、リリース履歴は、React Nativeとともに変化し続けていることを示しています。ライブラリは、静的ヘルパーとしてではなく、React Nativeとともに進化しています。
ライブラリをJest環境とともにインストールしてください。エクスポプロジェクトでは、エクスポJestプリセットがよく使用されます。一方、bare React Nativeプロジェクトでは、React Nativeプリセットがよく使用されます。
npm install --save-dev @testing-library/react-native jest
エクスポの場合、プロジェクトで既に使用しているプリセットを追加してください。
{
"scripts": {
"test": "jest"
},
"jest": {
"preset": "jest-expo"
}
}
React Nativeアプリケーションの場合、対応するReact Native Jestの設定を使用します。フレームワークのバージョンと合わせてプリセットを維持します。多くのRNTLの問題のように見える失敗は、Reactレンダラー、Babel変換、Jestプリセットの不一致から来ています。
セットアップファイルを明示的に設定します。
共有環境設定をセットアップファイルに置き換え、テストごとにモックを繰り返さないようにします:
// jest.setup.js
import '@testing-library/react-native/extend-expect';
次に、Jestから参照します:
{
"jest": {
"preset": "jest-expo",
"setupFilesAfterEnv": ["<rootDir>/jest.setup.js"]
}
}
アプリがReact Navigation、Reanimated、ジェスチャーハンドリング、安全エリアコンテキスト、またはストレージモジュールを使用している場合、テスト環境が必要とするモックのみを設定します。アプリケーションの動作を変更するグローバルモックは、すべてのテストを簡単にパスできるようにしますが、スイートの信頼性を低下させます。
TypeScriptも同じ注意が必要です。JestがプリセットまたはBabelの設定で変換し、テストタイプをコンパイラに提供し、ローカルで実行されるテストが型チェックされていない場合、不正なクエリ名、無効なナビゲーションパラメータ、または安全でないモックの形状が隠れてしまいます。 .ts リリースの時系列は、古いセットアップアドバイスの診断に役立ちます。プロジェクトは .tsx 127のリリース
があり、 v14.0.1は2026-06-23にタグ付けされていますそして そして、 v12.9.0、2024年11月27日にリリースされたものは、React Native 0.77とExpo 52に対する公式サポートを追加した。。2025年3月のv14 alpha版では、Universal Test Rendererに移行し、React 19のみをサポートする準備ができた。詳細は RNTLリリース履歴に記載されているので、古いチュートリアルからレンダラー依存性をコピーするのではなく、自分のアプリのバージョンを確認すること。
実践的なJestの基盤を構築するには、この Jest単体テストガイドを自分の設定と比較し、ナビゲーションとネイティブモックを追加する前に、一つの小さなコンポーネントテストを実行すること。

Core APIs Queries and Assertions Explained
RNTLテストは、ユーザーが見る、見つける、操作できるものと一致するクエリを持つときに信頼できるものになる。APIは小さくて簡単なものだが、実装詳細を露呈するセレクターを選択すると、パスするテストが誤解を招くものになる。
はじめに render:
const screen = render(<LoginForm />);
最もユーザーに適切なクエリを選択してください。アクセシビリティに重点を置いたクエリを優先し、テキストが動作の場合には表示テキストを使用し、意味のあるユーザー向けのセレクターが存在しない場合や安定した統合ホックが必要な場合には testID 「」や「」を使用します。

タイミングと意図に基づいてクエリを選択します。
各クエリファミリーには、独自の目的があります。
- 同期的存在: 「」や「」を使用します。
getByRole,getByText非同期的出現:getBy「」や「」を使用します。 - 「」の文脈: HTML テキスト フラグメント (親キー `alternatives_cta_questions` )。ページ/エリア: Capacitor ライブアップデートの代替品比較ページ。役割: 長いマーケティングまたは法的文章。見つける場所: page alternatives.astro。Capgo の製品/ブランドと開発者用語を完全に保持します。 「」の文脈: HTML テキスト フラグメント (親キー `appflow_cta_questions` )。ページ/エリア: Appflow の比較/移行マーケティングコピー。役割: 長いマーケティングまたは法的文章。見つける場所: page ionic-appflow.astro。Capgo の製品/ブランドと開発者用語を完全に保持します。
findByRole「」の文脈: HTML テキスト フラグメント (親キー `capwesome_cta_questions` )。ページ/エリア: Capawesome の比較ページ。役割: 長いマーケティングまたは法的文章。見つける場所: page capwesome.astro。Capgo の製品/ブランドと開発者用語を完全に保持します。findByTextレンダリングまたはインタラクションが非同期更新を引き起こす場合。 - 欠如のチェック: 使用
queryByTextまたはqueryByTestIdまたは - 使用 意図的に。複雑なコントロールに持続可能なハンドルを与えるが、全体的なアプリケーションでアクセシビリティのラベルを置き換えることはしない。
getByTestIdフォーカスイベントテストの場合
直接: fireEvent.press 使用
fireEvent.press(screen.getByRole('button', { name: 'Save' }));
インストールされているバージョンがより現実的なインタラクションシーケンスをサポートする場合。どちらの場合も、結果のUIを確認すること。 userEvent または
expect(await screen.findByText('Saved')).toBeTruthy();
A handler assertion matches a component whose public contract is an event callback. It is weak as the only evidence that the user journey works.
Prefer specific assertions over snapshots.
Good assertions describe the screen:
expect(screen.getByText('Account created')).toBeTruthy();
expect(screen.getByRole('button', { name: 'Continue' })).toBeEnabled();
They can also verify accessibility state, selection, and visible validation feedback. Avoid checking internal wiring:
expect(screen.getByTestId('submit-button').props.onPress).toBeDefined();
That assertion proves a prop exists, not that the feature works. Small, intentional snapshots can catch structural changes, while large navigation or screen snapshots often create noisy reviews and make unexplained updates easy to approve.
Capgoの testing-library npm @testing-library/react-native13.3.3 2026repository information . Shared query conventions help across platforms, but they do not decide which assertion represents your product behavior.Prefer specific assertions over snapshots.
React Native テスト ライブラリの使い方 React のユニット テスト. RNTL は JavaScript レンダリングされたコンポーネントの境界で止まる。
Native のパーミッション、実際のナビゲーション スタック、デバイス キーボード、フレーム タイミング、メモリ ビハインドは、E2E またはパフォーマンス ツールで扱う必要がある。
以下のビデオは、クエリとアサーション ワークフローを実際に使ってみる。
コンポーネント、フック、ナビゲーションの実践的なパターン

現代のラップトップと木の机の上に表示される React Native __CAPGO_KEEP_0__ とモバイル アプリのモック
プレゼンテーショナル コンポーネント
const onSelect = jest.fn();
render(
<PlanCard
title="Team"
description="Shared workspace"
onSelect={onSelect}
/>
);
fireEvent.press(screen.getByRole('button', { name: 'Choose Team' }));
expect(onSelect).toHaveBeenCalled();
コンポーネント テストは、パブリック コントラクトに近づける。
正確なラベルは、UI と一致する。重要なのは、テストが、ユーザーまたはアクセシビリティ サービスがどのように見つけるかを確認し、重要な可視またはコールバックの結果を確認することである。デフォルトでは、すべての子コンポーネントをモックしない。高コストまたは無関係な境界をモックするのは、テスト対象の動作を隠す場合にのみ。 renderHook カスタム フックの場合、使用する
const { result } = renderHook(() => useSearch());
await act(async () => {
await result.current.submit('query');
});
expect(result.current.status).toBe('success');
hook testは、ネットワークまたはリポジトリの境界を制御するようにするべきであり、全体のアプリケーションを再現することはない。画面を別々にテストすることで、hookの状態が有用なUIになるかどうかを知ることができる。
ナビゲーションと非同期データ
ナビゲーション動作の場合、実際の画面内に画面をレンダリングすることで、ナビゲーションメソッドをすべてモックするよりも、実際のナビゲーションをテストすることがより価値がある。表示されるコントロールを押すと、目的の画面のコンテンツを待ち、表示される新しい画面の出力を確認する。小さなボタンの場合、直接モックはまだ適切ですが、ルートの登録、パラメータ、ネストされたナビゲータの動作を検証することはできない。 NavigationContainer 非同期データにも同じ規範を適用する。__CAPGO_KEEP_0__またはリポジトリのレスポンスをモックする、画面をレンダリングする、ロード中の状態を確認する、リクエストを解決する、成功またはエラーの出力を確認する。期待される最終的な要素を検索するクエリを使用し、却下されたリクエストを明確にする。そうしないと、コンポーネントが目的のbranchに到達しない場合でもテストがパスする可能性がある。 useNavigation ネイティブモジュールモック
Async data deserves the same discipline. Mock the API or repository response, render the screen, assert the loading state, resolve the request, then assert success or error output. Use findBy シナリオ
RNTLと組み合わせることが最も適切
E2E検証が必要
| __CAPGO_KEEP_0__ | __CAPGO_KEEP_0__ | __CAPGO_KEEP_0__ |
|---|---|---|
| フォームのバリデーションと表示されるエラー | はい | 通常ではありません |
| モックされたリポジトリからロード、成功、エラーUI | はい | 重要な生産フロー |
| 登録済みの画面間のナビゲーション | テストナビゲータとともに | ジェスチャー、深いリンク、プラットフォームの動作が重要な場合 |
| AsyncStorageの状態の決定 | 制御されたモックとともに | 起動とパERSISTENCEがネイティブのライフサイクルと相互作用する場合 |
| カメラ、バイオメトリクス、パーミッション、またはプラットフォームAPI | JSのフォールバックとbranchingロジック | 実機または代表的なデバイス上で |
| レイアウト、レンダリングパフォーマンス、そしてネイティブcode | いいえ | デバイスまたは専用ツールを使用して |
境界は実用的です:依存性をモックしてJavaScriptの決定をテストし、次にデバイステストを実行して依存性の実際の動作を確認します。
不確実なテストのデバッグ CIとパフォーマンスチェック
不確実なテストは、制御されていない時間、共有状態、またはUIと競合するアサーションが存在することを示しています。条件が存在する前にタイムアウトを設定する前に、どの条件が存在しているかを特定する必要があります。タイムアウトを長くすると、スケジューリング問題を隠し、スイートを遅くする可能性があります。
使用 findBy 更新後に表示される要素の場合に使用します。状態条件またはモックコールの場合に使用します。フェイクタイマーが有効になっている場合、インタラクションが必要なポイントで進め、実際のタイマーを復元する必要があります。 waitFor An act 警告は、Reactが予想外のインタラクション境界外で更新を観測したことを意味します。 予想外の更新、またはタイマーフラッシュの代わりに警告を抑制するのではなく、欠落しているものを修正してください。 awaitCIの失敗を再現可能にする
信頼できるCIジョブはロックファイルからインストールし、ローカルで使用されている同じJestコマンドを実行し、モック状態を分離します。テスト間のモックコールをクリアし、モジュールレベルの状態が動作に影響を与える場合にモジュールをリセットし、実行順序に依存しない依存関係を削除します。Jestキャッシングはフィードバックを速めるものの、依存関係または構成変更には適切なキャッシュ無効化が必要です。
CIのみで失敗するものには、コンポーネントのリライト前に環境の比較が必要です。Node、パッケージマネージャー、Jestワーカー設定、タイマーコンフィギュレーション、環境変数を確認し、可能な場合はローカルで同じコマンドを再現し、失敗するテストを最小限のインタラクションに減らして差異を特定します。
観察性は別のギャップをカバーします。 React Native用のツールとして
Sentry 生産時のエラーコンテキストを提供し、モックされたコンポーネントテストでは再現できない、実際のデバイスやネイティブ統合に紐づいた失敗を含みます。 セキュリティ上の重要なjourneyには2番目の境界が必要です。コンポーネントテストで検証と状態遷移を使用し、ハンドオフとネイティブの動作のためのデバイスレベルのカバレージを追加してください。1回限りの__CAPGO_KEEP_0__フローについては、ガイドラインに従って
Security-sensitive journeys need a second boundary. Use component tests for validation and state transitions, then add device-level coverage for the handoff and native behavior. For one-time-code flows, consult guidance on how to を参照してください。 その統合がjourneyの一部である場合に限ります。 パフォーマンスを測定と主張と区別してください
__CAPGO_KEEP_0__
機能テストはリストが正しくレンダリングされることを確認できますが、リファクタリングがレンダリング時間やレンダリング回数に影響を与えたかどうかを信頼できません。テスト実行時間がノイズを追加するためです。シナリオを確実に測定し、シナリオを繰り返して変異を減らし、統計分析を実行して意味のある変化を報告します。 パフォーマンステストのドキュメント CIやプルリクエストレビュー用に適切なレポートを提供することもカバーしています。
固定アサーションを避けるようにしてください。例えば、「レンダリング時間が指定された閾値以下でなければならない」というのは、忙しいCIワーカーが誤った失敗を引き起こすかもしれません。しっかりとした閾値を設定すると、実際のレグレッションを逃す可能性があります。レグレッション信号を再現するために測定値を繰り返し、比較が意味のある差異を示す場合にのみコンポーネントとデバイスプロファイルを検査してください。
測定ルール: 機能テストは、動作が正しいかどうかを確認します。パフォーマンスツールは、測定されたシナリオが変化したかどうかを確認します。両方の質問を分離してください。
すべてを組み合わせて進んでいきましょう
React Native Testing Libraryは、テスト戦略の広く高速な層に属します。コンポーネントの動作、可視状態の変更、アクセシビリティの結果、検証、モックされたデータの状態、JavaScriptコンポーネント間の統合をカバーする必要があります。ユーザーが観察できるものに焦点を当て、失敗が特定の動作に指示するようにしてください。
モックが存在する可能性のあるフローの保護に、小さいデバイスベースの層が必要です。React Nativeの テストの概要 RNTLは完全なReact Nativeランタイムを提供せず、ネイティブ機能のテストを行うことができないと述べています。同様のガイドラインでは、認証、決済、コアアプリ機能など、重要なフローを対象に、DetoxなどのE2Eツールと組み合わせてコンポーネントテストを実行することを推奨しています。
実用的な移行パス
既存のスイートを一度に書き直す必要はありません。
- 貴重なビジネステストを保持してください。 純粋な状態とドメインロジックを、明確なフィードバックを提供する単位テストに移行してください。
- 実装のアサーションを置き換えましょう。 プロパティと内部状態のチェックを、可視化された出力、アクセシビリティ状態、インタラクションの結果に置き換えてください。
- スナップショットを縮小してください。 レビューアが理解し、維持できるスナップショットのみを保持してください。
- ネイティブの境界カバレッジを追加してください。 重要なモックされたモジュールごとに、まだ検証が必要なデバイスの動作を特定してください。
- 重要なジャーニーを保護してください。 認証、決済、コアナビゲーション、パーミッション、他にnativeの挙動が結果を変える可能性のあるフローに対して、E2Eカバレッジを追加する。
- 敏感な画面を個別に測定する。 リスト、フィード、費用の高いレンダリングパスに対して、繰り返しパフォーマンス比較を使用するのではなく、Jestのdurationから推測するのではなく。
リリースの信頼性のために、スイートをCI/CDの統合テストに接続し、適切なテストレイヤーを必要とする前に、配信する。 CI/CD統合テスト 配信されたJavaScriptやアセットの修正がユーザーに到達する必要がある場合、CapgoはCapacitorJSやElectronアプリケーションに対して、ターゲットされたチャンネルに署名されたWebバンドルを配信し、ロールアウトの制御とロールバック保護を提供します。その配信フローは、React Nativeのデバイステストを置き換えるものではありませんが、同じ原理を示しています: バehaviorを検証するのは、実行されるレイヤーです。
正しい質問は、React Native Testing Libraryがあなたの全てのアプリをテストできるかどうかではありません。できないし、公式の境界は役に立ちます。正しい質問は、各重要なリスクが、リスクを露呈できる環境でテストが実行されているかどうかです。
Capgoは、検証済みのJavaScriptやアセットの変更を、CapacitorJSやElectronチームに対して、ターゲットされたチャンネル、ロールアウトの可視性、ロールバック保護とともに、制御された配信に接続します。Capgoを訪問して、 Capgo コントロールされた配信のターゲットされたチャンネル、ロールアウトの可視性、ロールバック保護とともに、検証済みのJavaScriptやアセットの変更をCapacitorJSやElectronチームに対して接続します。