Thursday 6 November 2014

Its Time for change - Get rid of au3 and exe file for using AutoIT

     In this series now I am going to dicuss about how to get rid of au3 files and exe files for using AutoIT. We all know how to use AutoIT along with automation code. Its lengthy and tedious process as we have to write AutoIT code and convert them into exe files and maintain all exe files that you use in your code. 
      Lets try an approach which makes this procedure easy.AutoIT allows for GUI automation using a very simple syntax and can be useful for testing Windows applications. It is packaged with AutoItX which supports accessing AutoIt functions through COM objects.AutoItX4Java uses JACOB to access AutoItX through COM and strives to provide a native Java interface while maintaining the simplicity of AutoIt. Getting started is simple.

Requirements: 
1. AutoIT DLL that supports JACOB protocol jacob-1.17-M2-x86.dll 
2. autoitx4java.jar which uses JACOB a Java bridge to run activex components of Autoit (jacob-1.17-M2-x86.dll) 
Both can be freely downloaded from the below links           
http://code.google.com/p/autoitx4java/downloads/list 
http://sourceforge.net/projects/jacob-project/ or use Autoit.dll  that gets downloaded together with AutoIT installation in windows machine. 
          
Steps used to set up: 
1. Add jacob.jar and autoitx4java.jar to your library path.      
2. Place the jacob-1.15-M4-x64.dll file in your library path.(Create a "lib" folder in project space and place jacob-1.15-M4-x64.dll in the    folder)
3. Start using AutoItX.

//sample code for the above approach
File file = new File("lib", "jacob-1.18-M2-x86.dll"); //path to the jacob dll
System.setProperty(LibraryLoader.JACOB_DLL_PATH, file.getAbsolutePath());
AutoItX x = new AutoItX();
String notepad = "Untitled - Notepad";
String testString = "this is a test.";
AutoITutils.startApp("C:\\Windows\\system32\\notepad.exe");
AutoITutils.waitforAppToLoad(notepad);
AutoITutils.setText(notepad, "Edit1", testString);
String strtemp=AutoITutils.getTextfromField(notepad, "Edit1");
x.winWaitActive(notepad);
x.send(testString);
System.out.println(x.winExists(notepad, testString));        
x.winClose(notepad, testString);
       

Wednesday 5 November 2014

Its Time for AutoIT - Parameterizing AutoIT Script through Java

                Many of us are aware that we can use AutoIT for handling windows based popups and Files uploading etc. Now Iam going to discuss about much more advanced usage of this AutoIT. When I was using this AutoIT for files uploading, I got scenario of uploading multiple files in different places. But if I use AutoIT script with the hard coded file path, I cannot use it for other files. Only way I got is to pass parameters to my AutoIT exe file while I run it. AutoIT provides us options for sending parameters from our java code.The below commands from the AutoIT will be used for doing that.

$CmdLineRaw - This command takes the whole text as a single parameter.
Lets see an example with the above command.

Below is the AutoIT script
#include <Constants.au3>
; This displays mesage box with the parameterized text
$text =$CmdLineRaw
MsgBox($MB_SYSTEMMODAL, "My First Script!", $text)

Java code looks like below:

String command="D:/Backup/Project/OwnWorkspace/AutoIT/notepad.exe This is parameterized test";
Runtime.getRuntime().exec(command);

Now the next question is how to multiple parameters.AutoIT provides option for this as well. Below commads are used for doing that.

$CmdLine[0] ; Contains the total number of items in the array.
$CmdLine[1] ; The first parameter.
$CmdLine[2] ; The second parameter.
...
$CmdLine[nth] ; The nth parameter e.g. 10 if the array contains 10 items.

Lets see an example with the above commands:

#include <Constants.au3>
; This displays given text in the notepad
$title =$CmdLine[1]
$text=$CmdLine[2]
Run("C:\Windows\notepad.exe")
Sleep(1000)
WinWaitActive($title)
WinFlash($title)
Sleep(3000)
Send($text)

Java Code:
String command="D:/Backup/Project/OwnWorkspace/AutoIT/notepad.exe \"Untitled - Notepad" \"Hi this is notepad\"";
Runtime.getRuntime().exec(command);

D:/Backup/Project/OwnWorkspace/AutoIT/notepad.exe--it is a path where you stored your .exe file which got converted from au3 file

Wednesday 29 October 2014

Automating CAPTCHA using selenium webdriver

The full form of CAPTCHA is - "Completely Automated Public Turing test to tell Computers and Humans Apart".

A CAPTCHA is a program that  protects  websites against bots  by generating and grading tests that humans can pass but current computer programs cannot.

Captchas are not brakeable but there are some third party captchas that can be breakable and one of the example for it is "jQuery Real Person" captcha. 

It is possible to bypass the captcha on the JQuery-Real-Person plugin to perform a brute force attack.

