The heart of end-to-end tests for webpages is finding DOM elements, interacting with them, and getting information about the current state of your application. This doc is an overview of how to locate and perform actions on DOM elements using Protractor.
E2E测试的核心就是找到DOM元素,和它们交互,并且得到应用目前的状态。
本文介绍了怎么用protractor找到页面元素并和它们交互。
Protractor exports a global function element, which takes a Locator and will return an ElementFinder. This function finds a single element - if you need to manipulate multiple elements, use the element.all function.
element
是protrator的 全局函数,接受一个locator,返回一个ElementFinder对象。
注意:这个函数返回一个元素,如果需要控制多个元素,要用element.all
函数。
实际上如果如果定位器找到多个符合条件的元素,会自动返回第一个元素。
The ElementFinder has a set of action methods, such as click(), getText(), and sendKeys. These are the core way to interact with an element and get information back from it.
When you find elements in Protractor all actions are asynchronous. Behind the scenes, all actions are sent to the browser being controlled using the JSON Webdriver Wire Protocol. The browser then performs the action as a user natively would.
ElementFinder 有一组方法,如 click()
, getText()
, and sendKeys
.
方法都是异步的。
A locator tells Protractor how to find a certain DOM element. Protractor exports locator factories on the global by
object. The most common locators are:
定位器告诉Protractor 怎么找到某个DOM元素。protractor 导出定位器定位到的元素给全局的by
对象。最常见的定位器如下:
// find an element using a css selector
by.css('.myclass')
// find an element with the given id
by.id('myid')
// find an element with a certain ng-model
by.model('name')
// find an element bound to the given variable
by.binding('bindingname')
For a list of Protractor-specific locators, see the Protractor API: ProtractorBy.
更多定位器见Protractor API: ProtractorBy.
The locators are passed to the element
function, as below:
定位器再传给element函数:
element(by.css('some-css'));
element(by.model('item.name'));
element(by.binding('item.name'));
When using CSS Selectors as a locator, you can use the shortcut ()notation:当定位器是css选择器时,可以用快捷符号 ()
$('my-css');
// Is the same as
element(by.css('my-css'));
The element() function returns an ElementFinder object. The ElementFinder knows how to locate the DOM element using the locator you passed in as a parameter, but it has not actually done so yet. It will not contact the browser until an action method has been called.
The most common action methods are:
element()
函数返回ElementFinder对象。但是它只有在方法被调用的时候才会联系浏览器定位DOM元素。
我之前就想找到元素了以后页面更新了怎么办,看来这并不是一个问题。
var el = element(locator);
// Click on the element
el.click();
// Send keys to the element (usually an input)
el.sendKeys('my text');
// Clear the text in an element (usually an input)
el.clear();
// Get the value of an attribute, for example, get the value of an input
el.getAttribute('value');
Since all actions are asynchronous, all action methods return a promise. So, to log the text of an element, you would do something like:
因为所有动作都是异步的,所有的动作方法都会返回一个promise(简单来说promise代表一个尚未产生的值,当这个值产生后可以用promise调用回调函数)
var el = element(locator);
el.getText().then(function(text) {
console.log(text);
});
Any action available in WebDriverJS on a WebElement is available on an ElementFinder.
更多动作见链接 See a full list
To deal with multiple DOM elements, use the element.all function. This also takes a locator as its only parameter.
主要使用element.all
函数
element.all(by.css('.selector')).then(function(elements) {
// elements is an array of ElementFinders.
});
几个重要方法:
// Number of elements.
element.all(locator).count();
// Get by index (starting at 0).
element.all(locator).get(index);
// First and last.
element.all(locator).first();
element.all(locator).last();
To find sub-elements, simply chain element and element.all functions together as shown below.
Using a single locator to find:
- an element
element(by.css('some-css'));
Using chained locators to find:
- a sub-element:
element(by.css('some-css')).element(by.tagName('tag-within-css'));
element(by.css('some-css')).all(by.tagName('tag-within-css'));
You can chain with get/first/last as well like so:
element.all(by.css('some-css')).first().element(by.tagName('tag-within-css'));
element.all(by.css('some-css')).get(index).element(by.tagName('tag-within-css'));
element.all(by.css('some-css')).first().all(by.tagName('tag-within-css'));
Written with StackEdit.