背景介绍
android开发过程中,每次迭代升级都需要去回归一下之前版本功能,看看最新的修改有没有影响到之前的正常功能。然而这个过程永远都是在做一些繁琐的重复的操作,大大浪费人力,所以我们决定使用自动化来做这个事情,这就引入了我们接下来要介绍的自动化测试框架——robotium。
Robotium是一款国外的Android自动化测试框架,主要针对Android平台的应用进行黑盒自动化测试,它提供了模拟各种手势操作(点击、长按、滑动等)、查找和断言机制的API,能够对各种控件进行操作。
配置robotium
robotium配置起来也很方面。首先在build.gradle中添加依赖
compile 'com.jayway.android.robotium:robotium-solo:5.6.0'
然后需要在测试工程中的AndroidManifest.xml中做如下的配置
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="xxxx.test">
<uses-library android:name="android.test.runner" />
<instrumentation
android:targetPackage="xxx"
android:name="android.test.InstrumentationTestRunner"
/>
</manifest>
上面的package="xxxx.test"是我们测试包的名称,下面定义的instrumentation中的tartPackage="xxx"是我们被测试工程的包名称,这个配置很关键,出问题的话很容易出现找不到被测试包的错误。以上就是简单的配置了,接下来就可以开始写测试代码了。
Quick Start Guide
在测试包下面创建一个测试类,命名规范为XxxTest,该类继承ActivityInstrumentationTestCase2,构造方法中需要传入app的启动activity。代码如下:
private static final String LAUNCHER_ACTIVITY_FULL_CLASSNAME = "xxxx.LuancherActivity";
private static Class<?> launcherActivityClass;
static{
//通过反射的方式获取的
try {
DebugUtil.debug(TAG, "启动类"+LAUNCHER_ACTIVITY_FULL_CLASSNAME);
launcherActivityClass = Class.forName(LAUNCHER_ACTIVITY_FULL_CLASSNAME);
} catch (ClassNotFoundException e) {
throw new RuntimeException(e);
}
}
public XxxTest() throws ClassNotFoundException {
super(launcherActivityClass);
}
以上就设置好了启动的activity,然后需要重载两个方法
public void setUp() throws Exception;
public void tearDown() throws Exception;
setUp()做一些启动测试前的准备工作,如创建Solo实例,启动activity等
@Override
public void setUp() throws Exception {
super.setUp();
//创建Solo实例
solo = new Solo(getInstrumentation());
//启动activity
getActivity();
}
tearDown()中测试做一些善后的工作,如结束activity等
@Override
public void tearDown() throws Exception {
solo.finishOpenedActivities();
super.tearDown();
}
上述工作准备好之后,剩下的就是我们的测试主体方法了。方法格式如下:
public void testXxxx() {
}
注意测试方法必须按照如上格式,否则框架无法识别测试方法,也就无法运行了。这种形式的方法在一个类中是可以定义多个的。在setUp()中我们定义了一个Solo实例,这个实例到底有什么用呢?接下来稍微讲一些Solo类的用法,如果里面有的功能无法满足你的需求,可以自行去查看api文档。
Solo类用法
- 点击控件
solo.clickOnView(solo.getView(???));
-
获取控件
solo.getView()
参数说明:
int id:直接调用R.id.xxx
int index:表示该控件是该页面的第几个同id控件。
Object tag:控件的tag属性
String id:xml中定义的id属性 -
点击按钮(可通过点击控件实现)
solo.clickOnButton()
参数说明:
int index:该页面的第几个按钮
String text:按钮上的文字 -
验证toast文字
toast的本质就是一个TextView,通过上述代码即可验证toast中显示的文本。
-
在输入框输入文本
参数说明:
第一种方法获取editText可以通过2中的方法获取,text即为待输入文本。
第二种方法中index为该页面上的第几个输入框。 -
等待对话框关闭和打开
参数说明:
long timeout:设置超时时间,单位为毫秒 -
验证activity的加载
参数说明:
String:直接传入activity名称字符串即可。
int:超时事件,默认为20000,单位为毫秒
Class<? extends Activity>:直接传入activity实例 -
获取网页元素
主要说明一下By类的用法
By.id(String) 元素的id
By.xpath(String) 元素的节点路径
By.cssSelector(String) 元素的css selector
By.name(String) 元素的name属性
By.className(String) 元素的class属性
By.textContent(String) 元素的textContent属性
By.tagName(String) 元素的tag属性 -
网页元素输入文本
type和enter的区别在于type输入时,相当于在输入完后直接键入了一个回车,而enter没有。
-
点击网页元素
int match表示当有多个匹配时取哪一个,默认为0
boolean srcoll 表示是否要滑动,默认为true -
验证网页元素是否加载成功
int miniumumNumberOfMatch 表示至少要找到多少个
int timeout 超时,单位为毫秒
boolean scroll 是否滑动