Friday, September 2, 2011

Selenium Grid with Webdriver

Recently I gone through the webdriver and then I thought to configure it with Selenium grid. On selenium grid site they have mention how to configure it but it's not in details so i though to write that on this blog.
To configure webdriver with Selenium grid you require grid2.

Prerequisites.
  • TestNG
  • Grid2
    Download the selenium-server-standalone-version.jar from the below location.
    Download Grid2

We will see two things in Selenium Grid.
  1. Run Testcase in parallel
  2. Run same testcase on different browser in parallel for browser compatibility testing.

Run Testcases in parallel.

In this example we will run testcases of GridWithWebdriver and GridWithWebdriver1 class on Internet Explorer.

GridWithWebdriver.java
/**
 * @author Gaurang Shah
 * To Demonstrate how to configure webdirver with Selenium Grid
 */
import java.net.MalformedURLException;
import java.net.URL;

import org.junit.AfterClass;
import org.openqa.selenium.*;
import org.openqa.selenium.remote.DesiredCapabilities;
import org.openqa.selenium.remote.RemoteWebDriver;
import org.testng.annotations.*;

public class GridWithWebdriver {
 
 public WebDriver driver;
 
 @Parameters({"browser"})
 @BeforeClass
 public void setup(String browser) throws MalformedURLException {
  DesiredCapabilities capability=null;
   
  if(browser.equalsIgnoreCase("firefox")){
   System.out.println("firefox");
   capability= DesiredCapabilities.firefox();
   capability.setBrowserName("firefox"); 
   capability.setPlatform(org.openqa.selenium.Platform.ANY);
   //capability.setVersion("");
  }
 
  if(browser.equalsIgnoreCase("iexplore")){
   System.out.println("iexplore");
   capability= DesiredCapabilities.internetExplorer();
   capability.setBrowserName("iexplore"); 
   capability.setPlatform(org.openqa.selenium.Platform.WINDOWS);
   //capability.setVersion("");
  }
  
  driver = new RemoteWebDriver(new URL("http://localhost:4444/wd/hub"), capability);
  driver.navigate().to("http://google.com");
  
 }
 
 @Test
 public void test_first() throws InterruptedException{
  Thread.sleep(3000);
  WebElement search_editbox = driver.findElement(By.name("q"));
  WebElement search_button = driver.findElement(By.name("btnG"));
  search_editbox.clear();
  search_editbox.sendKeys("first");
  search_button.click();
 }
 
 @Test
 public void test_second(){
  WebElement search_editbox = driver.findElement(By.name("q"));
  WebElement search_button = driver.findElement(By.name("btnG"));
  search_editbox.clear();
  search_editbox.sendKeys("second");
  search_button.click();
 }
 
 @AfterClass
 public void tearDown(){
        driver.quit();
 }
}
GridWithWebdriver1.java
/**
 * @author Gaurang Shah
 * To Demonstrate how to configure webdirver with Selenium Grid
 */
import java.net.MalformedURLException;
import java.net.URL;

import org.junit.AfterClass;
import org.openqa.selenium.*;
import org.openqa.selenium.remote.DesiredCapabilities;
import org.openqa.selenium.remote.RemoteWebDriver;
import org.testng.annotations.*;

public class GridWithWebdriver1 {
 
 public WebDriver driver;
 
 @Parameters({"browser"})
 @BeforeClass
 public void setup(String browser) throws MalformedURLException, InterruptedException {
  DesiredCapabilities capability=null;
   
  if(browser.equalsIgnoreCase("firefox")){
   System.out.println("firefox");
   capability= DesiredCapabilities.firefox();
   capability.setBrowserName("firefox"); 
   capability.setPlatform(org.openqa.selenium.Platform.ANY);
   //capability.setVersion("");
  }
 
  if(browser.equalsIgnoreCase("iexplore")){
   System.out.println("iexplore");
   capability= DesiredCapabilities.internetExplorer();
   capability.setBrowserName("iexplore"); 
   capability.setPlatform(org.openqa.selenium.Platform.WINDOWS);
   //capability.setVersion("");
  }
  
  driver = new RemoteWebDriver(new URL("http://localhost:4444/wd/hub"), capability);
  driver.navigate().to("http://google.com");
  
 }
 
 @Test
 public void test_third() throws InterruptedException{
  Thread.sleep(3000);
  WebElement search_editbox = driver.findElement(By.name("q"));
  WebElement search_button = driver.findElement(By.name("btnG"));
  search_editbox.clear();
  search_editbox.sendKeys("third");
  search_button.click();
  
 }
 
 @Test
 public void test_fourth(){
  WebElement search_editbox = driver.findElement(By.name("q"));
  WebElement search_button = driver.findElement(By.name("btnG"));
  search_editbox.clear();
  search_editbox.sendKeys("foruth");
  search_button.click();
  
 }
 
 @AfterClass
 public void tearDown(){
        //Close the browser
     //   driver.quit();

 }
}

Testng.xml
<suite name="Selenium Grid with webdriver" verbose="3"  parallel="classes" thread-count="2">   
  <test name="Selenium Grid Demo">
  <parameter name="browser" value="iexplore"/>
    <classes>
      <class name="tests.GridWithWebdriver"/>
   <class name="tests.GridWithWebdriver1"/>
    </classes>
 </test>
 </suite>

Now in order to run using testng.xml we need to start the Grid hub and two remote control with Iexplore as browser.

Now to start the Grid and remote control open CMD and navigate to folder where Grid2 jar (selenium-server-standalone-x.x.x.jar) file is located and use the following commands

To start the Grid Hub
java -jar selenium-server-standalone-2.5.0.jar -role hub
To start the remote control supporting Internet explore
java -jar selenium-server-standalone-2.5.0.jar -role webdriver -hub http://localhost:4444/grid/register -browser browserName=iexplore,platform=WINDOWS
To start another the remote control supporting Internet explore
java -jar selenium-server-standalone-2.5.0.jar -role webdriver -hub http://localhost:4444/grid/register -browser browserName=iexplore,platform=WINDOWS -port 5556

After this open http://localhost:4444/grid/console in you browser. You should be able to see something like below image.



Now if you will run using testng.xml you will see two Internet explorer will open and one will execute test_first() and test_second() while another will execute test_third() and test_fourth() in parallel.

Run same testcases on different browser in parallel.

In this example we will execute GridWithWebdriver tests on Firefox and Internet Explorer in parallel.

