Selenium应该是目前前端测试最主流的测试工具吧,支持主流浏览器如Firefox、Chrome、IE等,无论你熟悉Python还是Java,都可以方便的使用Selenium提供的丰富的测试套件,还有其它很多基于Selenium二次封装开发的测试框架如Robot Framework可供选择。
这次是第一次使用Java操作WebDriver,以TestNG作为测试框架,实现简单的Web前端测试。
IDE: Eclipse Oxygen.3a Release (4.7.3a)
Step1:打开Eclipse,在Help - Install New Software…中搜索并安装TestNG插件
安装重启之后可在Window - Show View - Other里,Java下查看到TestNG
Step2:使用Eclipse自带的Maven插件(或者在Window - Preferences - Maven - Installations添加系统安装的其它版本Maven),新建一个Maven项目
输入groupId和artifactId
Step3:在testExample/pom.xml中添加TestNG、Selenium作为dependencies,若只想使用特定的WebDriver实现,如Firefox,可直接添加selenium-firefox-driver作为dependency。
<project xmlns="http://maven.apache/POM/4.0.0" xmlns:xsi="http://www.w3/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache/POM/4.0.0 http://maven.apache/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>testExamples</groupId>
<artifactId>testExamples</artifactId>
<version>0.0.1-SNAPSHOT</version>
<dependencies>
<dependency>
<groupId>org.seleniumhq.selenium</groupId>
<artifactId>selenium-firefox-driver</artifactId>
<version>3.13.0</version>
</dependency>
<dependency>
<groupId>org.testng</groupId>
<artifactId>testng</artifactId>
<version>6.14.3</version>
</dependency>
</dependencies>
</project>
Alt+F5选择项目进行更新,可以在Maven Dependencies里检查依赖包是否存在
右键点击JRE System Library, 改成系统默认
Step4:下载浏览器对应的driver放到特定目录下(如C:\webdriver),可查看官网下载地址 。如使用Firefox,需要到这里下载最新的geckdriver.exe。
Step5:右键点击项目,创建一个新的TestNG class并指定package。
可选:
- Annotations,后面可在定义测试类的时候添加
- XML suite file,在这里添加可直接在package里生成suite文件;也可以缺省,创建好测试类之后右键选择项目TestNG - Convert to TestNG,会在项目下生成suite文件包含项目里不同package的所有测试类。本文暂时不涉及Test Suite的使用。
Step6:实现测试类
用例1:
AUT - http://live.guru99/index.php/
测试类如下
package selenium;
import org.testng.annotations.Test;
import static org.testng.Assert.assertTrue;
import java.util.List;
import org.openqa.selenium.support.ui.Select;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.firefox.FirefoxDriver;
import org.testng.annotations.AfterClass;
import org.testng.annotations.BeforeClass;
public class testPractice1 {
private String aut_url = "http://live.guru99/index.php/";
private WebDriver driver;
@Test
public void checkMainTitle() {
driver.get(aut_url);
String title1 = getTitle();
assertTrue(title1.contains("THIS IS DEMO SITE"));
}
@Test
public void checkMobileTitle() {
driver.findElement(By.linkText("MOBILE")).click();
String title2 = getTitle();
assertTrue(title2.equals("MOBILE"));
}
@Test
public void checkSortByName() {
List<WebElement> list1 = getProductList();
list1.sort((e1, e2) -> e1.getAttribute("title")pareTo(e2.getAttribute("title")));
Select sort_type = new Select(driver.findElement(By.xpath("//select")));
sort_type.selectByVisibleText("Name");
List<WebElement> list2 = getProductList();
for (WebElement a:list2) {
int index = list2.indexOf(a);
assertTrue(a.getAttribute("title").equals(list1.get(index).getAttribute("title")));
}
}
@BeforeClass
public void setUp() {
System.setProperty("webdriver.gecko.driver", "C:\\webdriver\\geckodriver.exe");
driver = new FirefoxDriver();
}
@AfterClass
public void afterTest() {
driver.quit();
}
public List<WebElement> getProductList() {
List<WebElement> list = driver.findElements(By.xpath("//h2[@class='item last']/a"));
return list;
}
public String getTitle() {
WebElement title = driver.findElement(By.className("page-title"));
String t = null;
if (title.isDisplayed()) {
t = title.getText();
System.out.println("Current title is:"+t);
}
return t;
}
}
用例2:
AUT - https://tokenpad.io (借用朋友公司开发的产品页面)
1. 注册新用户
- 测试注册成功,页面提示下一步
- 测试注册失败,页面提示警告信息
2. 登陆
- 测试登陆成功,页面跳转到登陆之后的Dashboard
- 测试 登陆失败,页面提示警告信息
在多用例的测试类中调试单个用例的时候可以用类似@Test(enabled=false),@AfterTest(enabled=false)来阻止其它用例或步骤运行。
package testPractice;
import static org.testng.Assert.assertTrue;
import static org.testng.Assert.fail;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.firefox.FirefoxDriver;
import org.openqa.selenium.support.ui.WebDriverWait;
import org.openqa.selenium.support.ui.ExpectedConditions;
import org.testng.annotations.AfterTest;
import org.testng.annotations.BeforeTest;
import org.testng.annotations.Test;
import java.util.List;
public class Practice2 {
private String base_url = "https://tokenpad.io";
private String login_url = base_url+"/auth/login";
private String signup_url = base_url+"/auth/sign-up";
private String dashboard_url = "https://tokenpad.io/invest/dashboard/onboard";
private WebDriver driver;
private String userId1 = "gracesheep@126";
private String passwd1 = "1234qwer";
private String userbase = "test";
private String passwd = "12345678";
private int delay = 3;
WebDriverWait waitVar = null;
@Test
public void checkLoginSuccessfully() throws InterruptedException {
String expected_text = "Welcome to Tokenpad";
login(userId1, passwd1);
Thread.sleep(5000);
if (driver.findElement(By.tagName("app-init")).isEnabled()) {
assertTrue(driver.getCurrentUrl().contains(dashboard_url));
assertTrue(driver.findElement(By.xpath("//div[@class='title']")).getText().contains(expected_text));
}
else {
fail();
}
}
@Test
public void checkLoginFailed() {
String expected_alert = "The email or password you have entered is invalid.";
login(userId1, passwd);
waitVar.until(ExpectedConditions.visibilityOfElementLocated(By.tagName("alert")));
assertTrue(driver.findElement(By.xpath("//div[@role='alert']")).getText().contains(expected_alert));
}
@Test
public void checkSignUpFailed() {
String country = "China";
String expected_alert = "Your email is already been used.";
signUp(userId1, passwd1, country);
waitVar.until(ExpectedConditions.visibilityOfElementLocated(By.tagName("alert")));
assertTrue(driver.findElement(By.xpath("//div[@role='alert']")).getText().contains(expected_alert));
}
@Test
public void checkSignUpSucceed() {
String country = "Sweden";
String userId = userbase+String.valueOf(System.currentTimeMillis())+"@test";
signUp(userId, passwd, country);
waitVar.until(ExpectedConditions.visibilityOfAllElementsLocatedBy(By.className("send-validation")));
assertTrue(driver.findElement(By.xpath("//h2[text()='Confirm Your Email']")).isDisplayed());
}
public void signUp(String user, String password, String country) {
driver.get(signup_url);
waitVar.until(ExpectedConditions.visibilityOfElementLocated(By.className("login-form")));
driver.findElement(By.name("email")).sendKeys(user);
driver.findElement(By.name("password")).sendKeys(password);
driver.findElement(By.className("ng-arrow")).click();
setCountry(country);
driver.findElement(By.xpath("//button[text()='Create Account']")).click();
}
public void setCountry(String country) {
if (driver.findElement(By.tagName("ng-dropdown-panel")).isEnabled()) {
List<WebElement> countries = driver.findElements(By.xpath("//div[@role='option']//span[@class='ng-option-label ng-star-inserted']"));
for (WebElement item:countries) {
if (item.getText().equals(country)) {
int index = countries.indexOf(item)+1;
String path = "//div[@class='ng-dropdown-panel-items scroll-host']//div["+index+"]";
driver.findElement(By.xpath(path)).click();
break;
}
}
}
}
public void login(String user, String password) {
driver.get(login_url);
if (driver.findElement(By.tagName("app-login")).isEnabled()) {
driver.findElement(By.name("email")).sendKeys(user);
driver.findElement(By.name("password")).sendKeys(password);
driver.findElement(By.xpath("//button[text()='Login']")).click();
}
}
@BeforeTest
public void setUp() {
System.setProperty("webdriver.gecko.driver", "C:\\webdriver\\geckodriver.exe");
driver = new FirefoxDriver();
System.out.println("Initialize browser");
//可以采用隐式设置通用的等待时间
//driver.manage().timeouts().implicitlyWait(delay, TimeUnit.SECONDS);
//也可以采用显式根据条件判断结果设置等待时间
waitVar = new WebDriverWait(driver, delay);
}
@AfterTest
public void afterTest() {
driver.quit();
}
}
总结两点使用心得:
1. 使用Selenium最重要的一点是在不同的web框架之中准确定位元素,在使用xpath的时候,可以借助浏览器插件如Chrome我使用的是ChroPath来方便的获取到。
2. 在assert之前给页面充分的加载时间,比如添加等待时间并通过判断元素是否显示、存在的方式确定页面加载完全了。
更多推荐
TestNG+Selenium实现简单的Web前端测试
发布评论