簡介web
原創文章,轉載請註明出處chrome
這個框架的名字叫OAT,全稱Object-Oriented Automation Test.這個框架的思想借助於Tellurium框架.他的主要功能是將頁面信息及行爲存儲在Java 對象中,而後在腳本中引用頁面的行爲.自動化程序最終由許多的頁面行爲組成.這個框架默認使用Selenium1驅動,而且能夠經過編程使用其餘驅動,因 爲OAT是面向接口的.編程
如下以google home page的demo爲例,介紹這個基於Annoation和反射的框架基本運行原理.框架
page對象ide
- //存儲頁面URL
- @OatPage("webhp")
- public class GooglePage extends Page{
- @Element("q") // 搜索輸入框的定位符
- private TextField textField;
- @Element("btnG") // 搜索按鈕的定位符
- private Button searchButton;
- // TextField和Button有共同的祖先類Element
- public TextField getTextField() {
- return textField;
- }
- public Button getSearchButton() {
- return searchButton;
- }
- //進行一次搜索
- public void doSearch(String q){
- this.textField.type(q);
- this.searchButton.click();
- }
- }
TextField和button類測試
- // Element子類,有本身獨特的行爲
- public class TextField extends Element {
- public void type(String value) {
- vendor.type(locator, value);
- }
- public boolean idEditable(){
- return vendor.isEditable(locator);
- }
- public String getValue() {
- return vendor.getAttribute(locator);
- }
- }
- // 一樣是Element的子類,有本身行爲
- public class Button extends Element {
- public void click() {
- vendor.click(locator);
- }
- public void clickAndWaitToLoad(Page page){
- click();
- page.waitToLoad();
- }
- public void clickAndWaitToLoad(Page page, long timeout) {
- click();
- page.waitToLoad(timeout);
- }
- public void clickAndWaitToLoad(Element element, long timeout) {
- click();
- element.waitToLoad(timeout);
- }
- public void clickAndWaitToLoad(Element element) {
- clickAndWaitToLoad(element, ELEMENT_DEFAULT_TIMEOUT);
- }
- }
自動化測試腳本代碼this
- import junit.framework.Assert;
- import org.junit.After;
- import org.junit.Before;
- import org.junit.Test;
- import com.thoughtworks.selenium.DefaultSelenium;
- import com.thoughtworks.selenium.Selenium;
- public class GoogleSearchTestExample1 {
- private String serverUrl = "localhost";
- private int serverPort = 4444;
- private String browserCommand = "googlechrome";
- private String url = "http://www.google.com.hk";
- private GooglePage page;
- private GoogleResultPage resultPage;
- private Selenium selenium;
- private Oat oat;
- @Before
- public void setUp() throws Exception {
- // 初始化selenium
- selenium = new DefaultSelenium(serverUrl,serverPort,browserCommand, url);
- // Oat類是框架總的控制器,設置Selenium爲背後的驅動
- oat = Oat.getInstance(selenium);
- oat.start();
- oat.open("/webhp");
- // 初始化被測試頁面
- page = (GooglePage) oat.getPage(GooglePage.class);
- resultPage = (GoogleResultPage) oat.getPage(GoogleResultPage.class);
- }
- @Test
- public void testSearch() throws InterruptedException {
- // 在google頁面收入"oat"進行搜索
- page.doSearch("oat");
- page.waitToLoad(2000);
- // 在結構頁面進行驗證
- boolean result = resultPage.isTextPresent("oat");
- Assert.assertTrue("Text oat is present", result);
- }
- @After
- public void tearDown() throws Exception {
- oat.stop();
- oat = null;
- page = null;
- selenium = null;
- }
- }
Oat.getInstance(Object engine):用於獲取真正的Driver:google
- //能夠根據傳入的不一樣engine,實例化不一樣的Vendor
- public static Oat getInstance(Object engine) {
- if(instance == null) {
- synchronized(Oat.class) {
- if(instance == null) {
- String vendorTypeStr = getVendorTypeStr();
- try {
- Class<?> vendorType = Class.forName(vendorTypeStr);
- Vendor vendor = getVendor(vendorType, engine);
- instance = new Oat();
- instance.vendor = vendor;
- } catch (ClassNotFoundException e) {
- throw new RuntimeException("Not Found vendor " + vendorTypeStr, e);
- }
- }
- }
- }
- return instance;
- }
Oat.getPage()方法詳解url
- public Page getPage(Class<? extends Page> pageType) {
- Page page = null;
- page = initialize(pageType);
- page.setVendor(vendor);
- }
- private Page initialize(Class<? extends Page> pageType) {
- //讀取page類中的annotation
- OatPage anno = pageType.getAnnotation(OatPage.class);
- if(anno == null) {
- throw new RuntimeException("Please add com.perficient.oat.component.annotaion.OatPage annotation in Page class!");
- }
- Page page = null;
- try {
- page = pageType.newInstance();
- } catch (Exception e) {
- throw new RuntimeException("Page Class must have a non-parameter constructor.", e);
- }
- Class<?> tempType = pageType;
- while(tempType != null) {
- Field[] fields = tempType.getDeclaredFields();
- for(Field field : fields ) {
- com.perficient.oat.component.annotaion.Element annotation =
- field.getAnnotation(com.perficient.oat.component.annotaion.Element.class);
- if(annotation == null) {
- continue;
- }
- Class<?> fieldClazz = field.getType();
- // 只處理Element的子類
- Class<? extends Element> elementClazz = fieldClazz.asSubclass(Element.class);
- String locator = annotation.value();
- field.setAccessible(true);
- //使用反射初始化Page類的各個Element子類,並賦予Locator值
- try {
- field.set(page, getElement(elementClazz, locator));
- } catch (Exception e) {
- throw new RuntimeException("set Element " + field.getName() + " error", e);
- }
- }
- tempType = tempType.getSuperclass();
- }
- return page;
- }
- //用於初始化Page類中的各個Element子類
- private Element getElement(Class<? extends Element> elementType, String locator) {
- Element element = null;
- try {
- element = elementType.newInstance();
- element.setLocator(locator);
- element.setVendor(vendor);
- } catch (Exception e) {
- throw new RuntimeException(e);
- }
- return element;
- }
以上就是一個完整的基於Selenium driver的框架實現.如下是咱們的Vendor接口:spa
- public interface Vendor {
- public void start();
- public void stop();
- public void open(String url);
- public void openWindow(String url, String windowId);
- public void type(String locator, String value);
- public void check(String locator);
- public void uncheck(String locator);
- public boolean isChecked(String locator);
- public boolean isEditable(String locator);
- public void select(String selectLocator, String optionLocator);
- public String getSelectedLabel(String locator);
- public String[] getSelectedLabels(String locator);
- public boolean isSelected(String label);
- public void submit(String formLocator);
- public void click(String locator);
- public boolean isTextPresent(String pattern);
- public boolean isElementPresent(String locator);
- public void waitForPageToLoad(String timeout);
- public void windowFocus(String windowId);
- public String getAttribute(String attributeLocator);
- public String getTableCellValue(String locator, int row, int col);
- public void waitForElementToLoad(String locator, String timeout);
- public String getLocation();
- }
如下是seleniumVendor的實現:
- public class SeleniumVendor extends VendorTemplate<Selenium> {
- @Override
- protected Selenium createEngine(VendorAttribute attribute) {
- return new DefaultSelenium(
- attribute.getHost(),
- attribute.getPort(),
- attribute.getBrowser(),
- attribute.getUrl());
- }
- @Override
- public boolean isTextPresent(String pattern) {
- return engine.isTextPresent(pattern);
- }
- @Override
- public void open(String url) {
- engine.open(url);
- }
- @Override
- public void select(String selectLocator, String optionLocator) {
- engine.select(selectLocator, optionLocator);
- }
- @Override
- public void start() {
- engine.start();
- }
- @Override
- public void stop() {
- engine.stop();
- }
- @Override
- public void submit(String formLocator) {
- engine.submit(formLocator);
- }
- @Override
- public void type(String locator, String value) {
- engine.type(locator, value);
- }
- @Override
- public void click(String locator) {
- engine.click(locator);
- }
- @Override
- public void waitForPageToLoad(String timeout) {
- engine.waitForPageToLoad(timeout);
- }
- @Override
- public void windowFocus(String windowId) {
- engine.selectWindow(windowId);
- engine.windowFocus();
- }
- @Override
- public void openWindow(String url, String windowId) {
- engine.openWindow(url, windowId);
- }
- @Override
- public void check(String locator) {
- engine.check(locator);
- }
- @Override
- public String getAttribute(String attributeLocator) {
- return engine.getAttribute(attributeLocator);
- }
- @Override
- public boolean isElementPresent(String locator) {
- return engine.isElementPresent(locator);
- }
- @Override
- public void uncheck(String locator) {
- engine.uncheck(locator);
- }
- @Override
- public boolean isChecked(String locator) {
- return engine.isChecked(locator);
- }
- @Override
- public String getSelectedLabel(String locator) {
- return engine.getSelectedLabel(locator);
- }
- @Override
- public String[] getSelectedLabels(String locator) {
- return engine.getSelectedLabels(locator);
- }
- @Override
- public boolean isSelected(String label) {
- return engine.isSomethingSelected(label);
- }
- @Override
- public boolean isEditable(String locator) {
- return engine.isEditable(locator);
- }
- @Override
- public String getTableCellValue(String locator, int row, int col) {
- return engine.getTable(locator + "." + String.valueOf(row)+ "." +String.valueOf(col));
- }
- @Override
- public void waitForElementToLoad(String locator, String timeout) {
- String script = "selenium.isElementPresent(\"" + locator + "\")";
- engine.waitForCondition(script, timeout);
- }
- @Override
- public String getLocation() {
- return engine.getLocation();
- }
- }
若是咱們須要改爲其餘Dirver,新創建一個Vendor的實現類便可