1. AndroidJUnitRunner介绍
AndroidJUnitRunner类是一个JUnit测试运行器,允许运行JUnit 3或JUnit 4测试类在Android设备上,包括那些使用Espresso和UI Automator框架。
2. AndroidJUnitRunner过滤器及参数
-e testFile <filePath> : 运行文件中指定的用例。
-e package <packageName>: 运行这个包中的所有用例。
-e size [small |medium| large]: 运行注解为SmallTest/MediumTest/LargeTest的用例。
-e annotation <annotation>: 运行指定注解的用例。
-e notAnnotation <annotation>: 运行不包含指定注解的用例。
-e numShards <num>: 将用例分割成不同的切片。
-e shardIndex <id>: 运行指定切片的用例。
-e debug true : 可以在代码中设置断点,通过此参数进行调试测试脚本。
-e log true: 只在日志模式下运行,将加载和遍历所有的测试类和方法,但会绕过实际的测试执行,用于快速获取通过instrumentation命令执行测试的信息。
-e coverage true: 生成代码覆盖率文件,这需要是一个集成了EMMA或JaCoCo的构建。 默认情况下,代码覆盖率结果文件将被保存在/data/data//files/coverage.ec文件,另外也可以自定义覆盖率结果文件的路径,e.g -e coverageFile /sdcard/myFile.ec。
-e listener <runlistener>: 指定一个或者多个运行监听器观察测试运行,可用于定制测试报告,e.g. -e listener com.foo.Listener,com.foo.Listener2.
-e timeout_msec <int> :设置超时时间,将被应用到每一个测试,e.g.-e timeout_msec 5000.
-e disableAnalytics true: 禁用谷歌分析, 主要是用于谷歌进行收集数据.
3. 帮助示例
3.1 运行所有的用例: adb shell am instrument -w com.android.foo/android.support.test.runner.AndroidJUnitRunner
3.2 运行一个类中的所有用例: adb shell am instrument -w -e class com.android.foo.FooTest com.android.foo/android.support.test.runner.AndroidJUnitRunner
3.3 运行单个测试用例:
db shell am instrument -w -e class com.android.foo.FooTest#testFoo com.android.foo/android.support.test.runner.AndroidJUnitRunner
3.4 运行多个类的所有用例:
adb shell am instrument -w -e class com.android.foo.FooTest,com.android.foo.TooTest com.android.foo/android.support.test.runner.AndroidJUnitRunner
3.5 运行所有测试用例除了指定的类:
adb shell am instrument -w -e notClass com.android.foo.FooTest com.android.foo/android.support.test.runner.AndroidJUnitRunner3.6 运行所有测试除了指定的用例: adb shell am instrument -w -e notClass com.android.foo.FooTest#testFoo com.android.foo/android.support.test.runner.AndroidJUnitRunner
3.7 运行文件中的所列的用例:
adb shell am instrument -w -e testFile /sdcard/tmp/testFile.txt com.android.foo/com.android.test.runner.AndroidJUnitRunner
文件制定的格式为:com.android.foo.FooClaseName#testMethodName
3.8 运行JAVA包中的所有测试用例: adb shell am instrument -w -e package com.android.foo.bar com.android.foo/android.support.test.runner.AndroidJUnitRunner
3.9 运行指定测试切片的用例:adb shell am instrument -w -e numShards 4 -e shardIndex 1 com.android.foo/android.support.test.runner.AndroidJUnitRunner
3.10 运行指定注解的测试用例:adb shell am instrument -w -e annotation com.android.foo.MyAnnotation com.android.foo/android.support.test.runner.AndroidJUnitRunner。如果使用多个选项,则运行的用例为两者的交集,比如:“-e size large -e annotation com.android.foo.MyAnnotation”,将只运行同时含LargeTest和MyAnnotation注解的用例。
3.11 运行没有指定注解的用例:adb shell am instrument -w -e notAnnotation com.android.foo.MyAnnotation com.android.foo/android.support.test.runner.AndroidJUnitRunner,指定多个注解,用“,”隔开,e.g. adb shell am instrument -w -e notAnnotation com.android.foo.MyAnnotation,com.android.foo.AnotherAnnotation com.android.foo/android.support.test.runner.AndroidJUnitRunner
3.12 以上所有参数也可以通过<meta-data>标签配置在AndroidManifest文件,比如 <meta-data android:name="listener" android:value="com.foo.Listener"/>,通过shell命令传入的参数将覆盖AndroidManifest文件中配置的参数。
4. 工程实践
4.1 通过测试切片,运行测试:
测试用例:
@RunWith(AndroidJUnit4.class)
public class TestClass01 {
public UiDevice mDevice;
public Instrumentation instrumentation;
@Before
public void setUp(){
instrumentation = InstrumentationRegistry.getInstrumentation();
mDevice = UiDevice.getInstance(instrumentation);
}
@Test
public void testCase01() throws IOException {
//test code
}
@Test
public void testCase02(){
//test code
}
@Test
public void testCase03(){
//test code
}
@Test
public void testCase04(){
//test code
}
}
执行测试:
am instrument -w -r -e numShards 4 -e shardIndex 1 com.test.tommyxie.hellouiautomator.test/android.support.test.runner.AndroidJUnitRunner 执行结果:
遇到的坑:
1. 切片数需要能被用例数整除,否则切片不成功,如下:
am instrument -w -r -e numShards 3 -e shardIndex 1 com.test.tommyxie.hellouiautomator.test/android.support.test.runner.AndroidJUnitRunner 2. 切片的索引为从0开始算起,比如切片为4份,指定运行的索引为4时,将会执行所有用例:
am instrument -w -r -e numShards 4 -e shardIndex 4 com.test.tommyxie.hellouiautomator.test/android.support.test.runner.AndroidJUnitRunner
rds 4 -e shardIndex 4 com.test.tommyxie.hellouiautomator.test/android.support*
INSTRUMENTATION_STATUS: numtests=4
INSTRUMENTATION_STATUS: stream=
com.test.tommyxie.hellouiautomator.TestClass01:
INSTRUMENTATION_STATUS: id=AndroidJUnitRunner
INSTRUMENTATION_STATUS: test=testCase01
INSTRUMENTATION_STATUS: class=com.test.tommyxie.hellouiautomator.TestClass01
INSTRUMENTATION_STATUS: current=1
INSTRUMENTATION_STATUS_CODE: 1
INSTRUMENTATION_STATUS: numtests=4
INSTRUMENTATION_STATUS: stream=.
INSTRUMENTATION_STATUS: id=AndroidJUnitRunner
INSTRUMENTATION_STATUS: test=testCase01
INSTRUMENTATION_STATUS: class=com.test.tommyxie.hellouiautomator.TestClass01
INSTRUMENTATION_STATUS: current=1
INSTRUMENTATION_STATUS_CODE: 0
INSTRUMENTATION_STATUS: numtests=4
INSTRUMENTATION_STATUS: stream=
INSTRUMENTATION_STATUS: id=AndroidJUnitRunner
INSTRUMENTATION_STATUS: test=testCase02
INSTRUMENTATION_STATUS: class=com.test.tommyxie.hellouiautomator.TestClass01
INSTRUMENTATION_STATUS: current=2
INSTRUMENTATION_STATUS_CODE: 1
INSTRUMENTATION_STATUS: numtests=4
INSTRUMENTATION_STATUS: stream=.
INSTRUMENTATION_STATUS: id=AndroidJUnitRunner
INSTRUMENTATION_STATUS: test=testCase02
INSTRUMENTATION_STATUS: class=com.test.tommyxie.hellouiautomator.TestClass01
INSTRUMENTATION_STATUS: current=2
INSTRUMENTATION_STATUS_CODE: 0
INSTRUMENTATION_STATUS: numtests=4
INSTRUMENTATION_STATUS: stream=
INSTRUMENTATION_STATUS: id=AndroidJUnitRunner
INSTRUMENTATION_STATUS: test=testCase03
INSTRUMENTATION_STATUS: class=com.test.tommyxie.hellouiautomator.TestClass01
INSTRUMENTATION_STATUS: current=3
INSTRUMENTATION_STATUS_CODE: 1
INSTRUMENTATION_STATUS: numtests=4
INSTRUMENTATION_STATUS: stream=.
INSTRUMENTATION_STATUS: id=AndroidJUnitRunner
INSTRUMENTATION_STATUS: test=testCase03
INSTRUMENTATION_STATUS: class=com.test.tommyxie.hellouiautomator.TestClass01
INSTRUMENTATION_STATUS: current=3
INSTRUMENTATION_STATUS_CODE: 0
INSTRUMENTATION_STATUS: numtests=4
INSTRUMENTATION_STATUS: stream=
INSTRUMENTATION_STATUS: id=AndroidJUnitRunner
INSTRUMENTATION_STATUS: test=testCase04
INSTRUMENTATION_STATUS: class=com.test.tommyxie.hellouiautomator.TestClass01
INSTRUMENTATION_STATUS: current=4
INSTRUMENTATION_STATUS_CODE: 1
INSTRUMENTATION_STATUS: numtests=4
INSTRUMENTATION_STATUS: stream=.
INSTRUMENTATION_STATUS: id=AndroidJUnitRunner
INSTRUMENTATION_STATUS: test=testCase04
INSTRUMENTATION_STATUS: class=com.test.tommyxie.hellouiautomator.TestClass01
INSTRUMENTATION_STATUS: current=4
INSTRUMENTATION_STATUS_CODE: 0
INSTRUMENTATION_RESULT: stream=
Time: 0.131
OK (4 tests)4.2 通过自定义注解,运行测试:
参照既有的注解的格式e.g.LargeTest注解,新建一个定义注解:
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.METHOD, ElementType.TYPE})
public @interface CustomAnnotation {
}测试用例引用自定义注解:
@RunWith(AndroidJUnit4.class)
public class TestClass01 {
public UiDevice mDevice;
public Instrumentation instrumentation;
@Before
public void setUp(){
instrumentation = InstrumentationRegistry.getInstrumentation();
mDevice = UiDevice.getInstance(instrumentation);
}
@Test
public void testCase01() throws IOException {
//test code
}
@Test
@CustomAnnotation
public void testCase02(){
//test code
}
@Test
public void testCase03(){
//test code
}
@Test
public void testCase04(){
//test code
}
}指定注解,运行测试:
am instrument -w -r -e annotation com.test.tommyxie.hellouiautomator.CustomAnnotation com.test.tommyxie.hellouiautomator.test/android.support.test.runner.AndroidJUnitRunner
4.3 通过AndroidManifest文件配置参数,运行测试,e.g.指定注解运行测试:
Manifest 文件配置
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.test.tommyxie.hellouiautomator">
<application android:allowBackup="true"
android:label="@string/app_name"
android:icon="@mipmap/ic_launcher"
android:theme="@style/AppTheme">
<instrumentation
android:name="com.android.support.test.runner.AndroidJUnitRunner"
android:targetPackage="com.test.tommyxie.hellouiautomator">
<meta-data
android:name="annotation"
android:value="com.test.tommyxie.hellouiautomator.CustomAnnotation" />
</instrumentation>
</application>
</manifest>运行测试,发现未按配置好的参数,运行指定的用例,还是会执行全部的用例。(备注:根据官方的说明,在manifest文件中配置参数,可以实现同样的效果,但是确认了配置是正确的,翻阅了一些资料,目前暂未找到原因)
本文详细介绍了AndroidJUnitRunner的使用,包括如何通过-e参数运行特定的测试用例、过滤器、注解、切片等。还提供了各种运行测试的示例,如按类、按方法、按包、按注解筛选,并提到了代码覆盖率生成、监听器配置以及通过AndroidManifest文件设置参数等实践操作。

1万+

被折叠的 条评论
为什么被折叠?



