Android Espresso 自动化测试指南(Java 版)
目录
1. 环境配置
1.1 添加 Gradle 依赖
在 app/build.gradle
中添加以下依赖:
android {
defaultConfig {
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
}
dependencies {
// Espresso 核心库
androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.1'
// AndroidX Test 支持
androidTestImplementation 'androidx.test.ext:junit:1.1.5'
androidTestImplementation 'androidx.test:rules:1.5.0'
}
1.2 测试目录结构
app/
├── src/
│ ├── main/ # 主代码
│ └── androidTest/ # UI 测试代码
│ └── java/
│ └── com/example/
│ └── YourActivityTest.java
2. Espresso 核心 API
2.1 基本操作
方法 | 说明 | 示例代码 |
---|---|---|
onView(withId(R.id.view_id)) | 通过 View ID 定位视图 | onView(withId(R.id.tv_hello)) |
perform(click()) | 点击操作 | .perform(click()) |
check(matches(isDisplayed())) | 验证视图是否可见 | .check(matches(isDisplayed())) |
2.2 常用匹配器
匹配器 | 说明 |
---|---|
withId(R.id.view_id) | 通过 ID 匹配视图 |
withText("text") | 匹配视图文本 |
isDisplayed() | 验证视图可见 |
allOf() | 组合多个匹配条件 |
3. 测试场景示例
3.1 验证 TextView 显示文本
@RunWith(AndroidJUnit4.class)
public class MainActivityTest {
@Rule
public ActivityScenarioRule<MainActivity> activityRule =
new ActivityScenarioRule<>(MainActivity.class);
@Test
public void testTextViewDisplay() {
onView(withId(R.id.tv_hello))
.check(matches(withText("Hello World!")));
}
}
3.2 测试 Fragment 生命周期
@RunWith(AndroidJUnit4.class)
public class FragmentLifecycleTest {
@Rule
public ActivityScenarioRule<FragmentContainerActivity> activityRule =
new ActivityScenarioRule<>(FragmentContainerActivity.class);
@Test
public void testFragmentResume() {
FragmentScenario.launchInContainer(MyFragment.class);
// 模拟回到前台
FragmentScenario.moveToState(MyFragment.class, Lifecycle.State.RESUMED);
onView(withId(R.id.tv_refresh)).check(matches(isDisplayed()));
}
}
3.3 测试文件读取与 UI 显示
@Test
public void testFileDisplay() {
// 准备测试文件
writeTextToAssets("test_data.txt", "Hello from File!");
// 启动 Activity
ActivityScenario.launch(DisplayActivity.class);
onView(withId(R.id.tv_file_content))
.check(matches(withText("Hello from File!")));
}
// 辅助方法:写入测试文件到 assets
private void writeTextToAssets(String fileName, String content) {
try {
Context context = ApplicationProvider.getApplicationContext();
AssetManager assetManager = context.getAssets();
// 实际项目中需使用临时文件或测试资源目录
} catch (IOException e) {
fail("文件写入失败: " + e.getMessage());
}
}
3.4 测试系统配置项(如 Build.MODEL)
@RunWith(AndroidJUnit4.class)
public class DeviceInfoTest {
@Rule
public ActivityScenarioRule<DeviceInfoActivity> activityRule =
new ActivityScenarioRule<>(DeviceInfoActivity.class);
@Test
public void testBuildModelDisplay() {
final String expectedModel = Build.MODEL;
onView(withId(R.id.tv_device_model))
.check(matches(withText(expectedModel.trim())));
}
}
4. 依赖管理
4.1 Gradle 配置
确保 app/build.gradle
包含以下内容:
android {
testOptions {
unitTests.includeAndroidResources = true
}
}
dependencies {
// Espresso 核心依赖
androidTestImplementation 'androidx.test.espresso:espresso-core:3.5.1'
androidTestImplementation 'androidx.test.ext:junit:1.1.5'
androidTestImplementation 'androidx.test:rules:1.5.0'
}
4.2 多模块项目配置
在根项目的 build.gradle
中添加:
allprojects {
repositories {
google()
mavenCentral()
}
}
5. 常见问题与解决
5.1 视图未找到
现象:NoMatchingViewException
原因:视图未加载完成或 ID 错误。
解决:
- 使用
IdlingResource
等待异步任务完成。 - 检查布局文件中的视图 ID。
5.2 测试时序问题
现象:断言在视图加载前执行。
解决:
IdlingRegistry.getInstance().register(EspressoIdlingResource.idlingResource);
// 触发异步操作
ActivityScenario.launch(MainActivity.class);
IdlingRegistry.getInstance().unregister(EspressoIdlingResource.idlingResource);
5.3 测试覆盖率低
解决:
- 使用 JaCoCo 生成报告:
android { buildTypes { debug { testCoverageEnabled true } } }
- 运行命令:
./gradlew createDebugCoverageReport
- 查看报告:
app/build/reports/coverage/debug/index.html
总结
通过本指南,您已掌握以下技能:
- 配置 Espresso 测试环境。
- 使用核心 API 编写 UI 测试用例。
- 覆盖常见测试场景(Fragment、文件读取等)。
- 解决测试中的常见问题。
如需进一步学习,请参考 Android 官方测试文档。