There is associated parameter with each image, to checkout the characters introduced by the user. But there is not a good chek to assure that the
characteres introduced are the characters shown on the picture.

Therefore we can just choose a pair of parameter and characters and use them in all the request to the web server.

The name of the parameter that determinate the captcha image is "value".
   
Example: The captcha image shown in the example is JYYBME and we use "Inspect Element" on Google Chorme or Firebug on Firefox to search this
line in the code:
  
<input type="hidden" class="realperson-hash" name="defaultRealHash" *
value="-1158072107"*>
  
In this case we already know a valid pair of parameter and characters that we can use to perform a brute force attack bypassing the captcha restriction.

JYYBME ----> *-1158072107*

We can generate as many valid pairs as we want but only one is necessary to perform the brute force attack.


It does not matters that the captcha does not show the characters that we type because the check is done through the value parameter so we just need to type one valid pair of parameter and characters.

The below example illustrates how to break captcha with jQuery Real Person plugin.

import org.openqa.selenium.By;
import org.openqa.selenium.JavascriptExecutor;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.firefox.FirefoxDriver;

 public class Sample { 
  
  static WebDriver driver;
  
 public static void main(String args[]){ 
 try{
  driver = new FirefoxDriver();
  //Loading jQuery Real Person Captcha demonstration page
  driver.get("http://keith-wood.name/realPerson.html");
  Thread.sleep(2000);
  JavascriptExecutor js = (JavascriptExecutor) driver;
  //Setting the captcha values
  js.executeScript("document.getElementsByName('defaultRealHash')[0].setAttribute('value', '-897204064')");
  driver.findElement(By.name("defaultReal")).sendKeys("QNXCUL");
  //Submit the form
  driver.findElement(By.xpath(".//*[@id='default']/form/p[2]/input")).submit(); 
 }
 catch(Exception e){
 //gulp the exception
 }
 }

}

Below are some of the workarounds that we can do to handle captchas in testing scenarios:
  • Captcha is build to avoid automation. But if this is some kind of blocking your testing in QA environment then there is a way to do it. Developers are generating captcha code and display as image. This generated captch code might be stored somewhere in database. Ask your developer the db detail of for storing captcha code and get the code from there and validate on the front.

  • You can ask your development team set a default password/captcha Which you can use to automate in order to check if the flow works fine.Beaware that it is not going to be a test to test Captcha works as such but to check if the flow/scenario that includes captcha pre & pro works accurate.


Tuesday 28 October 2014

Extracting text from PDF files using Selenium + PDF Box

In many production environments, PDF files need to be checked before going to print  or send to customer in order to avoid Legal issues and costly reprints.This PDF files cannot be read by using Selenium. So, here we use PDFBOX, which is third party jar file that reads data from PDF Files. The below example illustrates how to read PDF file by opening them in the browser. To work with this, add the below jar file in classpath of eclipse along with selenium webdriver.
pdfbox-app-1.8.3.jar


import java.io.BufferedInputStream;
import java.io.IOException;
import java.net.URL;
import java.util.concurrent.TimeUnit;
import org.apache.pdfbox.pdfparser.PDFParser;
import org.apache.pdfbox.util.PDFTextStripper;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.firefox.FirefoxDriver;

public class Sample {

 Static WebDriver driver;

   public Static void main(String args[]) throws IOException{
 try{
    // Proxy has to be set if we working under any firewal 
   System.setProperty("http.proxyHost", "proxyname.com");
System.setProperty("http.proxyPort", "portnumber");
System.setProperty("https.proxyHost", "proxyname.com");
System.setProperty("https.proxyPort", "portnumber");
driver = new FirefoxDriver();
 driver.get("http://keith-wood.name/realPerson.html");
 driver.manage().timeouts().implicitlyWait(10, TimeUnit.SECONDS);
 URL url = new URL(driver.getCurrentUrl()); 
 BufferedInputStream fileToParse=new BufferedInputStream(url.openStream());

 //parse()  --  This will parse the stream and populate the COSDocument object. 
 //COSDocument object --  This is the in-memory representation of the PDF document

 PDFParser parser = new PDFParser(fileToParse);
 parser.parse();

 //getPDDocument() -- This will get the PD document that was parsed. When you are done with this document you must call    close() on it to release resources
 //PDFTextStripper() -- This class will take a pdf document and strip out all of the text and ignore the formatting and such.

 String output=new PDFTextStripper().getText(parser.getPDDocument());
 System.out.println(output);
 parser.getPDDocument().close(); 
 driver.manage().timeouts().implicitlyWait(100, TimeUnit.SECONDS);
 }
 catch(Exception e){
 System.out.println(e.getMessage());
 }
  }

}


Wednesday 17 September 2014

Archiving Log4j Reports with Runtime Path

    General Log4j Reports will be stored in the path which is specified in the Log4j.properties or Log4j.xml. But in case if one need to pass reports path in runtime(eg: Time Stamped folder names), we have to override the existing Log4j properties. The below example shows how to archive the reports in the folder which will be passed in runtime.

