select an element with protractor

There are different ways to select an element using protractor. You can get it by using id or tagName or css selector or or ng-repeat etc.

Select an element by id using protractor

element(by.id('element id'));

Select an element by css selector using protractor

element(by.css("css selector"));
css selector means you can select element using its class, attribute etc

Select element by class using protractor

element(by.css(".className"));
Example:
consider you have a element like
<div class="test"></div>
you can select the above element by its class name using protractor
element(by.css(".test"));

select element by tag name using protractor

element(by.tagName("h1"));

Select element by attribute using protractor

element(by.css("attributeValue"));
Example:

consider you have a element like below
<input type="button" class="test" ng-click="getAllRecords()" />
now you can select the above element by its ng-click attribute using protractor
element(by.css('[ng-click="getAllRecords()"]'));

Select element by ng-repeter using protractor


consider you have a div element for which you are applying ng-repeat.
<div ng-repeat="item in items">
    {{item.name}}
</div>
you can select all the elements resulted by ng-repeat using protractor
element.all(by.repeater("item in items"));
If you want to select only first element from ng-repeat , you can select by using below code
element.all(by.repeater("item in items")).get(0);
Read more...

Test new window url using protractor

You can test the new window url using protractor.


Consider a scenario where you have to click on a html element(say <a href='url' target='_blank'/>) which opens a new window and you want to check the url of the new window opened using protractor. You can check the url using below code

it("should check the new window url"function () {
    element(by.id('id of the element to be clicked')).click();
    browser.getAllWindowHandles().then(function (handles) {
        newWindowHandle = handles[1];
        browser.switchTo().window(newWindowHandle).then(function () {
            expect(browser.driver.getCurrentUrl()).toBe("url to check");
        });
    });
});

The above code checks the url of the new window opened.

Note:

In the above code we are using browser.driver.getCurrentUrl() because the newly opened window may not contain angular in it. If it conatins angular, then use browser.getCurrentUrl() to get the url of the window.

Now if you want to close the newly opened window and test something else on the previous window you can do that by using below code 

it("should check the new window url"function () {
    element(by.id('id of the element to be clicked')).click();
    browser.getAllWindowHandles().then(function (handles) {
        newWindowHandle = handles[1];
        browser.switchTo().window(newWindowHandle).then(function () {
            expect(browser.driver.getCurrentUrl()).toBe("url to check");
            //to close the current window
            browser.driver.close().then(function () {
                //to switch to the previous window
                browser.switchTo().window(handles[0]);
            });
 
        });
    });
});

The above code closes the newly opened window after the url is checked and switches to the previous window.

In this way you can check the url of the new window using protractor.

For more posts on protractor visit: Protractor

Read more...

Select element from ng-repeat using protractor

You can select any element from ng-repeat using Protractor.

Consider you have ng-repeat like this
<div ng-repeat="item in items">
    <span>{{item.name}}</span>
</div>

If you have 5 items then your div will be repeated 5 times.

So, if you want to select an element from ng-repeat use below code
var elm = element.all(by.repeater('item in items')).get(0);

The above code returns the first element in ng-repeat.

We use element.all because we are getting more than one element when selecting through ng-repeat. So to select all the elements we have to use element.all.


Click on first element in ng-repeat using Protractor


To click on the first element in ng-repeat use below code
element.all(by.repeater('item in items')).get(0).click();

similarly you can click on any element in ng-repeat just by changing the index in get()

Example :
element.all(by.repeater('item in items')).get(n).click();


Get Text from first element in repeater using protractor


To read the text from the first element in ng-repeat use below code
element.all(by.repeater('item in items')).get(0).getText();

In our example we are showing item name in a span. So, to get the text we have to use the following code
var elm = element.all(by.repeater('item in items')).get(0);
elm.findElement(by.css('span')).getText();

Similarly you can get text of any element in ng-repeat by changing the index in get()

Example
element.all(by.repeater('item in items')).get(n).getText();

In this way you can select element from ng-repeat using protractor

Read more...

Conditionally apply a class with AngularJS

Using AngularJs we can apply a class condionally on any element by using ng-class.

According to AngularJS docs on ng-class

The ng-class allows you to dynamically set a css class name on html element by data-binding an expression that represents all classes to be added.


