转载:https://www.jianshu.com/p/82fdd2db9c44
在创建测试自动化框架时,我们应该考虑以下要点:
自动化测试的基本步骤.png
功能
对页面上的操作行为进行拆分和抽象,保存为一个个具体的行为关键字。用户根据需求对关键字进行组装
实现
将每个页面的操作行为,封装为不同的关键字函数,测试用例可调用不同关键字,组成不同的操作流程
好处
将单个行为和系统流程拆分,减少耦合,所有的用例针对同一个行为是调用同一个函数,减少维护成本
坏处
关键字的个数和页面功能的复杂性成正比
应用
page object model
考虑这个简单的脚本登录网站:
如图所示,我们所做的只是找到元素并为这些元素填充值。这是一个小脚本。脚本维护看起来很简单 但随着时间的推移测试套件将会增长 随着代码添加越来越多,维护将变得越来越困难。脚本维护的主要问题是,如果10个不同的脚本使用相同的页面元素,并且该元素有任何更改,则需要更改所有10个脚本。这是耗时且容易出错的。
更好的脚本维护方法是创建一个单独的类文件,该文件可以找到Web元素,填充它们或验证它们。可以在使用该元素的所有脚本中重用此类。将来,如果Web元素发生更改,我们只需要在1个类文件中进行更改,而不是10个不同的脚本。这种方法称为页面对象模型(POM)。它有助于使代码 更具可读性,可维护性和可重用性。
Page Object Model是一种为Web UI元素创建Object Repository的设计模式。在此模型下,对于应用程序中的每个网页,应该有相应的页面类。此Page类将查找该Web页面的WebElements,还包含对这些WebElements执行操作的Page方法。这些方法的名称应根据它们正在执行的任务给出,即,如果加载程序正在等待显示支付网关,则POM方法名称可以是waitForPaymentScreenDisplay()。
关于页面对象是否应该包含断言本身,或者仅为测试脚本提供数据以进行断言,存在意见分歧。
在页面对象中包含断言的倡导者说,这有助于避免在测试脚本中重复断言,使得更容易提供更好的错误消息,并支持更多的TellDontAsk样式API。
无断言页面对象的倡导者说,包含断言将提供对页面数据的访问权限与断言逻辑混合在一起,并导致一个膨胀的页面对象。
我赞成在页面对象中没有断言。我认为您可以通过为常见断言提供断言库来避免重复 - 这也可以使提供良好诊断更容易。页面对象通常用于测试,但不应自行进行断言。他们的职责是提供对底层页面状态的访问。由测试客户端来执行断言逻辑。
简单的例子:
详细的例子:
步骤1)转到Guru99演示站点
步骤2)在主页检查文本“Guru99 Bank”存在
步骤3)登录应用程序
步骤4)验证主页是否包含“Manger Id:demo”
功能中包含两个页面:
1. Login page POM
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
public class Guru99Login {
WebDriver driver;
By user99GuruName = By.name("uid");
By password99Guru = By.name("password");
By titleText =By.className("barone");
By login = By.name("btnLogin");
public Guru99Login(WebDriver driver){
this.driver = driver;
}
//Set user name in textbox
public void setUserName(String strUserName){
driver.findElement(user99GuruName).sendKeys(strUserName);
}
//Set password in password textbox
public void setPassword(String strPassword){
driver.findElement(password99Guru).sendKeys(strPassword);
}
//Click on login button
public void clickLogin(){
driver.findElement(login).click();
}
//Get the title of Login Page
public String getLoginTitle(){
return driver.findElement(titleText).getText();
}
/**
* This POM method will be exposed in test case to login in the application
* @param strUserName
* @param strPasword
* @return
*/
public void loginToGuru99(String strUserName,String strPasword){
//Fill user name
this.setUserName(strUserName);
//Fill password
this.setPassword(strPasword);
//Click Login button
this.clickLogin();
}
}
2. Home Page POM;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
public class Guru99HomePage {
WebDriver driver;
By homePageUserName = By.xpath("//table//tr[@class='heading3']");
public Guru99HomePage(WebDriver driver){
this.driver = driver;
}
//Get the User name from Home Page
public String getHomePageDashboardUserName(){
return driver.findElement(homePageUserName).getText();
}
}
3. 测试用例
import java.util.concurrent.TimeUnit;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.firefox.FirefoxDriver;
import org.testng.Assert;
import org.testng.annotations.BeforeTest;
import org.testng.annotations.Test;
import pages.Guru99HomePage;
import pages.Guru99Login;
public class Test99GuruLogin {
WebDriver driver;
Guru99Login objLogin;
Guru99HomePage objHomePage;
@BeforeTest
public void setup(){
driver = new FirefoxDriver();
driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
driver.get("http://demo.guru99.com/V4/");
}
/**
* This test case will login in http://demo.guru99.com/V4/
* Verify login page title as guru99 bank
* Login to application
* Verify the home page using Dashboard message
*/
@Test(priority=0)
public void test_Home_Page_Appear_Correct(){
//Create Login Page object
objLogin = new Guru99Login(driver);
//Verify login page title
String loginPageTitle = objLogin.getLoginTitle();
Assert.assertTrue(loginPageTitle.toLowerCase().contains("guru99 bank"));
//login to application
objLogin.loginToGuru99("mgr123", "mgr!23");
// go the next page
objHomePage = new Guru99HomePage(driver);
//Verify home page
Assert.assertTrue(objHomePage.getHomePageDashboardUserName().toLowerCase().contains("manger id : mgr123"));
}
2.1.5 扩展
Page Factory是Selenium WebDriver的内置页面对象模型概念,但它已经过优化。在这里,我们遵循页面对象存储库和测试方法的分离概念。另外,在PageFactory类的帮助下,我们使用@FindBy注释来查找WebElement。我们使用initElements方法初始化Web元素
@FindBy可以接受tagName,partialLinkText,name,linkText,id,css,className,xpath作为属性。让我们使用Page Factory查看与上面相同的示例
软件开发中常见的浪费活动包括:
低行为的沟通可能是使用BDD的最大优势,使技术团队和非技术团队之间的协作能够以更高的效率运行。用通用语言编写的BDD测试用例的优点是所有人都可以容易地理解应用程序的行为方式。例如,可以使用实际需求的实时示例编写测试用例,以解释系统的行为,减少误解。
能更方便的会用例进行管理
行为驱动开发(BDD)是一种从TDD(测试驱动开发)发展而来的软件开发方法。它的不同之处在于用共享语言编写,这改善了技术与非技术团队和利益相关者之间的沟通。在这两种开发方法中,测试都是在代码之前编写的,但在BDD中,测试更加以用户为中心,并且基于系统的行为。设计要求为:
'Given-When-Then'公式
这是为用户故事编写BDD测试用例的建议模板,可以定义为:
给定某种情况
当一个动作发生时
那么这应该是结果。
一个实际的例子是:
-由于用户没有输入窗体上的任何数据。
当他们点击提交按钮
然后显示验证成功的消息
用户在对web UI进行测试时,一般会包含多个Page(功能页面),每个Page都有自己的UI元素和行为操作,各个Page之间相互不干扰,需要分离。
在新增用例的时候,每个用例设计时都需要考虑配置信息、页面元素信息、行为操作、具体流程设计。不同用例之间的配置信息、页面元素信息、行为操作会有重叠部分,只是流程上会有差异,因此,需要将业务操作和测试用例分离,进行分层设计。
因此,测试系统设计可采用Page Object Model设计模式,以用户登陆为例,可以分成以下几个层次:
Page层:完成单个页面页面元素、页面行为的配置,包括CommonPage基本页面层、PageElement页面对象层、ActionOperator行为操作层。
Workflow TCs:完成单个页面的行为流程和校验的test cases,该test case不能直接执行,只能被真正Main TCs引用。
Main TCs:真正执行的测试用例
Test Suite:测试用例集合
Data-bingding:测试系统所需的配置数据
功能: 完成系统配置,如:web服务地址、用户名、密码、git/p4地址等信息
实现:
完成单个页面页面元素、页面行为的配置
功能: 完成Page交互时的通用功能,如:点击、切换到frame、拖动滚动条、元素获取等. 该层是Page最底层,可供ActionOperator行为操作层调用。
实现:定义CommonPage,调用katalon WebUI对应的接口,实现上述功能。
功能:保存不同page的元素path。当页面元素变更了,直接修改单个元素,不存在测试用例维护问题。
实现:新建Object Repository, 按照page划分目录,对每个page的元素Xpath/Css/Arribute进行配置
功能:对每个Page用户独立的行为操作进行封装,如:登陆、新增workspace等。将业务操作与测试用例分离,因为多个用例可能是对应一个业务操作的,这样,我业务代码ji'hu,只需要修改用例就好了。
实现:继承于 CommonPage,实现各个页面独有的所有行为(不包括校验)。每个页面的元素,引用于 PageElement页面对象层
命名:
Bad:
Input Valid Username And Valid Password And Click Login Button
功能:对每个page可能的页面流程进行设计并校验。
实现: 引用ActionOperator行为操作层,将页面流程封装称测试用例
功能:完成具体测试用例
实现 : 调用WorkFlow工作流程层,进行流程组装
命名:
例子:
Login With Empty Password Should FailLogin With Empty Username Should FailLogin With Empty Username And Password Should FailLogin With Invalid Username Should FailLogin With Invalid Password Should FailLogin With Invalid Username And Invalid Password Should Fail
功能:每个testSuit中包含多个测试用例,可对testcase进行分组,指定待执行的测试用例。
实现:配置test suit
命名:
功能: 保存测试用例中运行过程中的日志、截图。
实现:
功能: 保存执行结果。
实现:katalon默认会生成每个test suit执行结果
功能:为每个测试用例/用例集提供用例执行的前置配置和后置配置
实现:
每个testcase内部支持自定义method。
testsuits中的script模式下可进行基于每个testcase和每个testsuit下的通用配置。
Test Listeners支持全局范围内的配置。
执行顺序如下:
page object model
作者:小飞侠fayer
链接:https://www.jianshu.com/p/82fdd2db9c44
来源:简书
简书著作权归作者所有,任何形式的转载都请联系作者获得授权并注明出处。