在 TesterHome 潜水很久,基本处于看帖不发贴的状态,很好的一个社区。在这里面学习到很多知识,无论是技术还是思想。
今天决定分享一下自己做的脚本录制回放工具,听取一下大家建议。
公司项目上面的原因,需要制作自动化测试的脚本录制回放工具,方便没有代码基础的测试工程师进行自动化测试。所以我这个 ATE 就只能硬着头皮来实现了。
其实我个人一直觉得脚本录制这个动作并没有什么用,一个好的测试脚本还是要靠写。毕竟录制的过程无法生成各种逻辑处理,而一个优秀的测试脚本,强健的逻辑处理是必不可少的。
1. 设备识别界面
没错,ThunderSoft 就是我们公司的名字。
打开工具时,会自动识别已经连接上 PC 的手机,如果连接了多台设备,界面的 Combox 控件就会显示多台手机的 id 让你选择。
然后点击 “开始” 按钮进入下一个界面。
2. 录制界面
红色区域:
手机屏幕实时投射界面,手机的画面会实时的投射到工具上面,不用说应该很多人也知道这一块用 Minicap 就可以完成,传输效率还是很不错的。
蓝色区域:
录制脚本时,脚本的显示区域,做了文本的关键词高亮显示处理。
橙色区域:
开始录制脚本按钮
绿色区域:
脚本菜单,通过这个菜单可以导出脚本和进入脚本回放页面。
3. 输入校准界面
当点击开始录制按钮后,会进入输入校准的界面,因为需要兼容到很多不同的手机,所以需要在录制之前校准输入,测试人员需要在屏幕的任意位子点击一下屏幕完成校准。
校准完成后就可以录制脚本啦!!!!!!看校准框里面的信息,应该很多人可以猜到录制功能是依靠什么来实现的了。
4. 正在录制界面
红色框体:
里面显示的内容,就是你操作手机时录制出来的脚本,可以看到脚本有坐标形式展现的,也有通过控件相关属性展现的,
所以工具在进行录制的过程中,还是有对布局进行分析检索的动作。
实际使用过程中,TE 的反馈,录制准确率控制在 76.3%~87.2% 之间,不准确的消耗点主要还是在对输入坐标和布局文件计算上面,这部分还是有很大空间进行优化的。
点击左上角红色按钮就可以停止录制,然后通过菜单项中的导出脚本功能导出脚本了。脚本是 Python 脚本。
5. 脚本回放界面
红色区域:
要进行回放的脚本显示区域,会显示出脚本的名字,路径,测试结果,测试次数,剩余测试次数等内容。
这个 List 中的 item 在开启测试之前是可以进行拖动的,调整测试顺序。
绿色区域:
脚本回放过程中,执行信息的显示,脚本中每一个动作的执行内容和结果都会显示在这个区域。
6. 脚本导入问题
脚本的导入,是直接导入 xml 类型的配置文件,在这个文件中配置了当前测试的模式,时间,已经脚本和脚本测试的次数。
实际回放过程中也会根据配置文件中的配置数据控制测试过程。
希望社区的牛人们多多给意见。
老板,加个精~
不错不错,python 脚本,我喜欢。但是感觉楼主还没说完,毕竟光录制成脚本还不够,如何断言如何处理 log 文件这些都还没说
#2 楼 @jamesparagon 写了一半开会去了 . 要补上。
没有现成的工具吗?
另外,跳转和响应的延迟怎么搞?
喜欢网易云音乐的还真多
感觉思路也不错的样子,生成的脚本具体长什么样子,方便用 markdown 格式化,看下
期待楼主后面的分享
页面解析速度快么 用什么解析的
可以开放出来,给大家试用试用呗
是呀是呀
你工具的录制和回放的成功率大概是多少呢?
楼主,滑动怎么处理的?
@kilmer 你这个录制工具,使用什么方法录制的呢?
缺乏对技术原理的介绍. 社区鼓励多 show 代码和技术原理.
#10 楼 @jamesparagon
首先赞成你的说的,录制脚本这个动作存在偏差问题。(我一直认为录制这个功能有点华而不实。)
关于控件重叠问题:
我目前没有遇到完全重叠的情况,只要不是完全重叠就可以通过不断优化判定控件的计算方法来定位控件,目前我是这么做的,以计算器举例
用户点击 Delete 的时候怎么完成对控件的精准筛选呢?
看代码
private boolean isInWidget(String bounds,int x,int y){
int x1=0,y1=0,x2=0,y2=0;
Matcher matcher = pattern.matcher(bounds);
while (matcher.find()) {
x1 = Integer.valueOf(matcher.group(1));
y1 = Integer.valueOf(matcher.group(2));
x2 = Integer.valueOf(matcher.group(3));
y2 = Integer.valueOf(matcher.group(4));
}
if ((x1 <= x) && (x <= x2) && (y1 <= y) && (y <= y2)) {
return true;
}
else {
return false;
}
}
private void findWidget(Element element,int widgetX,int widgetY){
NodeList widgets = element.getChildNodes();
for (int i = 0; i < widgets.getLength(); i++) {
Element widget = (Element) widgets.item(i);
if (widget.getAttribute("clickable").equals("true") && isInWidget(widget.getAttribute("bounds"), widgetX, widgetY)) {
widgetList.add(widget);
}
if (widget.getChildNodes().getLength()>0) {
findWidget(widget, widgetX, widgetY);
}
}
}
private int findBestWidget(int x,int y){
int marginX = 0;
int marginY = 0;
int tmpIndex = 0;
if (widgetList.size() > 0) {
for (int i = 0; i < widgetList.size(); i++) {
String bounds = widgetList.get(i).getAttribute("bounds");
// 分析bounds
int x1=0,y1=0,x2=0,y2=0;
Matcher matcher = pattern.matcher(bounds);
while (matcher.find()) {
x1 = Integer.valueOf(matcher.group(1));
y1 = Integer.valueOf(matcher.group(2));
x2 = Integer.valueOf(matcher.group(3));
y2 = Integer.valueOf(matcher.group(4));
}
// 计算边距
int tmpMarginX = x - x1;
int tmpMarginY = y - y1;
if (i > 0) {
if ((tmpMarginX < marginX)||(tmpMarginY < marginY)) {
marginX = tmpMarginX;
marginY = tmpMarginY;
tmpIndex = i;
}
}
else {
marginX = tmpMarginX;
marginY = tmpMarginY;
tmpIndex = i;
}
}
return tmpIndex;
}
else {
return -1;
}
}
这段代码是在手机上面执行的哈,解析的数据会按照 JSON 串的形式返回给工具。
#10 楼 @jamesparagon
另外一个问题,关于控件没有属性
不要忘了是有 xpath 的哦 ,xpath 相对路径下 bounds 也可以成为标注控件的唯一属性。
#10 楼 @jamesparagon
第三个问题,回放的执行效率和录制时不一样
如果录制出来的脚本直接进行回放,的确是有这个问题,除非你自己在录制功能模块中加入了计时功能,能记录测试人员录制时的时序,让然后回放的时候再体现出来 。
不过我这个没加这个功能,录制出来的脚本也不会直接进行回放,而是需要进行逻辑处理然后验证脚本健壮性没有问题后,在入库投入到使中。
原理:通过 adb 实时监控读取 android 的事件并解析,翻译成对应的 action 脚本?
@kilmer agent 解决的吧 通过 socket 传输到 pc 端
@kilmer 看来你玩整机的
@kilmer 呵呵 辛苦 整机不好做 要求功力非凡 跨界很麻烦
这个真心不错,如果详细点就好了,期待下面的内容,
我用按键精灵是不是显得太 out 了(手动哭笑不得表情)
楼主能说一下技术原理和 show 一下代码吗?
...你这是简介啊 可以介绍原理吗?用了什么工具?录制的原理是什么?为什么要适配?获取屏幕计算相对坐标不可以吗?GUI 是 py 写的吗? ...要不放出来大家一起用吧
惊为天人
这个思路很好呀~ 楼主能否把代码放出来,大家一起用么?
界面对比吧
没有试用版吗 小哥?