The below method will override the existing properties of Log4j. Here I am overriding file location and I will pass it in runtime.

public void updateLog4jConfiguration(String logFile) {
       Properties props = new Properties();
       try {
           InputStream configStream = getClass().getResourceAsStream( "/log4j.properties");
           props.load(configStream);
           configStream.close();
       } catch (IOException e) {
           System.out.println("Error: Cannot load configuration file ");
       }
       props.setProperty("log4j.appender.FileAppender.File", logFile);
       LogManager.resetConfiguration();
       PropertyConfigurator.configure(props);
   }

This method has to be called with foldername as parameter and before executing your suite(ideally before starting any of your activity).

eg: updateLog4jConfiguration("C:\\Reports\\Report.log");

Below is the Log4j.property file used for the above example:

log4j.rootLogger=WARN
log4j.logger.com.pgx=DEBUG,FileAppender,ConsoleAppender
log4j.appender.FileAppender=org.apache.log4j.FileAppender
log4j.appender.FileAppender.File=./target/logs/report.log
log4j.appender.FileAppender.layout=org.apache.log4j.PatternLayout
log4j.appender.FileAppender.layout.ConversionPattern= %d{yyyy-MM-dd HH:mm:ss} %-5p: %m%n
log4j.appender.ConsoleAppender=org.apache.log4j.ConsoleAppender
log4j.appender.ConsoleAppender.layout=org.apache.log4j.PatternLayout
log4j.appender.ConsoleAppender.layout.ConversionPattern= %d{yyyy-MM-dd HH:mm:ss} %-5p: %m%n

In this example, we changed only log file location but you can even change pattern, layout, log level and any of the values in log4j.properties file.
 
The main trick here is to put following lines in your running code to reset Lo4j with the new values.
LogManager.resetConfiguration();
PropertyConfigurator.configure(props);

Thursday 28 August 2014

Magic with JExcel

            Most of the automation Frameworks deal with generating reports for various situations. Usually such documents should be designed for reviewing by people who are not closely familiar with different technologies and prefer to obtain reports in a usual format. For Microsoft Windows users, the most common office solution is Microsoft Office, and when talking about electronic worksheets, it is undoubtedly Microsoft Excel.

           The JExcel library allows Java programmers for Windows to easily create, modify or display Microsoft Excel files. Using this library, you can work with workbook files, print a workbook, worksheet or even a specific range of cells, and modify cell values, cell number formats, etc. Also, there is an ability to customize cell appearance, including text font, cell background and border, text alignment and orientation, etc.

           JExcel can be used for solving different tasks from simple display of a workbook in a standalone Excel application to handling Excel events and embedding a workbook into Java Swing applications. The use of the library is very simple and doesn't require from a Java programmer specific knowledge of Microsoft Office programming.

           Many of us knows that JExcel can be used to read and write the excel sheets. But, in this post we will explore various options available for customizing cells in Excel Sheets.

1. Changing a Number Format:
            The range number format reflects the way of displaying numeric data. For instance, a double value can be represented as an integer or as a date. A number format  in Excel is set by a string pattern in a specific locale-dependent format. For detailed specification of the number format, please refer to appropriate articles  on Excel.
         //Getting a range number format
         Range range = worksheet.getRange("A1:A3");
         String numberFormat = range.getNumberFormat();

         System.out.println("A1:A3 number format is " + numberFormat);
  The Range.setNumberFormat(String) method changes the number format of a range:
         
//Setting a custom number format
         String newNumberFormat = "0,00%";
         range.setNumberFormat(newNumberFormat);
         System.out.println("A1:A3 new number format is " + range.getNumberFormat());

2. Changing Text Alignment:            
               JExcel provides the TextAlignment class, which is an enumeration of all alignment types supported by Excel. The Range (Cell) class enables you to obtain and modify both horizontal and vertical text alignment.

             The Range.getHorizontalAlignment() method returns the current horizontal text alignment as an instance of the TextAlignment class. The possible values are TextAlignment.CENTER,TextAlignment.DISTRIBUTED, TextAlignment.FILL,TextAlignment.GENERAL,TextAlignment.JUSTIFY, TextAlignment.LEFT and TextAlignment.RIGHT. If the range cells have mixed horizontal alignment, the return value is null. To change horizontal alignment of a range, call the Range.setHorizontalAlignment() method:
       //Setting custom horizontal text alignment
        range.setHorizontalAlignment(TextAlignment.RIGHT);
        //Checking horizontal text alignment
        if (range.getHorizontalAlignment().equals(TextAlignment.RIGHT))
        {
            System.out.println("A1:A3 range: new horizontal text alignment was applied successfully.");
        }
        else
        {
            System.out.println("Horizontal text alignment failed to be applied.");
        }

3. Changing the Font Size:              
                 The Font class from the com.jniwrapper.win32.jexcel package provides the ability to customize fonts in Excel.
 The following font attributes can be obtained or modified:
 