To do so you need to modify you testng.xml as below.
Testng.xml
<suite name="Same TestCases on Different Browser" verbose="3"  parallel="tests" thread-count="2">   
  <test name="Run on Internet Explorer">
 <parameter name="browser"  value="iexplore"/>
    <classes>
      <class name="Tests.GridWithWebdriver"/>
    </classes>
 </test>  

  <test name="Run on Firefox">
 <parameter name="browser"  value="firefox"/>
    <classes>
      <class name="Tests.GridWithWebdriver"/>
    </classes>
 </test>  
 </suite>
Now to run testcases we need to start grid hub and one remote control supporting Firefox and another supporting Internet Explorer.

Now to start the Grid and remote control open CMD and navigate to folder where Grid2 jar (selenium-server-standalone-x.x.x.jar) file is located and use the following commands
To start the Grid Hub
java -jar selenium-server-standalone-2.5.0.jar -role hub
To start the remote control supporting Firefox
java -jar selenium-server-standalone-2.5.0.jar -role webdriver -hub http://localhost:4444/grid/register -browser browserName=firefox,platform=WINDOWS
To start another the remote control supporting Internet explore
java -jar selenium-server-standalone-2.5.0.jar -role webdriver -hub http://localhost:4444/grid/register -browser browserName=iexplore,platform=WINDOWS -port 5556
After this open http://localhost:4444/grid/console in you browser. You should be able to see something like below image.

Now if you will run above test case one Firefox and one IE will launch and both test_first() and test_second() will execute in both browser simultaneously.

Wednesday, August 31, 2011

Selenium Grid for Browser Compatibility Testing

There are two way things we can use Selenium Gird for.


so let's see how to use selenium grid for browser compatibility testing.

There are two way we can make this happen
  1. Using different browsers on same machine.
  2. Using different browsers on different machines.

Using different browsers on same machine.
In this example we will use SeleniumGridDemo.java file, It has two methods test_first() and test_second() which we will execute on Safari and Internet Explorer in parallel.

SeleniumGridDemo.java
/**
 * @author Gaurang Shah
 * To demonstrate the Selenium Grid 
 */
import org.testng.annotations.*;
import com.thoughtworks.selenium.DefaultSelenium;
import com.thoughtworks.selenium.Selenium;

public class SeleniumGridDemo {

 public Selenium selenium;

 @Parameters( { "browser" })
 @BeforeClass
 public void setup(String browser) {
  selenium = new DefaultSelenium("localhost", 4444, browser,"http://google.com");
  selenium.start();
 }

 @AfterClass
 public void tearDown() {
  selenium.stop();
 }

 @Test
 public void test_first() {
  selenium.open("/");
  selenium.type("q", "First");
  selenium.click("btnG");
 }

 @Test
 public void test_second() {
  selenium.open("/");
  selenium.type("q", "second");
  selenium.click("btnG");
 }

}
testng.xml
<suite name="Same TestCases on on same machine on different Browser" verbose="3"  parallel="tests" thread-count="2"> 
  <test name="Run on Firefox">
 <parameter name="browser"  value="*safari"/>
    <classes>
      <class name="SeleniumGridDemo1"/>
    </classes>
 </test>
  <test name="Run on IE">
 <parameter name="browser"  value="*iexplore"/>
    <classes>
      <class name="SeleniumGridDemo1"/>
    </classes>
 </test>
</suite>

Now you can run this using eclipse IDE or you can write down the ANT build file as follows.

build.xml
<project name="demo" default="run" basedir=".">

 <property name="classes.dir" value="bin" />
 <property name="src.dir" value="src" />
 <property name="report.dir" value="reports" />
 
 <path id="libs">
  <fileset dir="src\Libs\">
   <include name="*.jar"/>
  </fileset>
  <pathelement path="${basedir}\${classes.dir}"/>
 </path>

 <target name="run">
  <antcall target="init"/>
  <antcall target="compile"/>
  <antcall target="runTestNG"/>
  </target>
 
 <!-- Delete old data and create new directories -->
 <target name="init" >
  <echo>Initlizing...</echo>
  <delete dir="${classes.dir}" />
  <mkdir dir="${classes.dir}"/>
  <delete dir="${report.dir}" />
  <mkdir dir="${report.dir}"/>
  <mkdir dir="${logs.dir}"/>
 </target>

 <!-- Complies the java files -->
 <target name="compile">
  <echo>Compiling...</echo>
  <javac debug="true" srcdir="${src.dir}" destdir="${classes.dir}"   classpathref="libs" />
 </target>

 <target name="runTestNG">
  <taskdef resource="testngtasks" classpathref="libs"/>
 <testng outputDir="${report.dir}" 
   haltonfailure="false"
   useDefaultListeners="true"
   classpathref="libs">
 <xmlfileset dir="${basedir}" includes="testng.xml"/>
 </testng>
 </target>
 </project>


Now in order to run testcases in parallel we need to start grid hub and selenium remote controls. As we have specified two threads in testng.xml we will start two remote controls.
To start grid hub and remote control, Open command prompt, go to selenium grid directory and give following commands.

to stat the grid hub
ant launch-hub
To Start the selenium remote control for Internet explorer
ant launch-remote-control -Denvironment=*safari
To Start the selenium remote control for Internet explorer on different port
ant launch-remote-control -Denvironment=*iexplore -Dport=5556
After this open http://localhost:4444/console. In this you should be able to see both the remote controls under Available Remote Controls section as appears in below image.

Using different browsers on different machines
To run the testcases on different machine we don't require to change in testng.xml or java file we just need to start two remote control on two different machines.

We will start Remote control for safari browser on local machine and for IE browser on remote machine.
To start grid hub and remote control, Open command prompt, go to selenium grid directory and give following commands.

to stat the grid hub
ant launch-hub
To Start the selenium remote control for Internet explorer
ant launch-remote-control -Denvironment="*safari"

Now Login into another machine and from command prompt navigate to selenium grid directory and fire following command
ant launch-remote-control -DhubURL=http://172.29.72.185:4444/ -Denvironment=*iexplore
In above command 172.29.72.185 is the IP address where my Selenium grid Hub is running.

After this open http://localhost:4444/console. In this you should be able to see both the remote controls under Available Remote Controls section as appears in below image.

Monday, August 29, 2011

Selenium Grid

Selenium grid is basically used to run the testcases in parallel. There are two things you can do using selenium grid.
1. You can run the testcases in parellel to save the execution time.
2. You can run the same testcases on different browsers in parellel to test for the browser compatibility.

