Wednesday, May 1, 2013

Executable Specifications using GUI-Less browser frameworks


Most of the tests for a product backlog are defined in terms of UI as that’s how the P.O or stakeholders think of the user story. Creating UI tests is also important for agile teams as it is a way of telling our customers that the user acceptance scenarios are tested and verified on every release and he/ she is going to use the application which is intended to work as he/ she expects. But integrating the UI automation tests with the builds (CI) comes with some challenges like browser configurations, non-interactive sessions etc. For these reasons frameworks that do not drive an actual browser, but simulate browser behaviors are becoming popular among agile teams.
 NHtmlUnit is a .Net wrapper of HtmlUnit a UI-less browser for Java programs. It models HTML documents and provides an API that allows you to invoke pages, fill out forms, click links, etc... just like you do in your "normal" browser. NHtmlUnit can be easily integrating with other unit testing frameworks like NUnit, MSTests etc.

A simple example of testing web pages using NHtmlUnit is as given below.

[TestClass]
public class SampleAppSmokeTestSuite
{
    private WebClient _webClient;

    [TestInitialize]
    public void TestInitialize()
    {
         _webClient = new WebClient(); 
    }

    [TestCleanup]
    public void TestCleanup()
    {
        _webClient.CloseAllWindows();
    }

    [TestMethod]
    public void UserLoginAcceptanceScenario()
    {
        var loginPage = _webClient.GetPage("http://localhost:42017/Home.aspx") as HtmlPage;
        Debug.Assert(loginPage != null, "loginPage != null");
        var header = loginPage.GetElementById("header");
        Assert.AreEqual(header.TextContent, "NHTML UNIT");

        var txtUserName = loginPage.GetElementById("txtUsername");
        var txtPassword = loginPage.GetElementById("txtPassword");


        txtUserName.SetAttribute("value", "user@mailserver.com");
        txtPassword.SetAttribute("value", "password");

        var submitButton = loginPage.GetElementById("btnLogin");
        var homePage = submitButton.Click() as HtmlPage;

        Debug.Assert(homePage != null, "homePage != null");

        var homeHeader = homePage.GetElementById("header");
        Assert.IsTrue(homeHeader.TextContent.Contains("Welcome"));
    }
}

The test initialize methods creates a WebClient object, which is the starting point for NHtmlUnit tests. This object acts as your browser simulator. The GetPage method returns the html page for the Uri passed to the method. The IPage object represents a single web page along with all of the client's data including HTML, JavaScript, and CSS etc.
You can now use this HtmlPage object to access the DOM elements by using methods like GetElementById, or GetElementByClass or GetByXPath etc. Once the elements are accessed you can use the object model to get or set values on these elements and perform actions like Click to simulate the actual behavior of the user. By integrating with an existing unit testing framework, you can do your assertions to validate the results.

No comments: