跳到主要内容

如何运行和编写测试

运行测试

本节介绍作为贡献者如何测试你对 React Native 所做的更改。如果你还没有,请按照步骤设置你的开发环境,以便构建包含原生代码的项目

JavaScript 测试

运行 JavaScript 测试套件最简单的方法是在你的 React Native 检出(checkout)的根目录中使用以下命令

bash
yarn test

这将使用 Jest 运行测试。

你还应该确保你的代码通过了 Flow 和 lint 测试

bash
yarn flow
yarn lint

iOS 测试

遵循 packages/rn-tester 目录中的 README.md 说明。

然后,回到你的 React Native 检出(checkout)的根目录并运行 yarn。这将设置你的 JavaScript 依赖项。

此时,你可以从你的 React Native 检出(checkout)的根目录调用以下脚本来运行 iOS 测试

bash
./scripts/objc-test.sh test

你也可以使用 Xcode 运行 iOS 测试。打开 RNTester/RNTesterPods.xcworkspace 并通过按下 Command + U 或从菜单栏中选择 Product 然后 Test 来本地运行测试。

Xcode 也允许通过其测试导航器(Test Navigator)运行单个测试。你也可以使用 Command + 6 快捷方式。

注意

objc-test.sh 确保你的测试环境已设置好以运行所有测试。它还会禁用已知不稳定或损坏的测试。使用 Xcode 运行测试时请记住这一点。如果你看到意外的失败,请首先查看它是否在 objc-test.sh 中被禁用。

iOS Podfile/Ruby 测试

如果你正在修改 Podfile 配置,那么有 Ruby 测试可以验证这些。

运行 Ruby 测试

bash
cd scripts
sh run_ruby_tests.sh

Android 测试

Android 单元测试不在模拟器中运行,而是在你本地机器的 JVM 上运行。

要运行 Android 单元测试,请从你的 React Native 检出(checkout)的根目录调用以下脚本

bash
./gradlew test

编写测试

每当你修复错误或向 React Native 添加新功能时,最好添加一个涵盖该功能的测试。根据你所做的更改,可能有不同类型的测试是合适的。

JavaScript 测试

JavaScript 测试可以在 __test__ 目录中找到,与被测试文件并置。请参阅 TouchableHighlight-test.js 获取一个基本示例。你还可以遵循 Jest 的 测试 React Native 应用 教程以了解更多。

iOS 集成测试

React Native 提供了便利,使得测试需要原生组件和 JS 组件通过桥接器通信的集成组件变得更容易。

两个主要组件是 RCTTestRunnerRCTTestModuleRCTTestRunner 设置 React Native 环境并提供设施来运行测试,作为 Xcode 中的 XCTestCaserunTest:module 是最简单的方法)。RCTTestModule 被导出到 JavaScript 为 NativeModules.TestModule

测试本身是用 JS 编写的,并且必须在完成后调用 TestModule.markTestCompleted(),否则测试将超时并失败。

测试失败主要通过抛出 JS 异常来指示。也可以使用 runTest:module:initialProps:expectErrorRegex:runTest:module:initialProps:expectErrorBlock: 来测试错误条件,这将期望抛出错误并验证错误是否与提供的条件匹配。

有关示例用法和集成点,请参阅以下内容

iOS 快照测试

一种常见的集成测试类型是快照测试。这些测试渲染一个组件,并使用 TestModule.verifySnapshot() 对屏幕快照进行参考图像验证,后台使用 FBSnapshotTestCase 库。通过在 RCTTestRunner 上设置 recordMode = YES 来记录参考图像,然后运行测试。

快照在 32 位和 64 位之间以及不同的操作系统版本之间会略有不同,因此建议你强制测试使用 正确的配置 运行。

强烈建议模拟所有网络数据,以及其他可能存在问题的依赖项。请参阅 SimpleSnapshotTest 获取一个基本示例。

如果你所做的更改在拉取请求中影响了快照测试(例如,向一个已生成快照的示例添加新示例用例),则需要重新记录快照参考图像。

为此,请将 recordMode 标志更改为 RNTester/RNTesterSnapshotTests.m 中的 _runner.recordMode = YES;,重新运行失败的测试,然后将记录翻转回 NO 并提交/更新你的拉取请求,然后等待查看 CircleCI 构建是否通过。

Android 单元测试

每当你正在处理仅可由 Java/Kotlin 代码测试的代码时,最好添加一个 Android 单元测试。Android 单元测试位于 packages/react-native/ReactAndroid/src/test/

我们建议你浏览这些测试,以了解一个好的单元测试可能是什么样子。

持续测试

我们使用 CircleCI 自动运行我们的开源测试。每当有提交添加到拉取请求时,CircleCI 都会运行这些测试,以帮助维护者了解代码更改是否引入了回归。这些测试也运行在 main*-stable 分支上的提交,以跟踪这些分支的健康状况。

还有另一组测试在 Meta 的内部测试基础设施中运行。其中一些测试是由 React Native 的内部使用者定义的集成测试(例如,Facebook 应用中 React Native 界面的单元测试)。

这些测试会在每次提交到 Facebook 源代码管理中托管的 React Native 副本时运行。当拉取请求被导入到 Facebook 的源代码管理时,它们也会运行。

如果其中一个测试失败,你需要 Meta 的某人来查看。由于拉取请求只能由 Meta 员工导入,因此导入拉取请求的人应该能够提供任何详细信息。

注意

在本地运行 CI 测试: 大多数开源协作者依赖 CircleCI 查看这些测试的结果。如果你更愿意使用与 CircleCI 相同的配置在本地验证你的更改,CircleCI 提供了一个命令行界面,能够本地运行作业。

常见问题

如何升级 CI 测试中使用的 Xcode 版本?

升级到新版本 Xcode 时,首先确保它被 CircleCI 支持

你还需要更新测试环境配置,以确保测试在 CircleCI 机器中安装的 iOS 模拟器上运行。

这也可以在 CircleCI 的 Xcode 版本参考 中找到,方法是点击所需的版本并查看“Runtimes”下。

然后你可以编辑这两个文件

  • .circleci/config.yml

    编辑 macos: 下的 xcode: 行(搜索 _XCODE_VERSION)。

  • scripts/.tests.env

    编辑 IOS_TARGET_OS 环境变量以匹配所需的 iOS 运行时。

如果你打算在 GitHub 上合并此更改,请务必通知 Meta 员工,因为他们需要在导入你的拉取请求时更新 react_native_oss.py 中内部 Sandcastle RN OSS iOS 测试所使用的 _XCODE_VERSION 值。