So let's see how to do it.

Run Testcases of different classes in parallel on same machine.
In this example we have to classes SeleniumGridDemo1 and SeleniumGridDemo2. SeleniumGridDemo1 class has two methods test_first() and test_second(). SeleniumGridDemo2 also has two methods test_third() and test_fourth().

By the following configuration test_first() and test_second() will run in parallel with test_third() and test_fourth().

SeleniumGridDemo1.Java
/**
 * @author Gaurang Shah
 * To demonstrate the Selenium Grid 
 */
import org.testng.annotations.*;
import com.thoughtworks.selenium.DefaultSelenium;
import com.thoughtworks.selenium.Selenium;

public class SeleniumGridDemo1 {

	public Selenium selenium;

	@Parameters( { "browser" })
	@BeforeClass
	public void setup(String browser) {
		selenium = new DefaultSelenium("localhost", 4444, browser,"http://google.com");
		selenium.start();
	}

	@AfterClass
	public void tearDown() {
		selenium.stop();
	}

	@Test
	public void test_first() {
		selenium.open("/");
		selenium.type("q", "First");
		selenium.click("btnG");
	}

	@Test
	public void test_second() {
		selenium.open("/");
		selenium.type("q", "second");
		selenium.click("btnG");
	}

}

SeleniumGridDemo2.java
/**
 * @author Gaurang Shah
 * To demonstrate the Selenium Grid 
 */
import org.testng.annotations.*;
import com.thoughtworks.selenium.DefaultSelenium;
import com.thoughtworks.selenium.Selenium;


public class SeleniumGridDemo2 {
public Selenium selenium;
	
	@Parameters({"browser"})
	@BeforeClass
	public void setup(String browser){
		selenium = new DefaultSelenium("localhost", 4444, browser, "http://google.com");
		selenium.start();
	}
	
	@AfterClass
	public void tearDown(){
		selenium.stop();
	}
	
	@Test
	public void test_third() { 
		selenium.open("/");
		selenium.type("q","third");
		selenium.click("btnG");
	}	
	@Test
	public void test_fourth() {
		selenium.open("/");
		selenium.type("q","fourth");
		selenium.click("btnG");
	}

}

TestNG.xml
<suite name="parelledSuite" verbose="3"  parallel="classes" thread-count="2">   
  <test name="Selenium Gird Demo">
  <parameter name="browser" value="*iexplore"/>
    <classes>
      <class name="SeleniumGridDemo1"/>
	  <class name="SeleniumGridDemo2"/>
    </classes>
 </test>
 </suite>

Now in order to run testcases in parallel we need to start grid hub and selenium remote controls. As we have specified two threads in testng.xml we will start two remote controls.
To start grid hub and remote control, Open command prompt, go to selenium grid directory and give following commands.

to stat the grid hub
ant launch-hub
To Start the selenium remote control for Internet explorer
ant launch-remote-control -Denvironment="*iexplore"
To Start the selenium remote control for Internet explorer on different port
ant launch-remote-control -Denvironment="*iexplore" -Dport=5556

After this open http://localhost:4444/console. In this you should be able to see you both the remote controls under Available Remote Controls section as appears in below image.



Now you can run the same using testn.xml from you eclipse any other IDE or you can write down ANT file.

<project name="demo" default="run" basedir=".">

 <property name="classes.dir" value="bin" />
 <property name="src.dir" value="src" />
 <property name="report.dir" value="reports" />
 
 <path id="libs">
  <fileset dir="src\Libs\">
   <include name="*.jar"/>
  </fileset>
  <pathelement path="${basedir}\${classes.dir}"/>
 </path>

 <target name="run">
  <antcall target="init"/>
  <antcall target="compile"/>
  <antcall target="runTestNG"/>
  </target>
 
 <!-- Delete old data and create new directories -->
 <target name="init" >
  <echo>Initlizing...</echo>
  <delete dir="${classes.dir}" />
  <mkdir dir="${classes.dir}"/>
  <delete dir="${report.dir}" />
  <mkdir dir="${report.dir}"/>
  <mkdir dir="${logs.dir}"/>
 </target>

 <!-- Complies the java files -->
 <target name="compile">
  <echo>Compiling...</echo>
  <javac debug="true" srcdir="${src.dir}" destdir="${classes.dir}"   classpathref="libs" />
 </target>

 <target name="runTestNG">
 	<taskdef resource="testngtasks" classpathref="libs"/>
	<testng outputDir="${report.dir}" 
			haltonfailure="false"
			useDefaultListeners="true"
			classpathref="libs">
	<xmlfileset dir="${basedir}" includes="testng.xml"/>
	</testng>
 </target>
 

 </project>

Run Testcases of different classes in parallel on different machine
In this example we will run the same testcases in SeleniumGridDemo1 and SeleniumGridDemo2 classes. We don't need to change in testng.xml or any other file.

We just need to start one remote control on local machine and another remote control on another remote machine.

To start grid hub and remote control, Open command prompt, go to selenium grid directory and give following commands.

to stat the grid hub
ant launch-hub
To Start the selenium remote control for Internet explorer
ant launch-remote-control -Denvironment="*iexplore"

Now Login into another machine and from command prompt navigate to selenium grid directory and fire following command
ant launch-remote-control -DhubURL=http://172.29.72.185:4444/ -Denvironment=*iexplore
In above command 172.29.72.185 is the IP address where my Selenium grid Hub is running.

After this open http://localhost:4444/console. In this you should be able to see both the remote controls under Available Remote Controls section as appears in below image.


Wednesday, August 3, 2011

WATIR framework

What I am going to discuss here is a standard Page Object Pattern Framework for WATIR.

What each and every framework requires are, Driver Script, Object repository, Script to read data from Data source(EXCEL, CSV or any other), Files to generate and store reports and finally Test Files.

Download Project

The framework designed by me contains following things
Xunit framework test-unit
Data Sources: EXCEL and YAML
Reports: I am using ci_reporter with JUnit ANT target to generate HTML report
Driver Script: BATCH file which will run tests according to parameter passed and will generate the report.
Object Repository: Ruby class per page.

Now let's see everything in details.

Test Script:LoginTestWithYAML.rb inside Test Folder
require 'rubygems'

gem 'test-unit'
require 'test\unit'
require 'watir'
require_relative '../Libs/BaseClassInstanceMethods'
require_relative '../Libs/BaseClassClassMethods'
require_relative '../ObjRepository/LoginPage'
require_relative '../Libs/ReadYAML'