Font name  
       Call the Font.getName() method to get the font name, and the Font.setName(String) method to specify the font name.
   
Font size
     Call the Font.getSize() method to get the font size, and the Font.setSize() method to specify the font size.
 
General font styles
    The Font class allows you to specify whether the font is bold, italic or strike-through.
 
Font underline style
    The Font.UnderlineStyle class is an enumeration of five underline styles supported by Excel: UnderlineStyle.NONE, UnderlineStyle.SINGLE, 
UnderlineStyle.SINGLEACCOUNTING,UnderlineStyle.DOUBLE,and UnderlineStyle.DOUBLEACCOUNTING.The Font.getUnderlineStyle() method returns the current   underline style as an instance of the Font.UnderlineStyle class. The return value can be one of the predefined values listed above. To change an   underline style, call the Font.setUnderlineStyle() method.
 
Font color
    Call the Font.getColor() method to get the currently set font color, and the Font.setColor() method to specify the font color. A color value in both   functions is an instance of the java.awt.Color class.
 
Font alignment style
    The Font class allows you to specify whether the text is normally aligned, subscript or superscript using the Font.setAlignment() method. This method 
takes one of the three predefined instances of the Font.Alignment class: Alingment.NORMAL, Alignment.SUBSCRIPT or Alignment.SUPERSCRIPT. To obtain the   current font alignment, call the Font.getAlignment() method.

 The following sample demonstrates the technique of changing text font:
       
   //Creating a new instance of the  om.jniwrapper.win32.jexcel.Font class
        Font font = new Font();
        //Changing font name
        font.setName("Courier New");
        //Changing font styles
        font.setBold(true);
        font.setStrikethrough(true);
        font.setUnderlineStyle(Font.UnderlineStyle.DOUBLE);
        //Changing font color
        font.setColor(Color.ORANGE);
        //Applying new font setting
        range.setFont(font);


4. Customizing cell borders:
            To customize a range or cell border, you need to specify the kind of border to work with. There are several standard kinds of borders which are provided in  JExcel as instances of the Border.Kind class. For example, Border.Kind.EDGELEFT or Border.Kind.EDGETOP.
 
         The Range.getBorder() method allows you to obtain an instance of the Border class that corresponds to some border kind. The Border class resides in the  com.jniwrapper.win32.jexcel package.

       The Border class provides functionality for working with border color, line style and line weight. The line style is set using the constants from the  Border.LineStyle class, such as LineStyle.CONTINUOUS, LineStyle.DASHDOT, etc. The line weight is set using the constants from the Border.LineWeight class:  LineWeight.HAIRLINE, LineWeight.MEDIUM, etc.

The following sample demonstrates the technique of customizing the range border:
         
//Getting the top border
         Border topBorder = range.getBorder(Border.Kind.EDGETOP);
         //Getting the border style
         java.awt.Color borderColor = topBorder.getColor();
         Border.LineStyle lineStyle = topBorder.getLineStyle();
         Border.LineWeight lineWeight = topBorder.getWeight();
         //Setting new border style
         Border border = new Border();
         border.setColor(Color.CYAN);
         border.setLineStyle(Border.LineStyle.DASHDOT);
         border.setWeight(Border.LineWeight.MEDIUM);
         //Applying the border settings to the top border
         range.setBorder(Border.Kind.EDGETOP, border);

Below is the consolidated example to coustomize the cells:

  public static void updateExcel(String strFilePath, ArrayList arrValues) throws IOException, BiffException, WriteException {
   try {
    jxl.Workbook workbook = jxl.Workbook.getWorkbook(new File(strFilePath));
    WritableWorkbook writableWorkbook = jxl.Workbook.createWorkbook(new File(strFilePath), workbook);
    WritableSheet writableSheet = writableWorkbook.getSheet(strGlobalSheetName);
    WritableCellFormat cfwithColor = new WritableCellFormat(getCellFormat(Colour.RED, Pattern.SOLID,Border.ALL,BorderLineStyle.THIN));
    WritableCellFormat cfwithoutColor = new WritableCellFormat(getCellFormat(Colour.RED, Pattern.NONE,Border.ALL,BorderLineStyle.THIN));
    // Creates Label and writes data to one cell of sheet
    Label label;
    CellView cellView;
    intOutputRowCntr = intOutputRowCntr + 1;
    for (int intColHdrCntr = 0; intColHdrCntr < arrValues.size(); intColHdrCntr++) {
     if(arrValues.get(intColHdrCntr).toString().contains("~")){
      String strTemp=arrValues.get(intColHdrCntr).toString();
      strTemp=strTemp.substring(0, strTemp.length()-1);
      label = new Label(intColHdrCntr, intOutputRowCntr, strTemp, cfwithColor);
     }
     else
      label = new Label(intColHdrCntr, intOutputRowCntr, arrValues.get(intColHdrCntr).toString(), cfwithoutColor);
     writableSheet.addCell(label);
     cellView = writableSheet.getColumnView(intColHdrCntr);
     cellView.setSize(arrValues.get(intColHdrCntr).toString().length()*256+100);
     writableSheet.setColumnView(intColHdrCntr, cellView);
    }
    writableWorkbook.write();
    writableWorkbook.close();
    workbook.close();
   } catch (Exception e) {
    //gulp the exception
   }
  }