ng-class supports an expression that must evaluate to either
  1. a string of space-delimited class names, or
  2. an array of class names, or
  3. a map/object of class names to boolean values.

Example:

Consider you have a div element as shown below

<div class="example">
    //inner elements
</div>

Now if you want to add class named "selected" to the above div conditionally. You can add the class using below code

<div class="example" ng-class="{'selected':isActive}">
    //inner elements
</div>

The class named "selected" gets applied to the above div only if "isActive" property is true.

The result will be like below

<div class="example selected" ng-class="{'selected':isActive}">
    // inner elements
</div>

You can even directly add a property(of model) as a class. see code below

<div ng-class="model.color">
    //inner elements
</div>

if model.color is "red" class named "red" is gets applied to the div.

The result will be like below

<div class="red" ng-class="model.color">
    //inner elements
</div>

Note

The directive won't add duplicate classes if a particular class was already set.
When the expression changes, the previously added classes are removed and only then the new classes are added.

In this way you can apply a class conditionally using AngularJS


For more posts on AngularJS please visit : AngularJS

Read more...

Element is not clickable at point using chrome driver

When you are trying to click on a element using chrome driver you may come across the error element is not clickable at this point.

This is due to the chrome driver always clicks the middle of the element in attempt to be faithful to what an actual user does.

The chrome driver first identifies the location of the element then clicks the middle of the element.

So if you are trying to click on a moving element, the chrome driver tries to clicks at the position where it first finds that element. And at the time of clicking , if the element is not at the same position, then chrome driver throws the error "Element is not clickable at this position". 

You may get this error in the following cases.

1. If the position of the element is changing in the DOM. 
2. If you are applying transformations/transitions/animations to that element.
3. If you are trying to click on a element before it gets loaded etc.

You don't face any problem when you are testing in IE or FF. You mostly face this issue when you are testing on chrome.

Quick Fix for Element is not clickable at point:


After reading all the discussions in the webdriver community at this page  https://code.google.com/p/selenium/issues/detail?id=2766 , i have found some quick fixes with which you can solve this issue

1. Many people are facing this issue only after upgrading to newer version of Chrome Driver
In the older version we have implicit waits, which waits for the element to be fully loaded. But now we have to explicitly wait for the element to load. 

We can do this by telling the browser to sleep for some time (say 2 seconds).

We have the following commands to tell the browser to sleep for some 'x' seconds  (choose the command based on your testing tool)

browser.sleep(2000); // for angular e2e testing using protractor
Thread.Sleep(2000); // for selenium webdriver

2. I see one more work around in the comment 27 in the above page

Scroll the element into view before clicking it.

For Javascript with webdriver:

IWebElement element = driver.findElement(By.xpath('element xpath'));
(driver as IJavaScriptExecutor).ExecuteScript(string.Format("window.scrollTo(0,{0});",element.Location.Y));
element.Click();

You cal also try following code

WebElement element = driver.findElement(By.xpath('element xpath'));
((JavaScriptExecutor) driver).ExecuteScript("window.scrollTo(0,"+element.getLocation().y+")");
element.click();

For Python:

ActionChains(w).move_to_element_with_offset(link,0,20).click().perform();

For Ruby with Capybara and selenium web-driver

#where @session is Capybara::session instance
#and object is a Capybara::Node::Element istance
@session.driver.execute_script "window.scrollTo(#{object.native.location.x},#{object.native.location.y})"
return_string = object.native.click 

Using the above work arounds you can solve the issue "Element is not clickable at point"
Read more...

Bootstrap modal close event

Boot strap refers two hide events that we can use 

Bootstrap 3 modal close event 



hide.bs.modal :  This event is fired immediately when the hide instance method has been called.

hidden.bs.modal : This event is fired when the modal has finished being hidden from the user (will wait for CSS transitions to complete).

Example:

You can use the following syntax to catch the bootstrap modal hide event 

$('#myModal').on('hidden.bs.modal', function () {

    // do somtething here

});

bootstrap 2 modal close event


hide: This event is fired immediately when the hide instance method has been called.

hidden: This event is fired when the modal has finished being hidden from the user (will wait for css transitions to complete).

Example:

You can use the following syntax to catch the bootstrap modal hide event

$('#myModal').on('hidden', function () {

     // do something…

});

Using above jquery code you can catch the bootstrap modal close event.
Read more...