class LoginTestWithYAML < Test::Unit::TestCase
  include ReadYAML
  include LoginPage
  include BaseClassInstanceMethods
  extend BaseClassClassMethods
  def test_gmail
    username_textbox.set(readData("noPassword","username"))
    password_textbox.set(readData("noPassword","password"))
    login_button.click()
    assert(($browser.text.include? "Enter your password."),"Verify Error Messages")
  end
end
ReadYAML.rb inside Libs folder
require 'yaml'

=begin
Author: Gaurang
read the YAML file based on the given scenario name and fieldname
=end

module ReadYAML
  @@config = YAML.load_file("#{File.dirname(__FILE__)}/../data/gmail.yaml")
  def readData(scenarioName, fieldName)
    if (@@config[scenarioName][fieldName].nil?) then
      return ""
    else
      return @@config[scenarioName][fieldName]
    end

  end
end
Object repository: LoginPage.rb inside ObjRepository folder
=begin
Author: Gaurang
Contains all the elements on the login page
=end

module LoginPage
  def username_textbox
    return $browser.text_field(:id,"Email")
  end

  def password_textbox
    return $browser.text_field(:id,"Passwd")
  end

  def login_button
    return $browser.button(:id,"signIn")
  end
end
ANT Target to generate HTML report
http://qtp-help.blogspot.com/2011/07/watir-html-report.html

And finally our driver scripts: run.rb
require 'rubygems'
gem 'test-unit'
require 'test/unit'
gem 'ci_reporter'
require 'ci/reporter/rake/test_unit_loader.rb'
=begin
Author: Guarang
Driver file which would run all the tests inside Test Folder.
=end

class Run

  if (ARGV.length >= 1 ) then
    if (ARGV[0].downcase == "smoke") then
      p "smoke"
      folder= "Tests/Smoke/*.rb"
    elsif  (ARGV[0].downcase == "regression") then
      p "regression"
      folder= "Tests/Regression/*.rb"
    end
  else
    p "default"
    folder= "Tests/*.rb"
  end
 
  Dir[folder].each do |test|
    p test
    require_relative test
  end

end
rub.bat
If you want to run all the tests inside Tests\Smoke folder give enter the following command on command prompt
run smoke
for regression enter the following command
run regression
if you will not provide any argument it will run all the tests under Tests folder.
@echo off 
@echo "initializing..."
rd /s/q Test
@echo "Running Tests..."
ruby run.rb %1
@echo "Generating reports..."
start cmd /C ant
rem wait for 6 seconds
PING 1.1.1.1 -n 1 -w 6000 >NUL
@echo "Opening report..."
start test/reports/junit-noframes.html"

Thursday, July 28, 2011

WebDriver First look

WebDriver has been for a while but never get a chance to look at it. finally today I downloaded the webdriver and executed the simple testcase. Let's see how to configure webdriver for java.

First download the selenium-java-2.2.0.zip (version may differ) from http://code.google.com/p/selenium/downloads/list

The first thing you will notice when you will extract this zip is, too much JAR files, too much as compared to only two in selenium RC.

Now create the simple java project in eclipse. Put all the extracted JAR files in the buildpath of the project.

