Using Locators in Protractor

To write end to end tests in Protractor, we use locators to find elements on web page. Locators in protractor are similar to selenium webdriver. As we all know Protractor works on top of Selenium WebDriver, so it supports all the Selenium locators along with protractor locators. We will see multiple ways of finding elements in Protractor with Angular specific element locating strategies by.model(), by.binding(), by.repeater() etc in detail below.

Let's first try to understand global variables that are most commonly used finding DOM elements in protracor.

By – By is a collection of element locator strategies. Like by.css('.myclass') and by.model('name') etc.

element - Element searches for an element on the web page. It takes a locator and returns an ElementFinder.

var ele = element(locator);
// Click on the element.
ele.click();

element.all - We use the element.all to work with multiple DOM elements. This also takes a locator as its only parameter.

Locators in Selenium : -

If you are familiar with selenium, Selenium has 8 locators to find the elements on web page. Please refer article for selenium locators in details.

Let us see example with selenium locator using Id.

Example : -

<input id="user" class="required" type="text">
WebElement ele = driver.findElement(By.id("user"));
ele.click()

The same can be used in Protractor as below : -

var ele = element(by.id('user'));
// Click on the element.
ele.click();

If you want to use selenium syntax in protractor, we can use it like below : -

var ele = browser.findElement(by.id('user'));
// Click on the element.
ele.click();

But there is a difference in using selenium syntax in protractor. Here when we use browser.findElement, it will try to find the element immediately, where as when we use element will find element only when we perform action on it.

Example :

var saveButton = element(locator); 

- No command has been sent to the browser yet. The browser will not receive any commands until you call an action on this element.

saveButton.click()

- Now two commands are sent to the browser - find the element, and then click it.

Below are the Angular specific locators in protractor :-

1. model : ng-model attribute is an angular locator. It locates the element by model attribute value given.
Example:

<input type="text" ng-model="person.name">

Syntax :

element(by.model('person.name')).click();

2. binding : ng-bind is also an angular locator. Binding locator is used to locate the element using bind attribute value given.

Find an element by text binding. Does a partial match, so any elements bound to variables containing the input string will be returned.
Example:

<p ng-bind="person.name"></p>

Code 1:

var eleName = element(by.binding('person.name'));
expect(eleName.getText()).toBe('Robert');

Code 2 : As said, we can also use a sub string for a partial match using by.binding

var eleName = element(by.binding('name'));
expect(eleName.getText()).toBe('Robert');

3. exactBinding : It is also used for locating element using ng-bind locator, But with exact string/value.

Example:

<p ng-bind="person.name"></p>

Code:

expect(element(by.exactBinding('person.name')).isPresent()).toBe(true);

4. buttonText : It is used to locate an element using the text on button tag.
Example:

<button>Show Result</button>

Code:

element(by.buttonText('Show Result')).click();

5. partialButtonText : It can locate the element using the partial text present in the button.
Example:

<button>Show Result</button>

Code:

element(by.buttonText('Show')).click();

6. repeater : ng-repeat is angular locator. Repeater locator is used to locate the elements with ng-repeat attribute in it.
Example:

<tr ng-repeat="product info">
    <td>{{prod.id}}</td>
    <td>{{prod.name}}</td>
    <td>{{prod.quantity}}</td>
</tr>

Code:

var eleID = element(by.repeater('product info').row(0));
expect(eleID.getText()).toBe('101');

var eleName = element(by.repeater('product info').row(1));
expect(eleName.getText()).toBe('Jujubi');

7. exactRepeater : It locates element with ng-repeat attribute with exact string present in it.
Example:

<li ng-repeat="emp in employee_names"></li>

Code:

expect(element(by.exactRepeater('emp in employee_names')).isPresent()).toBe(true);

8. cssContainingText : It locates the element with text in it using css selector.
Example: -

<ul>
<li class="name">Mike</li>
  <li class="name">Linda</li>
</ul>

Code: Below code returns the li for the name mike, but not linda.

element(by.cssContainingText('.name', 'Mike'));

9. Options : It locates the element with ng-option attribute in it.
Example:

<select ng-options="options in list">
  <option value="0">Option 1</option>
  <option value="1">Option 2</option>
  <option value="2">Option 3</option>
</select>

Code:

var allOptions = element.all(by.options('options in list'));
expect(allOptions.count()).toEqual(3);

10. addLocator : Add a locator to this instance of ProtractorBy. This can be used for creating a custom locators and load them later in config.

Example :-

<button ng-click="viewResults()">View</button>

Add the custom locator in Protractor :-

by.addLocator('buttonTextExample',
function(buttonText, opt_parentElement, opt_rootSelector) {
var using = opt_parentElement || document,
buttons = using.querySelectorAll(‘button’);
// Return an array of buttons with the text.
return Array.prototype.filter.call(buttons, function(button) {
return button.textContent === buttonText;
});
});

Using custom locator in Protractor :-

element(by.buttonTextExample('View')).click();

11. deepCss : It is used to find an element using css in Shadow DOM. We have discussed on what is Shadow dom and working with Shadow dom elements using selenium.

Example : -

<div>
  <span id="outerspan">
  <"shadow tree">
    <span id="span1"></span>
    <"shadow tree">
      <span id="span2"></span>
    </>
  </>
</div>
<code>

Using deepcss in protractor :-

<code>
var spanEles = element.all(by.deepCss('span'));
expect(spanEles.count()).toEqual(3);

Let us know if you find this article useful. Please let us know if you have any queries / suggestions in the comment box.

Protractor Tutorials: 

Comments

Could you extend on finding shadow DOM elements? Because deepCss only works for the given example with span, but it doesn't work for other elements, it throws "no such element". Thanks.

This article will help to get better understanding of the locators in the protractor. Thank you Joel Ortiz.

Add new comment

CAPTCHA
This question is for testing whether or not you are a human visitor and to prevent automated spam submissions.