如何用Espresso判断Intent(Activity)的包名包含指定字符串?
解决Espresso测试适配多设备相机包名的问题
我明白你的痛点——硬编码相机包名在不同设备上很容易失效,比如三星Galaxy S8的相机包名就是com.sec.android.app.camera,和原生的com.android.camera不一样。要实现判断Intent包名包含"camera"的逻辑,我们可以通过自定义Espresso Intent Matcher来搞定,具体方案如下:
步骤1:自定义Intent匹配器
写一个TypeSafeMatcher,专门用来检查Intent的包名是否包含指定的子字符串:
import android.content.Intent; import org.hamcrest.Description; import org.hamcrest.TypeSafeMatcher; private Matcher<Intent> hasPackageContaining(String targetSubstring) { return new TypeSafeMatcher<Intent>() { @Override protected boolean matchesSafely(Intent intent) { String packageName = intent.getPackage(); // 确保包名不为空,并且包含目标子串 return packageName != null && packageName.contains(targetSubstring); } @Override public void describeTo(Description description) { description.appendText("期望Intent的包名包含子串: " + targetSubstring); } }; }
步骤2:修改测试代码
把原来的intended(toPackage("com.android.camera"))替换成我们自定义的匹配器:
@Test public void profileImageClickOpensCamera() { mIntentsRule.getActivity().startActivity(new Intent(mIntentsRule.getActivity(), ProfileActivity.class)); onView(withId(R.id.circleProfileImage)).perform(click()); // 使用自定义匹配器检查包名包含"camera" intended(hasPackageContaining("camera")); }
补充说明
正如你提到的,这确实不是最完美的方案——更优的做法是检查Intent的Action是否为MediaStore.ACTION_IMAGE_CAPTURE(因为不管哪个厂商的相机应用,都会响应这个标准拍照Action),这样完全不需要依赖包名。不过如果你的需求就是要匹配包名包含"camera"的情况,上面的方案已经能很好解决多设备兼容问题了。
内容的提问来源于stack exchange,提问作者Adam Varhegyi
相关产品推荐
相关产品推荐