Copy and paste the following code and run using Junit. (you don't require to run any selenium server)

package Tests;

import static org.junit.Assert.assertTrue;

import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
import org.openqa.selenium.By;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.WebElement;
import org.openqa.selenium.firefox.FirefoxDriver;
/**
 * 
 * @author Gaurang
 *
 */
public class GoogleTest  {

 public static WebDriver driver;
 @BeforeClass
 public static void setup(){
 // Create a new instance of the Firefox driver
        driver = new FirefoxDriver();
        
        // And now use this to visit Google
        driver.get("http://www.google.com");
 }
 
 @AfterClass
 public static void tearDown(){
        //Close the browser
        driver.quit();

 }
 @Test
 public void testSearch() throws InterruptedException {
        // Find the text input element by its name
        WebElement element = driver.findElement(By.name("q"));
        // Enter something to search for
        element.sendKeys("Cheese!");
        //driver.findElement(By.name("btnG")).click();
        // Now submit the form. WebDriver will find the form for us from the element
        element.submit();
        // Check the title of the page
        System.out.println("Page title is: " + driver.getTitle());
        Thread.sleep(3000);
        assertTrue(driver.getTitle().contains("cheese!"));
  }
}

To run the webdriver testcase in Internet Explorer
replace the driver = new FirefoxDriver(); line from the setup() method with following line.
driver = new InternetExplorerDriver();

To run the webdriver testcase in Opera
replace the driver = new FirefoxDriver(); line from the setup() method with following line.
driver = new OperaDriver();

To run the Webdriver testcase in Chrome
Download the chrome driver form the below URL
Download Chrome driver

Now extract the zip file and set the path of executable in PATH variable.

replace the driver = new FirefoxDriver(); line from the setup() method with following line.

driver = new ChromeDriver();

Selenium - Handle Alert and Confirmbox

Handling alertbox.
Alertbox is special kind of modal dialog created though JavaScript. As it's modal dialog box the things in the parent window will not be accessible until close it.

selenium has getAlert()  method to handle javascript alertbox, It will click on the OK button of the alertbox and will return the text of the alertbox to verify. However Selenium fails to identify the alertbox if it has appeared through page load event. ( i.e. should not appeared when you navigate to some page or when refresh it).

Handle Alertbox at page load event
selenium is not able to indentify the dialogs appeard at the pageload event. look at this.
So I tried to click on the OK button with AutoIt script. I make the Autoit script, not a big, it's just three lines of code and tested it with both the browser and it did well. But when I call the same script (exe) from my testcase it fails to indentify the alertbox and my testcase failed. I am still finding out why the hell this is happening.
Following is the script to handle alertbox appeard at body load event.
AutoItSetOption("WinTitleMatchMode","2")

WinWait($CmdLine[1])
$title = WinGetTitle($CmdLine[1]) ; retrives whole window title
MsgBox(0,"",$title)
WinActivate($title)
WinClose($title); 


Confirmbox
Confirm box is a kind of alertbox with OK and Cancel button as compared to only OK button in alerbox.
Selenium provides following APIs to handle this.
chooseOkOnNextConfirmation() - This will click on the OK button if the confirm box appears after executing the very next step.
chooseCancelOnNextConfirmation() - This will click on the cancel button if the confirm box appears after executing the very next step.

You need to write down any of the above functions (depends on you requirement, ofcourse) just before the step which opens the confirmbox.
/**
 * @author Gaurang Shah
 * Purpose: To handle Confirm box.
 * Email: gaurangnshah@gmail.com
 */
import org.testng.annotations.*;
import com.thoughtworks.selenium.DefaultSelenium;
import com.thoughtworks.selenium.Selenium;

public class Handle_Alert {
private Selenium selenium;


@BeforeClass
public void startSelenium() {
selenium = new DefaultSelenium("localhost", 4444, "*chrome", "http://gaurangnshah.googlepages.com/");
selenium.start();

}

@AfterClass(alwaysRun=true)
public void stopSelenium() {
this.selenium.stop();
}

@Test
public void handleAlert() throws Exception{
selenium.open("selenium_test");
selenium.click("Alert");
String a = selenium.getAlert();
System.out.println(a);
}

@Test
public void handleConfirmBox() throws Exception {
selenium.open("selenium_test");
selenium.chooseCancelOnNextConfirmation();
selenium.click("Confirm");
}
}
Download above file

Watir - Setup and TearDown

In Test/Unit framework setup and teardown method invokes before and after each and every tests but sometimes we require to call setup method before test method of the class and teardown method after the last test method of the class.

After searching so much on the internet i found this

In the following example setup and teardown method will be called before and after each and every test.
beforeClass method will be called before the first test method executes.
afterClass method will be called after the last test method executes.

require 'test/unit'

class TestSuite < Test::Unit::TestCase

  def setup
    p 'setup'
  end

  def teardown
    p 'teardown'
  end

  def test1
    p 'test1'
  end

  def test2
    p 'test2'
  end

  def self.suite
    s = super
    def s.beforeClass
      p 'suite_setup'
    end

    def s.afterClass
      p 'suite_teardown'
    end

    def s.run(*args)
      beforeClass
      super
      afterClass
    end
    s
  end
end

Tuesday, July 26, 2011

WATIR: Parameterization with Excel

Ruby has already a functionality under win32ole package to make your test data-driven.
It has functions to read and write data from and to cell. if you need to read the data from a column and 10th row the code will the something like below.
value = worksheet.Range("a10").Value

However the problem with above code is, when we use that in automation we need to remember what data does "a" column contains, is it username or password or error messages and which scenario does 10th row contain, valid or invalid ?

To get rid of all this question i have write the excel class which will read the data based on given column name(data field name) and row name(scenario name).

The excel file we will access should look like below, where first row should contain data field names and first column should contain scenario names.

Following is the excel class which will read the data based on given data field name and scenario name
Excel.rb
require 'win32ole'

=begin
Purpose: Class to read Excel file given the column name and scenario name
Author:  Gaurang Shah
=end

class Excel

  @@map = Array["a","b","c","d","e","f","g","h","i","j","k","l","m","o","p","q","r","s","t","u","v","w","x","y","z"]
  #provide the path of the EXCEL file.. i.e. c:/demo.xls
  #Provide the worksheet number if you have multiple worksheets
  #If you will not provide the worksheet number by default it will take 1
  def initialize(path, workSheetNumber=1)
    @path=path
    @workSheetNumber=workSheetNumber
  end

  def openExcel
    # puts "inside excel"
    @excel = WIN32OLE::new("excel.Application")

    @workbook = @excel.Workbooks.Open("#{File.dirname(__FILE__)}/#{@path}")

    @worksheet = @workbook.WorkSheets(@workSheetNumber)
    # just to make sure macros are executed, if your sheet doesn't have macros you can skip this step.
    @worksheet.Select

    column = @worksheet.range("a1:a100").Value
    index=0
    while(column[index].to_s != "") do
      index = index+1
    end

    @scenarios = Array.new(index)
    for i in(0...index)do
      @scenarios[i] = column[i]
    end
  end

  #Returns the EXCEL cell value based on provided ScenarioName and columnName
  def getValue(scenarioName,columnName)

    openExcel()
    #get the first line of excel
    columnNames = @worksheet.Rows(1).value[0]

    #Find out the total number of columns
    name=0
    while(columnNames[name+=1] != columnName) do
    end
    #puts name

    begin
      colData = @worksheet.Range("#{@@map[name]}1:#{@@map[name]}100").Value
    rescue
      return "Data Not Found: Invalid Column"
    end

    totalScenarios  = @scenarios.length
    for index in(0..totalScenarios) do
      if(@scenarios[index].to_s == scenarioName) then
        break;
      end
    end

    if(index >= totalScenarios) then
      return "Data Not Found: Invalid Scenario"
    end
    index+=1;

    value = @worksheet.range("#{@@map[name]}#{index}").value
    @workbook.close
    @excel.Quit

    if(value.nil?) then
      return ""
    end
    return value
  end
end

Following is the sample test which will use the excel class to make test data-driven(parametrized)
DemoTest.rb
require 'test/unit'
require 'rubygems'
require 'watir'
require 'Excel'

class DemoTest < Test::Unit::TestCase
  def setup
    @browser = Watir::Browser.new
    @browser.goto("http://gmail.com")
    @browser.maximize
  end

  def test_gmail
    readExcel = Excel.new("gmail.xls")
    puts readExcel.getValue("noPassword","username")
    @browser.text_field(:id,"Email").set(readExcel.getValue("noPassword","username"))
    @browser.text_field(:id,"Passwd").set(readExcel.getValue("noPassword","password"))
    @browser.button(:id,"signIn").click()
    assert((@browser.text.include? "Enter your password."),"Verify Error Messages")
  end

  def teardown
    @browser.close()
  end
end

Friday, July 15, 2011

WATIR - HTML Report

I was just evaluating WATIR for one of our project and stuck for some time when it came to report.
There are ci_reporter gem which generates xml reports, but we required HTML reports. There are various XSL files available on internet which we can use to generate HTML reports out of this XML, I tried that but the reports were not good. We wanted something like generated through ReportNG or Junit.

So I did the trick, I generated JUnit HTML reports from this WATIR XML report file using junitreport ANT Task.
So let's see how to do it.

First you need to install ci_reporter. use the following command to install it.
gem install ci_reporter

require 'test/unit/testcase'
require 'rubygems'
require 'funfx'
require 'ci/reporter/rake/test_unit_loader.rb'


class Demo < Test::Unit::TestCase
 
  def test_first
      assert(true,"PASS");
  end

  def test_second
      assert(false,"Fail");
  end

end  
When you will run the above code it will generate the XML report under test\report folder. Now to generate the HTML report from this XML file, save the following file as build.xml where your above test file is located.
<project name="Report" default="generateReport" basedir=".">
<property name="report.dir" value="test\reports" />
<target name="generateReport">
 <junitreport todir="${report.dir}">
  <fileset dir="${report.dir}">
    <include name="*.xml" />
  </fileset>
  <report format="noframes" todir="${report.dir}" />
 </junitreport>
 </target>
</project>

Now run the following command from command line.

ANT

But before you run this command ANT need to be installed on your system. Download and install the ANT from following location.
http://ant.apache.org/bindownload.cgi

Following is the screenshot of report.

Thursday, July 14, 2011

Selenium with Regular Expression

import static org.junit.Assert.assertTrue;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;

import com.thoughtworks.selenium.DefaultSelenium;
import com.thoughtworks.selenium.Selenium;


public class SeleniumWithRegex {
 static Selenium selenium;
 @BeforeClass
 public static void setUp() throws Exception {
  selenium = new DefaultSelenium("localhost", 2323, "*chrome", "http://qtp-help.blogspot.com");
  selenium.start();
 }
 /**
  * Verify Text using regular expression
  * @throws InterruptedException
  */
 @Test
 public void verifyText() throws InterruptedException {
  selenium.open("/2010/10/selenium-checkbox-example.html");
  assertTrue(selenium.isTextPresent("regexp:.*gaurang00.*"));
 }
 
 /**
  * Click on button using regular expression
  * @throws InterruptedException
  */
 @Test
 public void testButton() throws InterruptedException {
  selenium.allowNativeXpath("false");
  selenium.click("//input[matches(@id,'Gaurang.*')]");
 }
 
 /**
  * Click on link using regular expression
  * @throws InterruptedException
  */
 @Test
 public void testLink() throws InterruptedException {
   selenium.click("link=regexp:gaurang.*");

 }
 
 @AfterClass
 public static void tearDown(){
  selenium.close();
  selenium.stop();
 }
}

Tuesday, May 31, 2011

Selenium - Parameterization with CSV

Earlier we saw how to write down data driven test cases using Excel file. Using Excel for data driven has it's own advatages like you can write down you function in excel and get rid of programming logic from your test. However to connect to excel you need JDBC connectivity which has it's own overhead in terms of processing time and you always need to remember to close the connection.

In a way using CSV for selenium automation is much faster than Excel. so let's see how to use CVS file with selenium automation.

Save the following data as data.csv. First row is header

Scenario name,username,password
valid,Gaurang,Shah
invalid,Gaurang,ccc


import java.io.BufferedReader;
import java.io.FileReader;
import java.util.HashMap;
import java.util.Map;
import java.util.StringTokenizer;

/**
 * @author GauranG Shah
 */
public class ReadCSV {
 /**
  * 
  * @param scenarioName - Row Name
  * @param columnName
  * @param fileName - CSV file name where data is stored
  * @return - Sting value
  */
 public String getValue(String scenarioName, String columnName,String fileName){
  
  try {

   // csv file containing data
   String strFile  =  fileName;
   String strLine   =   "";
   StringTokenizer st  =   null;
   int lineNumber   =   0;
  
   // create BufferedReader to read csv file
   BufferedReader br = new BufferedReader(new FileReader(strFile));

   strLine = br.readLine(); //read first line 
   st = new StringTokenizer(strLine, ",");
   int totalRows = st.countTokens();
  
   
   Map<Object,String> mp=new HashMap<Object, String>();
   
   //Fetch the header
   for(int row=0; row<totalRows; row++){
    mp.put(new Integer(row), st.nextToken());
   }
   lineNumber++;

   while ((strLine = br.readLine()) != null){
    st = new StringTokenizer(strLine, ",");
    lineNumber++;
    if(st.nextToken().equalsIgnoreCase(scenarioName)){
     //Identified the row Now return the specific element based on column name specified.
     totalRows= st.countTokens();
     for(int key=1; key<=totalRows; key++){
      String value = st.nextToken();
      if(mp.get(key).equalsIgnoreCase(columnName)){
       return value;
      }
     }
    }
   } 
 
  }catch (Exception e){
   System.out.println("Exception while reading csv file: " + e);
  }
  
  return "Element Not Found";
 }
 
 //This is just to show usage, you can discard this when you use in your project
 public static void main(String[] args) {
  ReadCSV rc = new ReadCSV();
  System.out.println(rc.getValue("valid", "username","data.csv"));
  
 }

}

Monday, May 23, 2011

Selenium - Parameterization with EXCEL

let's see how to make your selenium test data driven using excel. Using excel as a data driven has it's own advantage. The biggest advantage is it's in a Table format, means easy to understand and modify.
Now let's take the simple example of Login test where we have multiple scenarios like Valid Login, Wrong Password, Wrong Username and let's see how we will automate it using selenium and excel.

Note: Make sue the excel sheet where you write down the data in above format has name "login"

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;

import org.testng.annotations.DataProvider;
import org.testng.annotations.Test;

/**
 * @author Gaurang
 */
public class Excel {

 public static Connection con ;
 
 public static String dbURL =
     "jdbc:odbc:Driver={Microsoft Excel Driver (*.xls)};DBQ= "+ "demo.xls;"
      + "DriverID=22;READONLY=false";
 public static  String  getValueFromExcel(String SheetName, String ColumnName, String Scenario) throws SQLException, ClassNotFoundException {
  Class.forName("sun.jdbc.odbc.JdbcOdbcDriver");

  Connection con = DriverManager.getConnection(dbURL);
    
   if(con == null)
    System.out.println("Not able to connect to MS EXCEL");
  Statement stmnt = con.createStatement(ResultSet.TYPE_SCROLL_SENSITIVE,ResultSet.CONCUR_UPDATABLE);
  String sFormattedSheetName = "[" + SheetName + "$]";
  SheetName = sFormattedSheetName;
 
  String query = "Select "+ColumnName+" from "+SheetName+" Where TestScenario='"+Scenario+"'" ;
    
  ResultSet rs = stmnt.executeQuery( query );  
  
  rs.next(); //initially cursors is at -1 position
  String value = rs.getString(1);
  rs.close();
  
  return value;
 
 }
 
 @DataProvider(name = "fromExcel")
 public Object[][] createData1() {
  return new Object[][] {
    { "Valid Login" },
    { "Wrong Username"},
    {"Wrong Password"}
  };
 }
 
 @Test(dataProvider="fromExcel")
 public void dataDrivenUsingExcel(String scenarioName) throws SQLException, ClassNotFoundException {
  System.out.println("Scenario="+scenarioName+" UserName="+Excel.getValueFromExcel("login", "UserName", scenarioName));
  System.out.println("Scenario="+scenarioName+" Password="+Excel.getValueFromExcel("login", "Password", scenarioName));
 }
 
}

Sunday, April 17, 2011

Email Testing with Selenium

If you web application is sending some emails and if you have to test writing code that opens email client (gmail or yahoo) and then check the mails is tedious and also not reliable. The best thing you can do for this is you can have your own SMTP server, that sends the mail for you and stores any system generated mail, rather than sending to actual user for your testing. The best SMTP server I came across is Dumbster.

Now let's see how to use this
Dumster.java
public class Dumbster{
  private SimpleSmtpServer server;

     public Dumbster() {       
       if(server == null)
        server = SimpleSmtpServer.start(25);
     }

     public int howManyMainsSent() {
         int noOfMailsSent = server.getReceivedEmailSize();
         server.stop();          
         return noOfMailsSent;
     }
  
       /**
      * Use only when you are sure only 1 email has been generated
      * @return Subject of the first email
      */
    public String getEmailSubject() {
         Iterator mailIterator = server.getReceivedEmail();
         SmtpMessage email = (SmtpMessage)mailIterator.next();
         return email.getHeaderValue("Subject");
     }
  
     /**
      * Use when more then 1 email has been generated
      * @param count If more than one mails are being generated, Index of the mail
      * @return Subject of the requested email
      */
     public String getEmailSubject(int count) {
          Iterator mailIterator = server.getReceivedEmail();
          SmtpMessage email = null;
          for(int i=1; i<=count; i++){
            email = (SmtpMessage)mailIterator.next();
          }
          return email.getHeaderValue("Subject");
      }
}

Now to use Test the mail you just need to create the server of this class just before you mails shoots and then you need to call the particular function you want.

Tuesday, April 12, 2011

Selenium Grid with JUnit

I just tried my hands on Selenium Grid few days back as our tests were taking too much time to execute, almost 5 hours if we run all and so we thought to use Selenium Grid to cut down the time.  I downloaded the Selenium Gid, run the demo and it all went well until I come to know that your framework should also support parallel execution if you want to run multiple test parallel using Grid. And the problem was JUnit doesn't provided parallel execution. One more reason why you should use TestNG...

There is solution where you can write your own class to parallelize the JUnit testcases  or better download from the Internet. There are so many available. But I found the another and bit easy way.

You can use the ANT parallel task to achieve this parallelism. Following is the demo which shows how to execute testcases parallel with Selenium Grid and JUnit.
Download the demo
  1. Download the selenium gird from here and extract it into some folder
  2. Now navigate to extracted folder through command prompt and type following command
    ant launch-hub
    This will launch the hub on port 4444, this is the port where your selenium tests need to connect.
  3. Now you need to launch the remote control.type the following command on command prompt
    ant launch-remote-control
    This will launch the remote control on port 5555. 
  4. Now we have launched one remote control, we will launch another remote control on port 5556. So one class will execute all it's test on remote control running on 5555 and another class will run it's testcases on remote control running on 5556. Type the following command to launch the remote control on 5556 port.
    ant launch-remote-control -Dport=5556
  5. Now we have two remote control running on the same machine we need to run testcases. 
  6. demo1.java
    import static org.junit.Assert.assertTrue;
    import org.junit.After;
    import org.junit.Before;
    import org.junit.Test;
    
    import com.thoughtworks.selenium.DefaultSelenium;
    import com.thoughtworks.selenium.Selenium;
    
    /**
     * @author Gaurang
     */
    public class demo1 {
     Selenium selenium;
    
     @Before
     public void setUp() throws Exception {
      selenium = new DefaultSelenium("localhost", 4444, "*firefox", "http://www.google.co.in/");
      selenium.start();
      selenium.setTimeout("6000");
     }
     
     @Test
     public void test_1() throws Exception {
      System.out.println("1");
      selenium.open("/");
      selenium.type("q", "1");
     }
     @Test
     public void test_2() throws Exception {
      System.out.println("2");
      selenium.open("/");
      selenium.type("q", "2");
     }
    
     @After
     public void tearDown() throws Exception {
       selenium.stop();
     }
    }
    
  7. demo2.java
    import static org.junit.Assert.assertTrue;
    import org.junit.After;
    import org.junit.Before;
    import org.junit.Test;
    
    import com.thoughtworks.selenium.DefaultSelenium;
    import com.thoughtworks.selenium.Selenium;
    
    /**
     * @author Gaurang
     */
    public class demo2 {
     Selenium selenium;
    
     @Before
     public void setUp() throws Exception {
      selenium = new DefaultSelenium("localhost", 4444, "*firefox", "http://www.google.co.in/");
      selenium.start();
      selenium.setTimeout("6000");
     }
     
     @Test
     public void test_3() throws Exception {
      System.out.println("3");
      selenium.open("/");
      selenium.type("q", "3");
     }
     @Test
     public void test_4() throws Exception {
      selenium.open("/");
      selenium.type("q", "4");
     }
      
     @After
     public void tearDown() throws Exception {
       selenium.stop();
     }
    }
    
  8. Build.xml
    <project name="demo" default="run" basedir=".">
     <path id="lib.classpath">
      <fileset dir="lib">
       <include name="*.jar" />
      </fileset>
      <pathelement location="bin" />
     </path>
     
     <target name="run" depends="compile">
      <parallel threadCount='4'>
       <junit printsummary="withOutAndErr" haltonfailure="no">
        <formatter type="xml" usefile="true" />
        <classpath refid="lib.classpath" />
        <batchtest fork="true" todir="results" failureproperty="seleniumTests.failed" errorproperty="seleniumTests.failed">
         <fileset dir="bin">
          <include name="demo1.class" />
         </fileset>
        </batchtest> 
       </junit>
      
      
       <junit printsummary="withOutAndErr" haltonfailure="no">
       <formatter type="xml" usefile="true" />
       <classpath refid="lib.classpath" />
       <batchtest fork="true" todir="results" failureproperty="seleniumTests.failed" errorproperty="seleniumTests.failed">
        <fileset dir="bin">
         <include name="demo2.class" />
        </fileset>
       </batchtest> 
       </junit>
      </parallel>
     </target>
     
     <target name="compile">
     <echo> compiling.....</echo>
      <javac srcdir="src" destdir="bin" classpathref="lib.classpath" />
     </target>
    </project>
  9. Now you run the testcases using build.xml file. Use the following command to run the testcases.
    ant run
    This will run demo1.class and demo2.class in parellel.

Tuesday, March 29, 2011

selenium Timed out after 30000ms error

"Timed out after 30000ms error" is one of the most frequent error of selenium. However the solution of this is very simple, but before we look into it let's see why we are getting this error.

Mostly this error appears after the following statement
selenium.waitForPageToLoad("30000");

Now let's see why it comes.
waitForPageToLoad(timeout) API says that, it will wait for the giving timeout and if page hasn't loaded withing that time it will return error. and so there are two reason it returns error.
  • timeout given is less that what it requires to load the page
  • page is not loading at all, it's just a AJAX call and only part of the page is being updated.

Now let's see the solultion.
The best solution for this is not to use waitForPageToLoad API, rather to wait for some specific element on the page to appear.

For example I am rather than waiting for the google page to load I am waiting until the searchbox is visible.

//Wait until searchbox appears or 3 min
waitForElementPresent("q",3); 
/**
  * @author Gaurang
  * @param xpath
  * @param timeout (minutes)
  * @throws InterruptedException
  * @return returns true if element found in given time else false
  *  Wait for specified time till specific element is not present 
  */
 public boolean waitForElementPresent(String xpath, int timeout) throws InterruptedException{
  int count = 0;
  while(selenium.isElementPresent(xpath) != true){
   Thread.sleep(10*1000); //Wait 10 seconds
   if(count++ > timeout*6 ) break;
  }
  
  if(selenium.isElementPresent(xpath))
   return true;
  else
   return false;
    
 }

Wednesday, March 16, 2011

Selenium with Flex

Recently I just got the chance to check the selenium support with Flex. And after few minutes spending on google I finally find almost everything required for to test flex application.
To provide flex support to selenium is easy, you just need to add few more JAR files but there is a minor problmes too.
  1. You require your developers to rebuild your application with provided library file (SeleniumFlexAPI.swc) by selenium flex
  2. It's not working with Firefox 3.0 or greater version (at least it didn't work with me !!, I am still searching for the solution)

