web 自动化测试框架的一些想法和实践
来源:互联网 发布:小学语文软件天天练 编辑:程序博客网 时间:2024/05/22 09:41
最近用java在写自动化测试框架,写着写着有点感觉好繁复。所以写出来希望可以得到一些建议,以下主要针对的是网页测试,总体的想法是:
1. Page Object模式,页面元素和外面的测试数据的模型命名一样,这样省去一些对应的代码,里面自己分装了自定义的元素
2. 使用类似于爬虫的第三方包生成page object 模型
3. 通过操作流程直接生成测试代码
4. 使用testng,data provider 来驱动测试
以下是一些实现:
使用一下脚本解析页面元素,source.txt是页面的html源码,可以页面片段也可以是整个页面:
PageObjectParser poParser = PageObjectParser.buildFromFilePath("source.txt");poParser.parseRadio();poParser.parseInputBox("ng-model");
得到一下结果:
@ElementName(elementName="property.propertyUsage")private Radio propertyUsage;@FindBy(name="property.estateName")@ElementName(elementName = "property.estateName")private InputBox estateName;@FindBy(name="property.address")@ElementName(elementName = "property.address")private InputBox address;@FindBy(name="property.roomNo")@ElementName(elementName = "property.roomNo")private InputBox roomNo;@FindBy(name="property.permitNo")@ElementName(elementName = "property.permitNo")private InputBox permitNo;
稍微复杂点的页面:
PageObjectParser poParser = PageObjectParser.buildFromFilePath("source.txt"); poParser.parseRadio(); poParser.parseInputBoxInTable("ng-model"); poParser.parseSelect("div");
得到结果:
@FindBy(name="property_propertySource")@ElementName(elementName="property.propertySource")private Radio propertySource;@FindBy(name="property_status")@ElementName(elementName="property.status")private Radio status;@FindBy(name="property_shape")@ElementName(elementName="property.shape")private Radio shape;@FindBy(name="property_currentStatus")@ElementName(elementName="property.currentStatus")private Radio currentStatus;@FindBy(name="property_propertyLook")@ElementName(elementName="property.propertyLook")private Radio propertyLook;@FindBy(name="property_isAuction")@ElementName(elementName="property.isAuction")private Radio isAuction;@FindBy(name="property_flagLoan")@ElementName(elementName="property.flagLoan")private Radio flagLoan;@FindBy(xpath="//tr[not(contains(@style,'display: none'))]//input[@name='property_contactName']")@ElementName(elementName="property.contactName")private InputBox contactName;@FindBy(xpath="//tr[not(contains(@style,'display: none'))]//input[@name='property_floorAll']")@ElementName(elementName="property.floorAll")private InputBox floorAll;@FindBy(xpath="//tr[not(contains(@style,'display: none'))]//input[@name='property_floorHeight']")@ElementName(elementName="property.floorHeight")private InputBox floorHeight;@FindBy(xpath="//tr[not(contains(@style,'display: none'))]//select[@name='property_relationship']")@ElementName(elementName="property.relationship")private SelectList relationship;
生成页面模型之后,生成一个页面元素描述的excel,可以是多个页面:
WebUICodeGenerator.build().writePageObjectsToExcel("sample.xls", Lists.newArrayList(MockPage1.class,MockPage2.class));
给业务流程自定需要跑那些元素,标上顺序,使用代码生成一个流程的方法或者注解:
2. 自动生成annotation 或者测试代码
当整个业务流程涉及的页面完成后,使用如下的代码生成一份excel:
WebUICodeGenerator t= WebUICodeGenerator.build("AddProperty.xls"); t.generateAnnotationStatement("流程1"); t.generateAnnotationStatement("流程12");
注解或者代码:得到注解
MockPage1:@UIActions(actions={@UIAction(processName="流程1",elementActionDescription={"propertyUsage","estateName","address","roomNo"})})MockPage2:@UIActions(actions={@UIAction(processName="流程1",elementActionDescription={"contactName","floorAll","isAuction","currentStatus","status","propertyDecoration"})})
放到页面Page Object类去。编写流程类:
最后构建整个业务流程,使用如下代码:中文命名只是为了说明使用。
public class 流程1 extends BaseWebTestAction { public 流程1(WebDriver driver, TestData testData) { super(driver, testData); } @Override public void execute() { WebTestActionBuilder.createTestActionByUIAction(MockPage1.class, "流程1",driver, testData).execute(); WebTestActionBuilder.createTestActionByUIAction(MockPage2.class, "流程1",driver, testData).execute(); }}
以上代码中execute()实质上等价:
MockPage1 page1 = ModifiedPageFactory.createPageObject(driver,MockPage1.class); page1.processUIAction("流程1",testData); MockPage2 page2 = ModifiedPageFactory.createPageObject(driver,MockPage2.class); page2.processUIAction("流程1",testData);
或者:
MockPage1 page1 = ModifiedPageFactory.createPageObject(driver,MockPage1.class); page1.getPropertyUsage().selectByVisibleText(testData.get("propertyUsage")); page1.getAddress().input(testData.get("address")); page1.getEstateName().input(testData.get("estateName")); page1.getRoomNo().input(testData.get("roomNo")); MockPage2 page2 = ModifiedPageFactory.createPageObject(driver,MockPage2.class); page2.getContactName().input(testData.get("contractName")); ...........
如果不生成注解,直接生成代码就是:
使用代码:
WebUICodeGenerator.build("AddProperty.xls").generateSingleTestStep("流程1");
生成流程的函数:
public static void 流程1(WebDriver driver,TestData testData){WebTestActionBuilder.createTestActionByElementActionList(MockPage1.class,Lists.newArrayList("propertyUsage","estateName","address","roomNo"),driver,testData).execute();WebTestActionBuilder.createTestActionByElementActionList(MockPage2.class,Lists.newArrayList("contactName","floorAll","isAuction","currentStatus","status","propertyDecoration"),driver,testData).execute();}
3. 测试数据准备
测试离不开测试数据的准备,测试数据类可以直接页面Page Object来生成:
WebUICodeGenerator t= WebUICodeGenerator.build(); t.generateTestDataClass(Lists.newArrayList(MockPage1.class,MockPage2.class));
结果:
private String roomNo;private String permitNo;private String propertySource;private String status;private String shape;private String currentStatus;private String propertyLook;..........
使用testng 驱动测试
public class SampleTest extends BaseWebTest { @DataProvider(name = "sample_data") public Iterator<Object[]> getAPITestData(Method m) throws Exception{ Map<String, Class> clazzMap = new HashMap<String, Class>(); clazzMap.put("Sample", Sample.class); Iterator<Object[]> y = ExcelHelper.build("abc.xls").ToIteratorInColMode(clazzMap); return y; } @Test(dataProvider ="property_data" ) public void addProperty(Sample testData) { Login。。。。。 流程1 flow = new 流程1(driver,testData); flow.execute(); }}
excel的数据就是类似与:
大概的思路是这样的。请大家多提宝贵意见。在这个过程可能可能看不到一些webdriver的操作,这个操作主要是封装了一层对应关系,每个自定义元素都有一个默认操作,没有特别说明就使用默认的操作。
其中对于自定义的元素也是使用过了PageFactory的方式,参考selenium的实现,自己做了一些定制化。
感谢分享,这是个很不错的思路,大部分体力活用自动生成来做。
不知道你说的 “繁复” 具体是指什么?就这么看的话没觉得哪里明显繁复啊。
PS:麻烦添加头像,最后的 excel 数据 那里表格的 markdown 用错了,具体怎么用可以参考右下角排版说明。
多谢,已修改.繁复,怎么说呢,就是用的人觉得有点复杂. 所以我不知道其他公司的框架是怎么样用的。
解析页面生成页面元素表挺可行的
1.为什么页面源码还要存个source.txt,不直接去爬虫解析的页面生成页面元素表
2.如果页面变了,重新解析生成的页面元素表,你这个维护再同一张表内的case流程顺序是不是就得重新排了?
3.作为一个菜鸟测试,感觉真的好复杂,技术菜逼伤不起
- 关于存source文件主要是可以一个页面片段一个页面片段去组装,另外有些页面源码在查看页面源码的时候不能完全看到 2.页面变了肯定要改的,如果小改动就不需要去重新生成了,代码都生成好了就在代码里面改
我感觉好像很多人担心页面改了会怎么样,我怎么觉得这其实不是什么问题,因为改了就相应的改一下,关键其实如果遇到改动,貌似没有什么很好的解决方案可以让测试代码完全不改。有些情况下可能定位可以写好一点比如是针对一些特定的属性或者css,其他我感觉这个问题无解,而且不是什么问题,开发代码改了,测试代码也改貌似挺合理的。我个人的理解,可能太肤浅了。
俩个问题请教:
1. 对于重复元素的定位,怎样精确定位
2. expectation怎么写
- web 自动化测试框架的一些想法和实践
- 关于Web应用API设计的一些想法和实践
- 没做过自动化测试的一些初级想法
- 基于Sahi和Twist搭建的Web自动化测试框架
- Web UI自动化应用测试框架实践 - 概览
- appium + xml + web 自动化测试框架设想及实践分享
- Web自动化测试框架
- Web UI 自动化测试实践
- 《QTP自动化测试实践》读者来信 - 买《QTP自动化测试实践》后的一些看法
- vueJs入门实践遇到的坑和一些想法
- 基于Grunt&mocha JavaScript自动化测试框架的实践
- Web自动化测试框架改进
- web自动化测试框架目录
- 关于web自动化测试的一些自己的思考和总结
- 自己动手写Web自动化测试框架(6):自动化测试框架的规划
- 关于功能自动化测试的一些想法(持续更新ing)
- 基于Java+Selenium+Appium集成Web、安卓和IOS自动化测试框架的设计
- 基于Java+Selenium+Appium集成Web、安卓和IOS自动化测试框架的设计
- 公司如何调薪才能让员工满意
- 开始在linux下做c语言开发
- Effective C++条款16:成对使用new和delete时要采取相同形式
- Java并发编程-33-线程安全的可遍历映射
- Hibernate缓存系列之原理与策略
- web 自动化测试框架的一些想法和实践
- HDU 5272 Dylans loves numbers
- 树结构练习——排序二叉树的中序遍历
- Java--Reflect(反射)专题2——动态加载类
- 游戏开发——Cocos2d-x
- Redis配置详解
- Hadoop学习(8)----MapReduce讲解
- EGORefreshTableHeaderView学习
- 【读书笔记:C++ primer plus 第六版 中文版】第3章:数据处理