在ui自动化测试过程中,目前存在最大的缺陷就是如果产品的ui或者结构改了那么这个项目进行的自动化测试脚本可能要面临全面维护。这也是目前ui自动化面临的很让人崩溃的事情。因此现在很多互联网产品项目发现ui自动化在测试中的价值越来越小,因为互联网产品的迭代太快,自动化测试组往往刚刚完善了自动化脚本,项目也跑起来了。突然来了项目大改版,崩溃啊,这意味这代码要重新进行维护,而且维护成本很高。可能维护完了产品需求又改了,往往跟不上脚步。因此我UI自动化比较适合以下两种情况的项目:1.产品原型趋于稳定阶段,2.手机固件项目(因为手机固件是在原生安卓上修改的,原生安卓的的系统构架通常短时间内很少会做重大改版,即使小改动也是一年一次)。
以前我们的自动化项目都是趋于关键字驱动,数据和代码是揉杂在一起的。我们写自动化测试用例的流程大概是这样的(以魅族社区发帖举例子只走流程不包括断言):点击发帖按钮—输入标题—输入正文—点击发送按钮
代码如下:
UiObject write_title=new UiObject(new UiSelector().resourceId("com.meizu.mzbbs:id/et_write_title"));
//assertTrue("write_title focusable is false", write_title.isFocused()==true);
Configurator config = Configurator.getInstance();
config.setKeyInjectionDelay(40);
write_title.setText(Utf7ImeHelper.e(“帖子标题”));
sleep(2000);
UiObject richet_post=new UiObject(new UiSelector().resourceId("com.meizu.mzbbs:id/richet_posts"));
richet_post.click();
sleep(2000);
//assertTrue("richet_post focusable is false", richet_post.isFocused()==true);
richet_post.setText(Utf7ImeHelper.e(“帖子正文”));
config.setKeyInjectionDelay(0);
sleep(2000);
UiObject send_post=new UiObject(new UiSelector().resourceId("com.meizu.mzbbs:id/action_send_posts"));
send_post.clickAndWaitForNewWindow(3000);
sleep(3000);
这样测试流程走通了,但是如过遇到以下问题1.resourceId改变了或者控件名称改变了(uiautomator也可以用控件名称定位控件)这就意味着我需要在代码中修改这些控件资源id或者name了。2.原始流程是A-B-C这种固定流程,万一流程中添加了F步骤变成A-F-B-C了,意味着在中间要插入一段代码,在无数行代码中找到这段代码然后插入,这样一定是很麻烦的而且还要调试。3.如果这个功能不要了意味着这些幸幸苦苦写的代码就白写了。相信以上问题都是大家在自动化测试实践过程中所到很蛋疼的问题。这也是为什么现阶段大家越来越对ui自动化持怀疑态度了,进而转向接口自动化的原因,因为随着产品的持续迭代维护成本越来越高。
那么为了解决以上问题,所以现在又出现了一种趋于数据驱动的自动化模型,就是将测试代码和测试数据分开来,做到代码和数据独自开来这样每次迭代我们只需要修改测试数据和少量测试代码就能对自动化测试脚本进行很好维护,同时能减少代码量,通过对方法的二次封装可以简化自动化测试的难度,使新手能更快的入手。整个设计思路为:将测试控件的资源id或者name和操作类型保存在excel表格或者数据库中,然后代码去读取excel表格中的控件资源数据作为参数传给操作代码。最后通过判断操作类型做出相应的操作,以上实现方法以魅族社区发帖步骤为例:
1.现在用excel建立一个管理测试数据的表格
2.获取表格中的资源id和操作方式数据主要方法如下:
public List<String> readXls(int rowNun)throw Exception{
String path="E:/新建 Microsoft Excel 97-2003 工作表.xls"
File file = new File(path);
InputStream is =new FileInputStream(
//默认第一个表格
HSSFSheet sheet = wb.getSheetAt(0);
HSSFRow row = sheet.getRow(rowNun);
int minColIx=row.getFirstCellNum();
int maxColIx=row.getLastCellNum();
List<String> result=new ArrayList<String>();
//过滤掉第一列和第二列数据
for(int collx=minColIx+2;collx<maxColIx;collx++){
HSSFCell cell=row.getCell(collx);
if(cell==null){
continue;
}
result.add(ExcelUtils.getStringVal(cell));
}
return result;
}
3.获取到数据后供uiautomator定位控件方法调用,接下来我们对获取的数据进行调用操作:
/*
通过判断操作类型来调用不同的用例方案
rowNum 读取数去行数
**/
public void testUI(int rowNum)throw Exception{
//还可以定义其他类型的操作(如:长按等)在里面这里只举例两种
if((String)this.readXls(rowNum).get(1).equals("单击")){
UiObject click=new UiObject(new UiSelector().resourceId((String)this.readXls(rowNum).get(0)));
richet_post.click();
sleep(2000);}
else if((String)this.readXls(rowNum).get(1).equals("输入")){
UiObject editText=new UiObject(new UiSelector().resourceId((String)this.readXls(rowNum).get(1)));
Configurator config = Configurator.getInstance();
config.setKeyInjectionDelay(40);
search_movies1.setText(Utf7ImeHelper.e((String)this.readXls(rowNum).get(2)));
config.setKeyInjectionDelay(0);}}
这样所有的工作都准备好了,我们设计测试用例定位控件操作时只要按照逻辑重复的调testUI(int rowNum)方法就行,只需修改rowNum参数,它会按照操作类型自动帮你调不同类型的操作。而且可以发现测试数据和代码都分离出来了。如果改了ui界面控件我们只需在excel表格中修改测试数据就行,就算项目大修改代码维护起来工作量也不是很大,而且操作逻辑上很灵活。(未完待续)。
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。