Now let's see how to test flex application with selenium step by step.
  1. Rebuild your flex application
    • Download the zip file from here and extract the zip file
    • In FlexBuilder, add the SeleniumFlexAPI.swc in the /src folder, then build your application with -include-libraries SeleniumFlexAPI.swc as the additional compiler argument
  2. Include the JAR files in the the project
  3. Before you began coding you require following jar files in your build in addition to selenium-java-client-driver.jar
    flashselenium-java-client-extension.jar
    flex-ui-selenium.jar
  4. Write the code
    okay let's write the code.. no no no hang on !! before we write the code we need to identify the elements of the flex application.  I am using following add-on of Firefox to identify the elements.
    FlashFirebug (this is actually a extension of the firebug add-on)
  5. /**
     * @author Gaurang
     */
    import org.junit.Before;
    import org.junit.Test;
    import static org.junit.Assert.*;
    import com.thoughtworks.selenium.DefaultSelenium;
    import com.thoughtworks.selenium.FlexUISelenium;
    import com.thoughtworks.selenium.Selenium;
    
    public class TestFlex {
     Selenium selenium;
      private FlexUISelenium flexUITester;
     @Before
     public void setUp() throws Exception {
      selenium = new DefaultSelenium("localhost", 2323, "*chrome", "http://qtp-help.blogspot.com");
      selenium.start();
      while(selenium.isElementPresent("myInput"))
      Thread.sleep(1000);
      selenium.open("/2011/03/flex-example.html");
      flexUITester = new FlexUISelenium(selenium, "selenium_demo");
     }
     
     @Test
     public void test() {
      //Enter text
      flexUITester.type("Gaurang").at("myInput");
      flexUITester.click("myButton");
      assertEquals("Gaurang", flexUITester.readFrom("myText"));
     }
    }
    
    

