Monday, 17 February 2014

Elements locator in webdriver

In WebDriver automation everything related with web elements as it is web application automation tool.
WebElement is nothing but, all DOM objects appeared in the web page. To do operations with DOM objects/ web elements we need to locate those elements exactly.
WebElement element=driver.findElement(By.<Locator>);
As we've seen in the above statement we have to specify some locator to identify web element.
'By' is the class, in that class we have different static methods to identify elements. Those are,
By.className
By.cssSelector
By.id
By.linkText
By.name
By.partialLinkText
By.tagName
By.xpath

By.className
See below example
Example:1
<td class=name> </td>
WebElement td=driver.findElement(By.className("name"));
By.cssSelector
CSS selector is the one the best ways to locate some complex elements in the page.
See below some examples for easy understanding
Example:1

<td class=name> </td>
driver.findElement(By.cssSelector("td.name")); In css selector we can denote class name with dot (.)
(or)
driver.findElement(By.cssSelector("[class=name]")) We can specify the attribute name and its value.

Example:2
<input id=create>
driver.findElement(By.cssSelector("#create")).sendKeys("test"); shortcut for denoting id is #
( or )
driver.findElement(By.cssSelector("[id=create]")).sendKeys("test")

Example:3
<td value=dynamicValue_13232><td>

driver.findElement(By.cssSelector("[value*=dynamicValue]")) * is for checking contained value
(here value contains dynamicValue)
Example:4
<div value=testing name=dynamic_2307></div>
driver.findElement(By.cssSelector("[value=testing][name*=dynamic]"));
If you want to include more attribute values in locator criteria use css locator as above.
By.id
See below example
Example:1
<td id=newRecord> </td>

WebElement td=driver.findElement(By.id("newRecord"));
here we can specify the id attribute value directly.
By.linkText
See below example
Example:1
<a onclick=gotonext()>Setup </a>
WebElement link=driver.findElement(By.linkText("Setup"));
This is the best locator for locating links (anchor tags) in your web page.
By.partialLinkText
See below example
Example:1
<a onclick=gotonext()>very long link text </a>
WebElement link=driver.findElement(By.partialLinkText("very"));
(or)
WebElement link=driver.findElement(By.partialLinkText("long link"));

This is the locator for locating links (anchor tags) using partial text it contains .
By.name
See below example
Example:1
<td name=WebDriver> </td>
WebElement td=driver.findElement(By.name("WebDriver"));
By.tagName
See below example
Example:1
<td class=name> </td>
WebElement td=driver.findElement(By.tagName("td"));
If you want to get the entire text of web page use below logic.
driver.findElement(By.tagName("body")).getText()
XPath is the language used for locating nodes in an XML document. As HTML can be an implementation of XML (XHTML), Selenium users can leverage this powerful language to target elements in their web applications. XPath extends beyond (as well as supporting) the simple methods of locating by id or name attributes, and opens up all sorts of new possibilities such as locating the third checkbox on the page.

One of the main reasons for using XPath is when you don’t have a suitable id or name attribute for the element you wish to locate. You can use XPath to either locate the element in absolute terms (not advised), or relative to an element that does have an id or name attribute. XPath locators can also be used to specify elements via attributes other than id and name.

Absolute XPaths contain the location of all elements from the root (html) and as a result are likely to fail with only the slightest adjustment to the application. By finding a nearby element with an id or name attribute (ideally a parent element) you can locate your target element based on the relationship. This is much less likely to change and can make your tests more robust.

For instance, conside this page source:
<html>
<body>
<form id="loginForm">
<input name="username" type="text" />
<input name="password" type="password" />
<input name="continue" type="submit" value="Login" />
<input name="continue" type="button" value="Clear" />
</form>
</body>
<html>

The form elements can be located like this:

login_form = driver.find_element_by_xpath("/html/body/form[1]")
login_form = driver.find_element_by_xpath("//form[1]")
login_form = driver.find_element_by_xpath("//form[@id='loginForm']")