private static WritableCellFormat getCellFormat(Colour colour, Pattern pattern,Border border, BorderLineStyle borderLineStyle) throws WriteException {
                         WritableFont cellFont = new WritableFont(WritableFont.ARIAL, 9, WritableFont.NO_BOLD);
                         WritableCellFormat cellFormat = new WritableCellFormat(cellFont);
                         cellFormat.setBackground(colour, pattern);
                         cellFormat.setBorder(border, borderLineStyle);
                         return cellFormat;
  }


Below is the example display with the above code

 

 

Sunday 17 August 2014

Sikuli integration with Selenium

Sikuli – An introduction
SikuliX automates anything you see on the screen of your desktop computer running on Windows/ Mac/Unix. It uses images patterns to identify and control GUI components.

This is useful when we try to automate a page developed using Flex, Adobe or Flash where the html DOM Structure is not defined easily.
That is why it is called as WYSIWYC – “what you see is what you script”

After reading the above introduction, my first impression as a selenium automation engg was “ May be sikuli is something very complex to learn and use in our day to day automation. Unless we spend some good amount of time in it, we can’t think of using Sikuli”
If your thoughts are similar to these, then you are the one to who is supposed to read this..

Let me give you quick step by step start on using sikuli with selenium.
First let us look at the initial installation and set-up procedures.

 1.       Download and Install Sikuli
·         Download sikuli from the following location.
§  Follow the steps provided in the link for installation guide. 

·         Once sikuli is installed successfully, one can see the changes in the following environment variables.

·         PATH and SIKULI_HOME 

·         The variable PATH would be appended with “ ~/Sikuli X/Sikuli-IDE/libs”

·         The new Variable SIKULI_HOME is assigned with the value  “~/Sikuli X/Sikuli-IDE”

       This indicates the successful installation of sikuli in the system.

2.       Sikuli Integration with selenium

·         Create a normal java project in eclipse as shown below. Let us name it as SikuliSample.

 

·         Next step is to add the required jars in the build path. To do this, select “ConfigureBuildPath” option as shown below


 

·         Add the selenium jars to the build path.

·         Add “Sikuli-script.jar” which is available in ~/Sikuli X/Sikuli-IDE/libs folder.

·         Add “external class folder” in build path and select the “Sikuli-IDE” folder located at ~/Sikuli X/

The final project created in eclipse would like this as shown here.

With this sikuli selenium integration is done seamlessly. You will now be able to start working on it.
Now that installation and set-up is done… Our next step is to create a sample application.

Problem statement: Verify the Google Logo in google.com webpage.
Prerequisite – sample google logo image file. Let’s assume we have this file located at

C:\Temp\google_logo.jpg
Create a new Class called Sample in the project (SikuliSample) we created above.