Flex example

Tuesday, February 8, 2011

selenium test auto suggest

There are few editboxes in the application that shows suggestions while you type. In some of the application you need to choose from that suggestions only to filled the edit box else it won't consider as in my application while in other application it is optional, like google search engine.

If you will simple type in the editbox using type method it won't give you any suggestion coz it works on keyevent so to see the suggestion you will require to use the keyPressNative method.

following code will open the google.com, will type the "selenium handle" in the search editbox and will choose the first option available and will search that.

public class AutoSuggest {
 Selenium selenium;
 @Before
 public void setUp() throws Exception {
  selenium = new DefaultSelenium("localhost", 2323, "*chrome", "http://www.google.co.in/");
  selenium.start();
 }

 @Test
 public void testUntitled() throws Exception {
  selenium.open("/");
  enterKeyStrokes("selenium handle");
  assertTrue(selenium.isTextPresent("Gaurang Shah"));
 }

 public void enterKeyStrokes(String str) throws InterruptedException {
  char[] strarry = str.toUpperCase().toCharArray();
  selenium.click("q");
  Thread.sleep(1000);
  for(int chars=0; chars<strarry.length; chars++){
   selenium.keyPressNative(""+(int)strarry[chars]);
   Thread.sleep(1000);
  }
  selenium.keyPressNative(String.valueOf(KeyEvent.VK_DOWN));
  selenium.keyPressNative(String.valueOf(KeyEvent.VK_ENTER)); // press enter
  Thread.sleep(2000);
 }
@After
public void tearDown() throws Exception {
 selenium.stop();
}

Thursday, January 20, 2011

this.onXhrStateChange.bind is not a function

Recently I require to work with the proxy injection mode. And as soon as I endup setting selenium for proxy injection mode I got following error.

this.onXhrStateChange.bind is not a function on session  ad4cf7d3106f4f379a27af514bd1ff5d

I tried a lot and finally got the solution. Though using this solution I am not getting above error anymore, browser is opening but some of the other command is failing, like waitforpagetoload.

Solution:
  1.  Download the source code of selenium-java-client-driver.Jar file and extract that into one folder 
  2. Open the file DefaultSelenium.Java and replace the "public void open(String url)" function with the following.
    public void open(String url) {
                    commandProcessor.doCommand("open", new String[] {url,"true"});
        } 
  3. Recompile the file and create new JAR 
  4. Replace the JAR with original JAR, Build the project again and then Run.