Absolute path (would break if the HTML was changed only slightly)
First form element in the HTML
The form element with attribute named id and the value loginForm

The username element can be located like this:

username = driver.find_element_by_xpath("//form[input/@name='username']")
username = driver.find_element_by_xpath("//form[@id='loginForm']/input[1]")
username = driver.find_element_by_xpath("//input[@name='username']")

First form element with an input child element with attribute named name and the value username
First input child element of the form element with attribute named id and the value loginForm
First input element with attribute named ‘name’ and the value username

The “Clear” button element can be located like this:

clear_button = driver.find_element_by_xpath("//input[@name='continue'][@type='button']")
clear_button = driver.find_element_by_xpath("//form[@id='loginForm']/input[4]")

Tuesday, 11 February 2014

XPath Overview



XPath gets quiet a bad press with regards to Selenium testing, and is sometimes the reason people ‘give up’ with their test automation. Basically, XPath is very powerful, it treats the web page as a structured document (which it is), and allows you to traverse the hierarchy of nodes (elements).

The two common misconceptions of XPath are: it’s slow, and it’s brittle. These are only true of complex XPaths that are heavily dependent of the structure of your web page. It’s true that in general XPath is slower than CSS locators, but you can just as easily write complex and brittle CSS locators.

XPath is one of the locator strategies often used when Selenium IDE is recording a test. The brittleness and speed issues can be mostly avoided by using simple and relative XPaths. This means finding an element near the one you want that you can locate quickly and easily (great if it has an id), and then describing how to get to your target element. As with CSS, some examples will help me to explain.

<div id="register">
<label>Email:</label>
<input type="text"/>
<label>Full Name:</label>
<input type="text"/>
</div>

To locate the fullname textbox in the above HTML snippet you could use the following:

xpath=id(‘register’)/input[2]

This locates the second input element beneath the element with an id value of ‘register’

xpath=//label[text()=‘Full Name:’]/following-sibling::input

This first locates a label element with the text contents of ‘Full Name:’ and then moves onto the following input element

The more complex your XPath gets, the longer it could take for the browser to find your element, and the more dependent your locator is on the structure of the page. This means that minor changes to the HTML on the page that cause no functional changes could quite easily cause your tests to fail.

Monday, 10 February 2014

Types of Locators in webdriver


Typesof Locators
Locators have changed with Selenium 2 with the WebDriver API. Out of the box WebDriver supports several ways to locate elements on the page using the By abstract class.

ids are the preferred way to locate elements on a page for 2 main reasons:
According to w3c ids are supposed to be unique on an html page. This makes ids a very explicit and reliable way to locate elements on the page.
Also, all browsers also have highly efficient methods to get an object on the page using their ids. This makes id locators the fastest type of locator in Selenium.
Let us now look at how to use id locators using this html code as an example:

<form name="loginForm">
    Login Username: <input id="username" name="login" type="text" />
    Password: <input id="password" name="password" type="password" />
    <input name="login" type="submit" value="Login" />
</form>
In the above code, the username and password text fields are can be set using their ids. The locators for them would be

driver.findElement(By.id(username));

Even though this is a great locator, it is not realistic for all elements on a page to have ids. The developers add ids to key elements on the page to better control the look and feel or provide the dynamic user interaction. However, ids should also be added to elements that are frequently interacted within tests … to make the pages more testable. Automated test script authors should consider adding, or requesting addition of, ids to these key elements on the page.

In some cases, the ids on an element cannot be reliably used in a test. For instance, if you are displaying objects stored in the database, the objects ids could contain the database id in it.

Generally ids are added to elements when they want to be referenced from css or javascript and names are added to form fields. When referencing element from javascript either can be used. From a test automation standpoint, whenever id is not available/ usable, you should try to use the name instead.
Using the same example above, the way you would find the submit button would be:

driver.findElement(By.name("login"));

There is one big difference between the id and name attributes though … name attributes don’t have to be unique in a page. If there are multiple elements with the same name, then the first element in the page is selected. So, in this example, if another button or form named “login” was present of added later, it could cause the test to fail.