Add the following code to this class
public static void main(String[] args){
WebDriver driver = new FirefoxDriver();
driver.get(http://www.google.com);
Pattern image = new Pattern("C:\\Temp\\google_logo.jpg");
Screen s = new Screen();
Match m = s.exists(image);
if(m != null){
       s.click(image);
}else{
  System.out.println("Image not found”);
}
}

In this program, we are trying to verify for the presence of google logo in the Google page and click on the logo if present.

In line #1, which is a normal Selenium webdriver code, initializes a firefox driver.

In line #2, driver opens firefox browser to load the google web page.

In line #3, a Pattern object is created for the image with which we want to compare and verify the webpage.

In line #4, a new Screen object is created. This denotes the screen which is being displayed in the monitor of the system.

In line #5, verify if the image pattern is present in the current screen.

If a Match is present, then go ahead and click on the image.

Otherwise, throw a message on the console screen saying “Image nor found”.
 
Run this program and execute it….

Yes you are done..!!!!

Introduction to Behavior Driven Development

 Behavior Driven Development
Behavior Driven Development is an Agile software development technique focused on improving a key factor in the successful development of any software product: Communication. It is a technique devised by Dan North as a response to the issues he encountered whilst teaching Test Driven Development. Eric Evans describes it this way in his book Domain Driven Design: “A project faces serious problems when its language is fractured. Domain experts use their jargon while technical team members have their own language tuned for discussing the domain in terms of design… Across this linguistic divide, the domain experts vaguely describe what they want. Developers, struggling to understand a domain new to them, vaguely understand.”
He goes on to describe the concept of modeling a system using a ubiquitous language based on the business domain, so that the business vocabulary permeates right into the codebase. BDD seeks collaboration amongst the delivery team and business participants in a software project. On the “Agile specifications, BDD and Testing eXchange” in November 2009 in London, Dan North gave the following definition of BDD: “BDD is a second-generation, outside–in, pull-based, multiple-stakeholder, multiple-scale, high-automation, agile methodology. It describes a cycle of interactions with well-defined outputs, resulting in the delivery of working, tested software that matters.”
It is a framework based on three Core Principles:
1. It’s All Behavior: Business and Technology should refer to the same system in the same way
2. Whereas The Business Value: Any system should have an identified, verifiable value to the business
3. Enough Is Enough: Up-front analysis; design and planning all have a diminishing return
Behavior Driven Development centers on obtaining a clear understanding of desired software behavior through discussion with stakeholders. From this initial discussion between the stakeholder or users and the business analyst comes a list of features of the system to be developed, features also known as “User Stories” in our Agile environment. They describe the behavior from the perspective of those interested in the product.
The format is:
As a [X], I want [Y], so that [Z]
Where X is the person (or role) who will benefit , Y is some feature , and Z is the benefit or value of the feature. Its strength is that it forces you to identify the value of delivering a story when you first define it. This can make it easier to descope some of the more esoteric requirements.
The next step is writing test cases in a natural language that non-programmers can read, specifying scenarios of system behavior. A scenario describes the feature acceptance criteria. We call scenarios “acceptance tests;” they express what the software needs to do in order for the stakeholder to find it acceptable. So, everyone on the team, including stakeholders, writes these tests collaboratively, because they not only decide the system behavior, but they learn how to describe that behavior in a common language that everyone understands. If the system fulfills all the acceptance criteria, it’s behaving correctly; if it doesn’t, it isn’t. So a template can be created to capture a story’s acceptance criteria.
The template had to be loose enough that it wouldn’t feel artificial or constraining to analysts but structured enough that we could break the story into its constituent fragments and automate them.
The next step is to automate these scenarios as examples, taking the following form:
Given – some initial context (the givens)
When an event occurs,
Then ensure some outcomes.
Acceptance tests written in this style become more than just tests: they are executable specifications and living documentation. When the software system is continuously validated against a set of executable specifications, the team ensures that the system will do what the specifications say. Or, to put it differently, the specifications will continue to describe what the system does.
They have the following benefits:
  • Living documentation replaces all the artifacts that teams need for delivering the right product.
  • We can continue defining specifications as the system grows up, in an incremental way.
  • They are cheap to write.
To illustrate, a classic ATM can be used as an example:
Title: Customer wants to withdraw cash.
As a customer, I want to withdraw cash from an ATM so that I don’t have to wait in line at the bank
There are many scenarios that we can consider: the account may be in credit, the account may be overdrawn but within the overdraft limit, the account may be overdrawn beyond the overdraft limit. Of course, there will be other scenarios, but let’s use the given-when-then template for an example.
Scenario 1: Account is in credit
Given the account is in credit
And the card is valid
And the dispenser contains cash
When the customer requests cash
Then ensure the account is debited
And ensure cash is dispensed
And ensure card is returned
Scenario 2: Account is overdrawn past the overdraft limit
Given the account is overdrawn
And the card is valid
When the customer requests cash
Then ensure a rejection message is displayed
And ensure cash is not dispensed
And ensure the card is returned
Both scenarios are based on the same event and even have some givens and outcomes in common. We want to capitalize on this by reusing givens, events, and outcomes.
Tools Used:
There are many tools available to in the market to implement the procedure. Following are tools which we use for BDD.
1. JBehave
2. Cucumber
3. SpecFlow
4. Watin
More Details about Tools are on the way. Keep look in the same space for more details. :-)

Enrich Your ReportNG Report with Screenshots and more…

          In the projects where we have a vast number of regression tests it became obvious to our QA team that a good reporting tool for reporting the execution results was of great essence. In the search, a simple HTML plugin for TestNG, called as “ReportNG” was the obvious way to go just because of its simplicity and easiness in integration with TestNG which is our testing framework. ReportNG provided us with a html report presenting each @Test with a pass / fail state. Although many projects are already using this option, here I am going to discuss about enrichment of your ReportNG Reports with some advanced features.

In this journey, we will first discuss about adding screenshot to the ReportNG Report.

Although ReportNG presented an excellent solution to our reporting problems it became apparent that for debugging purposes as well as for defect evidence purposes an extension to include screenshots was needed. These screenshots should be attached to every @Test annotation which fails along with the assertion failure.

Adding Screenshot is a three step procedure:

1. Disable the Default TestNG Listeners:
     For disabling the TestNG Listeners Go to Project –> Right click on the project in which we need to add ReportNG with screenshot. Select “Properties” from the menu displayed. In the displayed window, search for “TestNG” option on the left side tree menu. Up on clicking on the “TestNG” option, you will see check box with the text “Disable default listeners”. Check that check box and click on “Apply”.

    Well done! Now you disabled your default TestNG Listeners. Our next task is assigning the proper listener in the TestNG xml.

2. Adding ReportNG Listeners to TestNG XML:
Add the following lines of XML tags for your existing TestNG XML under “<suite” tag.

<listeners>
< listener class-name=”org.uncommons.reportng.HTMLReporter”/>
<listener class-name=”org.uncommons.reportng.JUnitXMLReporter”/>
< /listeners>
Good work! You are almost there. The next step is to write a code for appending screenshot to your existing ReportNG Report.

3. Write code for appending Screenshot:
Add the following code for test class for doing this task. Let’s discuss about the code now. The first method with the annotation “@AfterMethod” will run after every method . In this method we are calling the “catchExceptions” method which takes care of taking screenshot and appending it to your default ReportNG reports.


@AfterMethod(alwaysRun = true)
public void afterMethod(ITestResult result) throws Exception {
if (!result.isSuccess())
catchExceptions(result);
// Quit environment.
Thread.sleep(1000);
driver.quit();
}
public void catchExceptions(ITestResult result) {
BufferedWriter writer = null;
String methodName = result.getName();
System.setProperty(“org.uncommons.reportng.escape-output”, “false”);
if (!result.isSuccess()) {
try {
String failureImageFileName = “sample1″;
String failureImageFileName1;
scrFile = ((TakesScreenshot) driver).getScreenshotAs(OutputType.FILE);
FileUtils.copyFile(scrFile, new File(failureImageFileName));
String userDirector = System.getProperty(“user.dir”) + “/”;
String s1 = “<table><tr><td><font style=\”text-decoration: underline;\” size=\”3\” face=\”Comic sans MS\” color=\”green\”><b>Screenshot</b></font></td></tr> “;
Reporter.log(s1);
Reporter.log(“<tr><td><a href=\””+ userDirector + failureImageFileName +”\”><img src=\”file:///” + userDirector+ failureImageFileName + “\” alt=\”\””+ “height=’120′ width=’120′/></td></tr> “);
Reporter.setCurrentTestResult(null);
} catch (IOException e1) {
e1.printStackTrace();
}
}
}
 
Fine!! Now you have successfully added the screenshot to your ReportNG Report.

Let’s discuss about another advanced feature “Webpage”. Webpage is nothing but the source code of the corresponding page. While working with selenium, the most probable and simple issues are object locations. As we have page source appended with the report, it is easy for identifying such issues. It also minimizes the debugging time, because while debugging the test case, we don’t want to go to that particular page. WebDriver itself is providing us an option to have that page source.

driver.getPageSource()” will fetch the page source. Now the following will be used to add such page source to our Report. Also see the Screenshots of the ReportNG report after adding these features.

String s2 = “<tr style=\”height:20px\”><td></td></tr>”;
Reporter.log(s2);
String s3 = “<tr><td><font style=\”text-decoration: underline;\” size=\”3\” face=\”Comic sans MS\” color=\”green\”><b>Webpage</b></font></td></tr> “;
Reporter.log(s3);
failureImageFileName1 = userDirector + “sample2″;
scrFile = new File(failureImageFileName1);
writer = new BufferedWriter(new FileWriter(scrFile));
writer.write(driver.getPageSource());
writer.close();
Reporter.log(“<tr><td><a href=\””+ scrFile +”\”><img src=\”file:///” + scrFile + “\” alt=\”\””+ “height=’120′ width=’120′/></td></tr></table> “+”<br />”);
Sample ReportNG Report: (Click for zoom)

Flash App ?? Now you can automate this too :-)

Flash testing is not normal automation testing.
Flash is not part of HTML webpage. Its embed object on HTML webpage.
So its not possible to get xpath of element on the flash movie / flash. As we all know that Webdriver works with the object properties, it is always impossible to automate the flash apps using webdriver.

Then How to automate Flash Applications using webdriver?
      While responding to the same question, the developer of selenium, Jason Huggins has suggested two ways. One way is navigate to the page where the flash object is located using webdriver and get x,y coordinates of the object. Now we can use Java’s Robot library to send an OS-level clicking and typing to an absolute screen coordinate that lines up with the fields and buttons in your flash app. Second way is First, you modify the source code of you the flash application, exposing internal methods using the ActionScript’s ExternalInterface API. Once exposed, these methods will be callable by JavaScript in the browser.Now that JavaScript can call internal methods in your flash app, you use WebDriver to make a JavaScript call in the web page, which will then call into your flash app.

Well!! We are going to see some other techniques apart from Jason’s suggestions .

In the current trends we can handle it based on two factors.
The first one is, when we don’t have any object ids and any Java Script methods exposed by the developer, we can use a tool called “Sikuli”. This is image based recognition tool and can be very well integrated with selenium. You can get the details about sikuli+Selenium from the below path:


The other approach is when you have object ID and Javascript methods exposed by the develeoper. For doing this Selenium RC has extension FlexUISelenium that enables the Selenium RC client drivers to interact (and test) the Flex UI components and methods of the Flex application.
you can download jar and include them into project and get functions to communicate with Flash.

You can get that jar from the below path

https://code.google.com/p/flash-selenium/downloads/detail?name=flash-selenium.jar&can=2&q=

But there is no extension available for Selenium Webdriver.
So we do smart work here. We rewrite FlashSelenium.java for selenium Webdriver.


import org.openqa.selenium.JavascriptExecutor;
import org.openqa.selenium.WebDriver;

public class FlexDriver {
   private final WebDriver webDriver;
   private final String flshObjectId;

   public FlexDriver(final WebDriver webDriver, final String flshObjectId) {
   this.webDriver = webDriver;
   this.flshObjectId = flshObjectId;
}


public String click(final String objectId, final String optionalButtonLabel) {
   return call(“doFlexClick”, objectId, optionalButtonLabel);
}

public String click(final String objectId) {
    return click(objectId, “”);
}


public String call(final String functionName, final String… args) {
    final Object result =
    ((JavascriptExecutor)webDriver).executeScript(
    makeJsFunction(functionName, args),
    new Object[0]);

    return result != null ? result.toString() : null;
}

private String makeJsFunction(final String functionName, final String… args) {
    final StringBuffer functionArgs = new StringBuffer();

       if (args.length > 0) {
         for (int j = 0; j < args.length;j++) {
            if (j > 0) {
                functionArgs.append(“,”);
             }
           functionArgs.append(String.format(“‘%1$s’”, args[j]));
          }
       }
        return String.format(
        “return document.%1$s.%2$s(%3$s);”,
           flshObjectId,functionName,functionArgs);
       }
}


Now we can use the above class for automating with the help of methods exposed by the developer. Just create a class and paste this code.
Here Iam going to demonstrate the use of above class for a website which has flash Object. Create another class and paste the below code and have the fun of automating Flash app.

import org.openqa.selenium.firefox.FirefoxDriver;
public class MainSetting {
    public static void main(String[] args) throws InterruptedException {
         FirefoxDriver driver = new FirefoxDriver();
         driver.get(“http://www.permadi.com/tutorial/flashjscommand/“);
         driver.manage().window().maximize();
         Thread.sleep(5000);
          FlexDriver flashApp = new FlexDriver(driver, “myFlashMovie”);
          flashApp.call(“Play”); // first number
          Thread.sleep(3000L);
          flashApp.call(“StopPlay”); // operation  
          Thread.sleep(3000L);
          flashApp.call(“Rewind”);
            System.out.println(flashApp.call(“GetVariable”,”/:message”));
         flashApp.call(“SetVariable”,”/:message”,”Learn Flash testing with Webdriver”);
          System.out.println(flashApp.call(“GetVariable”,”/:message”));
       }
}

In the above example Iam passing the object’s ID to the “FlexDriver” class along with driver object. Now Iam calling the methods which were exposed by the developer.

Let us see one more example with Youtube.

public class MainSetting {
public static void main(String[] args) throws InterruptedException {
      System.setProperty   (“webdriver.ie.driver”,”D:\\Backup\\Project\\OwnWorkspace\\AutomationJars\\chromedriver.exe”);
        WebDriver driver = new ChromeDriver();
       FlexDriver flashApp = new FlexDriver(driver, “movie_player”);
        //driver.manage().window().maximize();
       driver.get(“http://www.permadi.com/tutorial/flashjscommand/“);
System.out.println(” Page Opened is: “+driver.getCurrentUrl()+driver.getTitle());
        Thread.sleep(5000L);
      //Wait for video to load
     while (Integer.parseInt(flashApp.call(“getPlayerState”)) == 3){
            Thread.sleep(1000);
      }
      // Play the video for 10 seconds
       Thread.sleep(5000);
       flashApp.call(“Play”);
       System.out.println(” Executing pauseVideo function “);  
       Thread.sleep(10000);
       flashApp.call(“StopPlay”);
       System.out.println(” Executing playVideo function “);
       Thread.sleep(5000);
       flashApp.call(“seekTo”,”140″,”true”);
       System.out.println(” Executing seekTo 140 function “);
       Thread.sleep(5000);
       flashApp.call(“mute”);
      System.out.println(” Executing mute audio function “);
      Thread.sleep(5000);
      flashApp.call(“setVolume”,”50″);
      System.out.println(” Executing setVolume to 50 function “);
      Thread.sleep(5000);
      System.out.println(” Closing Browser”);
      driver.close();
     }

}
In the above example, the methods like “Play”, “stopplay” etc were exposed by the google for youtube.
So, Finally we are out of a illusion that flash apps/flash cannot be automated.
Happy Testing . Do reach me @ illi.nainappa@gmail.com for any queries and assistance.