打开APP
userphoto
未登录

开通VIP,畅享免费电子书等14项超值服

开通VIP
Selenium WebDriver 之 PageObjects 模式 by Example
目录  1. 项目配置  2. 一个WebDriver简单例子  3. 使用Page Objects模式  4. 总结  5. Troubleshooting  6. 参考文档

本篇文章通过例子来阐述一下Selenium2.0 WebDriver 之 Page Objects模式。

 

项目配置

maven 3, pom.xml配置如下

<dependency>    <groupId>org.seleniumhq.selenium</groupId>    <artifactId>selenium-java</artifactId>    <version>2.46.0</version></dependency>

另外我是用TestNG 写Selenium tests, 加如下dependency

<dependency>    <groupId>org.testng</groupId>    <artifactId>testng</artifactId>    <version>6.8</version></dependency>

 

一个WebDriver简单例子

主要做如下几个动作:

1. 打开博客园首页

2. 断言页面标题出现

3. 在找找看输入框输入字符

4. 点击找找看按钮

5. 断言进入的页面标题

 1 package test.demo; 2  3 import static org.testng.Assert.assertEquals; 4  5 import org.openqa.selenium.By; 6 import org.openqa.selenium.WebDriver; 7 import org.openqa.selenium.WebElement; 8 import org.openqa.selenium.firefox.FirefoxDriver; 9 import org.openqa.selenium.firefox.FirefoxProfile;10 import org.testng.annotations.AfterTest;11 import org.testng.annotations.BeforeTest;12 import org.testng.annotations.Test;13 14 ;15 16 /**17  * @Description: A simple Test using WebDriver18  * @author wadexu19  * 20  * @updateUser21  * @updateDate22  */23 public class WebPageTest {24 25     private WebDriver driver;26 27     @BeforeTest28     public void setUp() {29         FirefoxProfile firefoxProfile = new FirefoxProfile();30         // use proxy31         firefoxProfile.setPreference("network.proxy.type", 1);32         firefoxProfile.setPreference("network.proxy.http", "10.51.1.140");33         firefoxProfile.setPreference("network.proxy.http_port", "8080");34 35         driver = new FirefoxDriver(firefoxProfile);36     }37 38     @AfterTest39     public void tearDown() {40         driver.close();41     }42 43     @Test44     public void test() {45         driver.get("http://www.cnblogs.com/");46         assertEquals("博客园 - 开发者的网上家园", driver.getTitle());47 48         WebElement searchBox = driver.findElement(By.id("zzk_q"));49         searchBox.sendKeys("wadexu");50 51         WebElement searchBtn = driver.findElement(By.xpath("//*[@id='search_block']/div[1]/input[2]"));52         searchBtn.click();53 54         assertEquals("wadexu-博客园找找看", driver.getTitle());55     }56 57 }

这种写法缺点很多, 可读性差,页面元素,操作HTML,测试逻辑全部在一起。

##转载注明出处:http://www.cnblogs.com/wade-xu/p/4744937.html 

 

使用Page Objects模式

PageObjects是对具体页面的抽象,使用时通过PageFactory来构造。

首先我们为博客园首页和找找看搜索页面定义两个page objects

-- CnBlogsHomePage

 1 package test.demo; 2  3 import org.openqa.selenium.WebElement; 4 import org.openqa.selenium.support.FindBy; 5  6 /** 7  * @Description: 博客园首页 8  * @author wadexu 9  *10  * @updateUser11  * @updateDate12  */13 public class CnBlogsHomePage {14 15     @FindBy(id = "zzk_q") //找找看输入框16     protected WebElement searchBox;17     18     @FindBy(xpath = "//*[@id='search_block']/div[1]/input[2]") //找找看按钮19     protected WebElement searchBtn;20     21     public void searchFor(String content) {22         searchBox.sendKeys(content);23         searchBtn.click();24     }25 }

 

-- SearchResultPage

package test.demo;import java.util.List;import org.openqa.selenium.By;import org.openqa.selenium.WebElement;import org.openqa.selenium.support.FindBy;/** * @Description: 博客园找找看頁面 * @author wadexu * * @updateUser * @updateDate */public class SearchResultPage {    @FindBy(id = "searchResult")     protected WebElement searchResult;        //for tutorial purpose only    public boolean searchResultListNotNull() {        WebElement searchResultItems = searchResult.findElement(By.cssSelector(".forflow"));        List<WebElement> resultItemTitleList = searchResultItems.findElements(By.tagName("a"));                for (WebElement e : resultItemTitleList) {            System.out.println(e.getText());        }                return resultItemTitleList.size() > 0;    }}

##转载注明出处:http://www.cnblogs.com/wade-xu/p/4744937.html 

 

下面是使用Page Objects 的测试

 1 package test.demo; 2  3 import static org.testng.Assert.assertTrue; 4  5 import org.openqa.selenium.WebDriver; 6 import org.openqa.selenium.firefox.FirefoxDriver; 7 import org.openqa.selenium.firefox.FirefoxProfile; 8 import org.openqa.selenium.support.PageFactory; 9 import org.testng.annotations.AfterTest;10 import org.testng.annotations.BeforeTest;11 import org.testng.annotations.Test;12 13 /**14  * @Description: UsingPageObjectsTest15  * @author wadexu16  * 17  * @updateUser18  * @updateDate19  */20 public class UsingPageObjectsTest {21 22     private WebDriver driver;23 24     @BeforeTest25     public void setUp() {26         FirefoxProfile firefoxProfile = new FirefoxProfile();27         // use proxy28         firefoxProfile.setPreference("network.proxy.type", 1);29         firefoxProfile.setPreference("network.proxy.http", "10.51.1.140");30         firefoxProfile.setPreference("network.proxy.http_port", "8080");31 32         driver = new FirefoxDriver(firefoxProfile);33     }34 35     @AfterTest36     public void tearDown() {37         driver.close();38     }39 40     @Test41     public void test() {42         driver.get("http://www.cnblogs.com/");43         CnBlogsHomePage homePage = PageFactory.initElements(driver, CnBlogsHomePage.class);44         homePage.searchFor("wadexu");45 46         SearchResultPage resultPage = PageFactory.initElements(driver, SearchResultPage.class);47         assertTrue(resultPage.searchResultListNotNull());48     }49 50 }

WebDriver为了支持PageObject模式,支持库包含一个叫PageFactory的工厂类, 我们通过PageFactory的initElements方法来实例化PageObject的实例.

这种方式看上去简洁明了,可读性高,封装了界面交互细节,可以使测试更关注业务逻辑而非页面细节,就像在写功能测试用例。

 

Run as TestNG 测试结果如下

就是这么简单!使用Rest-assured 测试Restful Web ServicesWadeXu这些年我们一起搞过的持续集成~Jenkins+Perl and Shell scriptWadeXuPostman (Chrome插件)HackerVirusVC/MFC如何设置对话框背景颜色youxin玩转单元测试之DBUnitWadeXu性能分析神器VisualVMWadeXu性能分析神器VisualVMqingchen1984玩转单元测试之WireMock -- Web服务模拟器WadeXu写在离职前夕平静缓和用胸音说爱带你入门带你飞Ⅰ 使用Mocha + Chai + Sinon单元测试Node.jsWadeXuPASSED: test===============================================    Default test    Tests run: 1, Failures: 0, Skips: 0===============================================[TestNG] Time taken by org.testng.reporters.JUnitReportReporter@288051: 4 ms[TestNG] Time taken by org.testng.reporters.SuiteHTMLReporter@4d865b28: 28 ms[TestNG] Time taken by org.testng.reporters.XMLReporter@45d64c37: 6 ms[TestNG] Time taken by [TestListenerAdapter] Passed:0 Failed:0 Skipped:0]: 0 ms[TestNG] Time taken by org.testng.reporters.EmailableReporter@68e6ff0d: 3 ms

##转载注明出处:http://www.cnblogs.com/wade-xu/p/4744937.html 

运行的很慢, 主要是因为博客园的页面加载的许多Script 都是在线引入,很多这种source <script async="" type="text/javascript" src="//www.googletagservices.com/tag/js/gpt.js"></script>

而我又不能禁用script,否则点不了找找看button。

测试截图

 

总结

本文我们学到的知识点有:

  • 使用Selenium WebDriver查找元素,通过By id, xpath, cssSelector, tagName 例子里尽可能的运用了这些方式。
  • 通过FirefoxProfile 设置代理, 也可以设置页面不加载一些对象如image, script, stylesheet 设置方式:firefoxProfile.setPreference("permissions.default.image", 2); //2表示关闭
  • Page Objects模式, 优点很多,分离页面元素及操作元素的步骤,便于维护, 降低代码冗余度,提升复用率。

 

(此图来源于网络)

##转载注明出处:http://www.cnblogs.com/wade-xu/p/4744937.html 

 

Troubleshooting

1. org.openqa.selenium.firefox.NotConnectedException: Unable to connect to host 127.0.0.1 on port 7055 after 45000 ms

firefox浏览器版本太高,selenium不兼容,要么降低firefox的版本,要么用新的selenium webDriver

 

2. Selenium WebDriver正常打开浏览器,但是无法访问页面

跟环境有关,使用FirefoxProfile setPreference 设置个代理, 有几种方式供参考

WebDriver每次启动一个Firefox的实例时,会生成一个匿名的profile,并不会使用当前Firefox的profile。这点一定要注意。比如如果访问被测试的web服务需要通过代理,你想直接设置Firefox的代理是行不通的,因为WebDriver启动的Firefox实例并不会使用你这个profile,正确的做法是通过FirefoxProfile来设置。

 

3. org.openqa.selenium.NoSuchElementException: Unable to locate element

代码问题,不能定位元素

 

参考文档

SeleniumHQ Website

Selenium API JavaDocs

 

感谢阅读,如果您觉得本文的内容对您的学习有所帮助,您可以点击右下方的推荐按钮,您的鼓励是我创作的动力。

##转载注明出处:http://www.cnblogs.com/wade-xu/p/4744937.html 

 

本站仅提供存储服务,所有内容均由用户发布,如发现有害或侵权内容,请点击举报
打开APP,阅读全文并永久保存 查看更多类似文章
猜你喜欢
类似文章
【热】打开小程序,算一算2024你的财运
Selenium2(webdirver)入门之环境搭建(Java版)
“Cannot find firefox binary in PATH. ”错误。
和我一起学 Selenium WebDriver(7)
Selenium Grid深入学习
Html5 Geolocation Test
selenium webdriver 环境搭建–java
更多类似文章 >>
生活服务
热点新闻
分享 收藏 导长图 关注 下载文章
绑定账号成功
后续可登录账号畅享VIP特权!
如果VIP功能使用有故障,
可点击这里联系客服!

联系客服