This locator identifies links by the text in them. Let us look at an example:

<html>
 <body>
    ...
    <a href="signin.html">Sign In</a> to modify your account details.
    ...
</body>
</html>
To click this hyperlink using the anchor tag’s text, you can use the By.linkText() locator:

driver.findElement(By.linkText("Sign In"));

If there are multiple elements with text “Sign In”, the first one is selected.

Btw, this is called linkText because it is used for hyperlinks. In Selenium if you used the link=textPattern locator, you could use it to locate other elements like div, span, td etc. In WebDriver, this locator works only for links.

Another common case is when we need to find links by a portion of the text it contains. In such cases you can find it by specifying the partial text. For example:

driver.findElement(By.partialLinkText("Sign"));

XPath is a very powerful language to express which element to identify. If you use it correctly, it can produce very reliable and low maintenance locators, but if you use it incorrectly, it can create very brittle test cases.


As you can guess, some of these expressions will not be as reliable as others. Of these //table/tr[2]/td/input is the worst because it would break even with slightest modification to the page structure. It can take some time to learn XPath if you aren’t familiar with it, but it is worth the time if you plan to spend a lot of time writing UI automated tests. In any case do not rely on tools, including selenium IDE, to generate the right xpath expression for you. They can help you get started but they are usually bad at identifying the more reliable XPaths.

There are some special cases you should be aware of when you work with XPath, like when you are trying to interact with SVG. Like in the example here, the html looks something like this:

<div id="svgchart">
  ...
    <svg xmlns="http://www.w3.org/2000/svg">
        <g>
            <path .../>
        </g>
        ...
    </svg>
  ...
</div>
Here, if you use XPath like:

//svg

you will get ERROR org.openqa.selenium.NoSuchElementException: Unable to locate element. This is because the svg element is in a different namespace. You will have to specify your xpath with the namespace uri like this instead:

//*[local-name()='svg' and namespace-uri()='http://www.w3.org/2000/svg']

So, if XPath’s are so versatile, why doesn’t everyone prefer these? It’s because they are often the slowest, especially in older versions of IE! There are some ways you can make XPath’s faster, but they still are a few times slower than ids or names.


css locators can be used to identify a large number of elements on a page.
</table>
In this case the css locator variations possible for the highlighted input field are:


input.required
input[class~='required']
input.required[type='text']
#item2_quantity
input#item2_quantity

The css locator may not be as expressive as XPath, but it generally executes faster.


This is more of a convinience mechanism to identify elements. In the css example above, instead of using

driver.findElements(By.css("input[class~='required']"));

you could use

driver.findElements(By.class("required"));

DOM stands for Document Object Model. DOM is convention for representing objects in HTML documents.

<form id="loginForm">
    Login Username: <input id="username" name="username" type="text" />
    Password: <input name="password" type="password" />
    <input name="login" type="submit" value="Log in" />
</form>
In this page, the dom expression for the highlighted input field would be:


document.forms[0].elements[0]
document.forms['loginForm'].elements['username']
document.forms['loginForm'].username
document.getElementById('username')

For those who have used Selenium 1 API, you would expect to find a By.dom() equivalent api, but it doesn’t exist. However, you still can get a handle to these elements using dom expressions by using the following code snippet instead:

    driver.findElement(byDom("document.forms[0].elements[0]"));
public By byDom(String domExpression) {
    final Object o = ((JavascriptExecutor) driver).executeScript("return " + domExpression + ";");
    if (o instanceof WebElement) {
        return new By() {
            @Override
            public List<WebElement> findElements(SearchContext searchContext) {
                return new ArrayList<WebElement>() {
                    {
                        add((WebElement) o);
                    }
                };
            }
        };
    }
}
The three key aspects of this code that you should note,

The driver can be casted to JavaScript Executor and other interfaces which will provide additional capabilities.
execute Script() in JavaScript Executor returns an object which can be casted to a WebElement if the JavaScript expression returns a dom element.
You can create your own implementation of By
Some things to note for Selenium 1 users
You will notice that Implicit locators are not supported in WebDriver.
When using name in Selenium 1, you could add other attributes in the expressions to filter the results. For example name=login type=text was valid. You cannot do that any more with the By.name() call.
findElement() and findElements()
As you might have noticed in the examples above, the By locators were used within findElement and findElements methods. The purpose of these methods is to return a WebElement, in case of findElement, and a list of WebElements in the case of findElements.

The WebElement represents an html element on the page. In the next section you will see that it is this WebElement object that you would interact with or read attributes of for validations etc.

When you use these methods on the WebDriver object, the scope within with the elements are located is the entire page.


The WebElement interface also has findElement() and findElements() methods. In this case, it is within the scope of this parent element that child elements are located. This is useful when you want to narrow the scope to find several elements that you would interact with. In most cases, narrowing the scope improves the execution times for locating the elements.

Tuesday, 4 February 2014

Unit testing with JUnit



JUnit is a unit testing framework for the Java programming language. JUnit has been important in the development of test-driven development, and is one of a family of unit testing frameworks collectively known as xUnit that originated with JUnit.
we'll define a unit test as a test of a single isolated component in a repeatable way. Let's go thru that one section at a time to get a clearer idea of what goes into a unit test.

"a test". This means to verify something is correct. In order for us to have a valid unit test, we need to actually validate that after a start condition A, an end condition B exists. "...a single isolated component...". This is what separates a unit test from other types of tests.
 In order for it to be a unit test, it must test something in isolation, aka without dependencies. The reason for this is that we are testing the component itself and not it's interaction with other components (that is an integration test).
Finally, although most definitions don't include this piece, "...in a repeatable way" is a very important piece of the definition. It's one thing to run a test that passes. It's quite different to have something you can run in a repeatable manor at any point to see if changes you made effected how the component behaves. For example, if you choose to do some refactoring to improve performance, can you rerun your unit test to verify that you didn't change the behavior of the component.

In test driven design, we develop the unit test before the functionality. We write a test that verifies that the class should do X after our call. We prove that the test fails, we then create the component to make the test pass. In this case, we are going to create a service with a method that authenticates a user. Below is a class diagram of the scenario.

We will start our coding by defining two interfaces, LoginService and Userx We will implement LoginService, For LoginService, we have a single method that takes a String userName and String password and returns a boolean (true if the user was found, false if it was not). The interface looks like this:

Provides authenticated related processing.
public interface LoginService {
     Handles a request to login.  Passwords are stored as an MD5 Hash in
     this system.  The login service creates a hash based on the paramters
     received and looks up the user.  If a user with the same userName and
     password hash are found, true is returned, else false is returned.
     boolean login(String userName, String password);
}
The Userx  interface will look very similar to the LoginService. It will have a single method that takes a userName and hash. The hash is an MD5 hashed version of the password, provided by the above service.

Provides database access for login related functions
public interface User x{
 Loads a User object for the record that
 is returned with the same username and password.

     User loadByUsernameAndPassword(String userName, String password);
}
Before we begin development, we will develop our test. Tests are structured by grouping methods that perform a test together in a test case. A test case is a class that extends junit.framework.TestCase. So in this case, we will begin by developing the test case for LoginService. To start, in your test directory, create a new class named LoginServiceTest and make it extend junit.framework.TestCase.

The lifecycle of a test execution consists of three main methods:

setUp is executed before each of the test. It is used to perform any setup required before the execution of your test. Your implementation will override the default empty implementation in TestCase.
testSomething is the actual test method. You may have many of these within a single test case. Each one will be executed by your test runner and all errors will be reported at the end.
tearDown is executed after each test method. It is used to perform any cleanup required after your tests.
So to begin flushing out our test case, we'll start with the setUp method. In this method, we'll instantiate an instance of the service to be tested. We'll also create our first mock object, UserDAO. You can see the source of our test below.