Printable Tutorial

Printable Watir Tutorial

This is a printable version of the Watir Tutorial created by Jonathan Kohl.

This tutorial collates the content from multiple pages in one (albeit long) page. The Table of Contents won't appear when you print this page.

Introduction

"Watir" (pronounced water) stands for "Web Application Testing in Ruby". Watir is an automated test tool which uses the Ruby scripting language to drive the Internet Explorer web browser. Watir is a toolkit for automated tests to be developed and run against a web browser.

What Does Watir Work With?

Watir will drive web applications that are served up as HTML pages in a web browser. Watir will not work with ActiveX plugin components, Java Applets, Macromedia Flash, or other plugin applications. To determine whether Watir can be used to automate a part of a web application, right click on the object and see if the View Source menu option is available. If you can view the HTML source, that object can be automated using Watir.

Prerequisites

To use the tool, you should have a basic understanding of:

  • HTML: This is a basic HTML tutorial.
  • Programming: You should understand programming basics, including variables and simple control structures like "for" loops and "if" statements.
  • Ruby: You do not need to know how to program in Ruby to get started with Watir, but you should learn some Ruby if you really want to get the most out of Watir
  • Check out the Ruby Cheat Sheet for basic Ruby information.
  • Microsoft has a toolbar for Internet Explorer which can be useful in navigating the DOM for pages that you're looking to automate. Installation instructions are here.

Installation

Watir runs on Windows machines and works with the Internet Explorer web browser, versions 6 and 7. We recommend using Ruby 1.8.5-24 or Ruby 1.8.6-26 final (or later). Watir runs on Windows 2000, XP, Server 2003 and Vista. Make sure you are logged in as Administrator while installing Ruby and Watir.

Step 1 - Install Ruby

Step 2 - Install Watir

Step 3 - Run the Watir Unit Tests (optional)

Step 4 - Install the IE Developer Toolbar (recommended)

Install Ruby

  • Log in as administrator.
  • Download the One-Click Ruby Installer for Windows (v.1.8.6-26) from the Ruby One Click Installer Page .
    We recommend using the latest version of Ruby 1.8.6 with Watir 1.6.
    Watir's modal dialog support in Watir 1.5 required Ruby 1.8.2. This is no longer true and this feature now requires Ruby 1.8.6.
  • Run it (leave all choices at the default).
  • You have installed Ruby.
  • Installing Ruby 1.9.1
     
    Install the lastest 1.9.1 RubyInstaller and development kit from here: http://rubyforge.org/frs/?group_id=167
    (at the time of writing it is this: rubyinstaller-1.9.1-p243-rc1.exe)
    Note: The Ruby path is not set by default but there is an option to set it in the installer
    Type ruby -v in the command line which should return
    ruby 1.9.1p243 (2009-07-16 revision 24175) [i386-mingw32]
    You can have >1 versions of Ruby installed, but the first that is found in the path is used.
    Download 7-zip www.7-zip.org and unzip the devkit to here C:\ruby19

     



Install Watir

Select the platform for which you are installing Watir:


Installing from behind a proxy
If you are installing from behind a proxy, be sure to add the following to the end of any gem install or gem update command:
-p http://your-proxy-server-name:your-proxy-server-port

For example, if your proxy server was named proxy and it accepted connections on port 8000, your addition to the command line would be

-p http://proxy:8000

Read the gem install documentation for more information on specifying the proxy.

 


Windows

Watir supports Internet Explorer 5.5, 6 and 7 on Windows 2000, XP, Server 2003 and Vista. Watir also supports Firefox 2 and 3.

  1. Make sure you are logged in as administrator.
  2. Open command prompt and type:
    gem update --system
    gem install watir
    
  3. Beginning with Watir 1.6.0 (Oct 2008), this installs drivers for both
    IE and Firefox (FireWatir). Output should be something like this:
    C:\Documents and Settings\Administrator\>gem install watir
    Successfully installed watir-1.5.x
    Installing ri documentation for watir-1.5.x...
    Installing RDoc documentation for watir-1.5.x...
    
  4. Watir's support for Firefox also requires a plugin.
    FireWatir Installation#InstalltheJSSHFirefoxExtension

You don't have to download the gem first. Ruby's gem system will automatically find it on the web, download it and install it. Watir's gem includes libraries, and the rdoc. It is convenient for setting up a new machine to run Watir scripts that you've already developed.

The "gem update --system" command will update the gem system itself. This is required
to install Watir gems beginning with Watir 1.5.4 (April 2008).

If you have any issues updating the rubygems system, you should update it manually before updating the watir gem. Details can be found on the FAQ Page

Mac

Type these commands at a command prompt:

sudo gem update --system
sudo gem install firewatir
sudo gem install safariwatir

Watir's support for Firefox also requires a plugin.
FireWatir Installation#InstalltheJSSHFirefoxExtension

Linux

To solve Ubuntu 8.10 gem hassle:
http://intertwingly.net/blog/2008/11/23/RubyGems-1-3-1-on-Ubuntu-8-10

Type these commands at a command prompt:

sudo gem update --system
sudo gem install firewatir

Watir's support for Firefox also requires a plugin.
FireWatir Installation#InstalltheJSSHFirefoxExtension

When you install Watir, you may get an error building the documentation for the Builder gem. You can safely ignore this error.
The unit tests don't work with the Watir 1.6 gem, as described below. Sorry.

You will need a development environment (Get the source code and unit tests from SVN) to run them. See Running Unit Tests in Development for current procedures.

Unit Tests
If you are following the Quick Start Guide, this section is not necessary to get up and running

Running the Unit Tests

After you have installed Ruby and Watir, you can run the unit tests to verify the installation.

To run the unit tests:

  • If you have installed Ruby in its default folder of "C:\Ruby" then in "SciTE" goto:
C:\ruby\lib\ruby\gems\1.8\gems\watir-1.5.x\unittests\core_tests.rb

And press "F5"

  • The tests should all run and pass.
  • If you receive any errors, try updating your gems with:
gem update

Having Problems?

If you are using Windows XP with Service Pack 2 or Windows Server 2003, several tests will fail unless you enable active content. To fix this:

  • From the browser, select Tools > Internet Options
  • Select the Advanced tab
  • Under Security, check Allow active content to run in files on My Computer
  • Click OK

There is more information on allowing active content.

Additional Problems

  • If you have the google toolbar installed, you will need to turn off the popup blocker.
  • If you are installing on a new system, you will get a dialog asking about auto-complete. You will have to answer this question before you can run the unit tests.
  • The following gems must be installed. (These are installed when you install the watir gem.)
    • activesupport
    • user-choices

To view details of elements in your web application, it is recommended to use a developer toolbar as it will provide element inspection functionality. These quickly show you the element attributes and properties you need to know to automate them with Watir.

There are two recommended packages depending on whether you prefer Internet Explorer or Firefox.

Browser Developer Toolbar
Internet Explorer IE Developer Toolbar
Firefox Firebug

Install Internet Explorer Developer Toolbar

  • Make sure you are logged in as administrator.
  • Download Internet Explorer Developer Toolbar.
  • Run it (leave all choices at the default).
  • After installing the toolbar, select Tools -> Toolbars -> Explorer Bar -> IE DOM Explorer.

Install Firebug

  • Got to get firebug using Firefox
  • Click Install Firebug
  • Click Add to Firefox
  • Follow prompts and restart Firefox to enable add on
  • Click the little bug in the lower right hand corner of Firefox
  • Click 'Inspect' then any element in your app to see its properties

Ruby Cheat Sheet

Created by Brian Marick and Bret Pettichord for Scripting for Testers tutorial.

This cheat sheet describes Ruby features. It's not a reference to the language. You do have a reference to the language: the full text of Programming Ruby: The Pragmatic Programmer's Guide is installed with Ruby. Select start -> All Programs -> Ruby -> Ruby Documentation -> RubyBook Help.

Comments

In Ruby, any text on a single line that follows a # is a comment, and is ignored by the Ruby interpreter at run time.

# comment

Function Calls

Parentheses can sometimes be omitted. If you're not sure whether they're required, put them in. To be safe, put them in whenever the call is at all complicated. Even one as simple as this.

puts "hello"
puts("hello")
assert_equal(5, number)

Variables

Ordinary (local) variables are created through assignment:

number = 5

Now the variable number has the value 5. Ordinary variables begin with lowercase letters. After the first character, they can contain any alphabetical or numeric character. Underscores are helpful for making them readable:

this_is_my_variable = 5

A variable's value is gotten simply by using the name of the variable. The following has the value 10:

number + this_is_my_variable # returns 10

Strings, Objects and Methods

Strings are sequences of text in quotation marks. You can use single or double quotes.

name = 'simon'
name = "simon"

Strings are objects in Ruby. This means that they have methods. (In fact everything in Ruby is an object.)

A method call looks like this:

"simon".upcase # returns "SIMON"

A method is a function for a particular type of object. In this case, the thing before the period is the object, in this case a string simon. The method is upcase. It capitalizes its object.

Like functions, methods can have arguments.

"bookkeeper".include?('book') # returns true

This method is true if its argument book is a substring of bookkeeper.

You can also concatenate strings using the + operator.

"dog" + "house" # returns "doghouse"

Conditionals (if)

if number == 5
  puts "Success" # "Success" is a string. Strings can be surrounded with single or double quotes. 
else
  puts "FAILURE"
end

Put the if, else, and end on separate lines as shown. You don't have to indent, but you should.

Function Definitions

def assert_equal(expected, actual)
  if expected != actual
    puts "FAILURE!"
  end
end

Functions can return values, and those values can be assigned to variables. The return value is the last statement in the definition. Here's a simple example:

def five # note that no parentheses are required
  5
end
box = five # box's value is 5

Note that we didn't need to say five(), as is required in some languages. You can put in the parentheses if you prefer.

The value of the last statement is always the value returned by the function. Some people like to include a return statement to make this clear, but it doesn't change how the function works. This does the same thing:

def five
  return 5
end

Here's a little more complicated example:

def make_positive(number)
  if number < 0
    -number
  else
    number
  end
end
variable = make_positive(-5) # variable's value is 5
variable = make_positive(five) # variable's value is 5

Libraries

Libraries contain functions or methods that can be used in many Ruby programs. Suppose we store the make_positive function defined above in a file called mathplus.rb.

To use it in another script, we must require it:

require 'mathplus'

This will cause Ruby to search its loadpath for a file named mathplus.rb. (It will automatically add the .rb.) It will search the directories that normally contain Ruby libraries, as well as the current directory (typically the same directory as your script).

If your library is in a location that Ruby doesn't know about, you will need to change the loadpath:

$LOAD_PATH << 'c:/my_lib/'

Make sure you include this line before you require libraries in it.

Arrays

This is an array with nothing in it:

[]

This is an array with two numbers in it:

[1, 2]

This is an array with two numbers and a string in it. You can put anything into an array.

[1, 'hello!', 220]

Here's how you get something out of an array:

array = [1, 'hello', 220]
array[0] # value is 1

Here's how you get the last element out:

array[2] # value is 220

Here's another way to get the last element:

array.last # value is 220

Here's how you change an element:

array[0]= 'boo!' # value printed is 'boo!'
# array is now ['boo', 'hello', 220]

How long is an array?

array.length # value is 3

Here's how you tack something onto the end of an array:

array.push('fred') # array is now ['boo', 'hello', 220, 'fred']

Iteration

When you do something multiple times, it is called iteration. There are many ways to do this. The following will print hello five times:

5.times do
  puts 'hello'
end

Here's one way to print the numbers from one to 10:

for x in 1..10 do
  puts x
end

And here's another:

(1..10).each do |x|
  puts x
end

The part between the do and the end is called a block. You can replace the do and end with braces:

(1..10).each { |x| puts x }

The 1..10 is a range, which works like an array of the numbers from 1 to 10. The each is a method that iterates through each element of the range. It is called an iterator.

This prints each value of an array:

["a", "b", "c"].each { |x| puts x }

What if you want to transform each element of an array? The following capitalizes each element of an array.

["hi", "there"].collect { |word| word.capitalize } # The result is ["Hi", "There"].

Regular Expressions

Regular expressions are a useful feature common to many languages. They allow you to match patterns in strings.

Regular expressions are characters surrounded by // or %r{}. A regular expression is compared to a string like this:

regexp =~ string

Most characters in a regular expression match the same character in a string. So, these all match:

/a/ =~ 'a string'
/a/ =~ 'string me along'

This also matches:

/as/ =~ 'a string with astounding length'

Notice that the regular expression can match anywhere in the string. If you want it to match only the beginning of the string, start it with a caret:

/^as/ =~ 'alas, no match'

If you want it to match at the end, end with a dollar sign:

/no$/ =~ 'no match, alas'

If you want the regular expression to match any character in a string, use a period:

/^.s/ =~ "As if I didn't know better!"

There are a number of other special characters that let you amazing and wonderful things with strings. Ruby uses the standard syntax for regular expressions used in many scripting languages. See Programming Ruby for more information about regular expressions.

Truth and Falsehood

If you try the examples above, you'll see that the ones that match print a number. That's the position of the first character in the match. The first expression (/a/ =~ 'a string') returns 0. (Ruby, like most programming languages, starts counting with 0.) The second returns 10.

What happens if there's no match? Type this:

/^as/ =~ 'alas, no match'

and the result will be nil, signifying no match. You can use these results in an if, like this:

if /^as/ =~ some_string
  puts 'the string begins with "as".'
end

In Ruby, anything but the two special values false and nil are considered true for purposes of an if statement. So match results like 0 and 10 count as true.

Blocks

A block is like a function without a name. It contains a set of parameters and one or more lines of code. Blocks are used a lot in Ruby. Iterators like each use blocks.

Here's how to search an array for an element:

gems = ['emerald', 'pearl', 'ruby']
gems.detect { |gem| /^r/ =~ gem } # returns "ruby"	

The detect method takes a block as an argument. This block returns true if the first argument starts with an r. (Actually it returns 0, which counts as true.) The detect method itself returns the first element for which its block is true.

When blocks are longer than one line, they are usually written using do and end. This is another way of writing the same code:

gems.detect do |gem| 
  /^r/ =~ gem 
end 

Dictionaries

A dictionary lets you say "Give me the value corresponding to key." Dictionaries are also called hashes or associative arrays.

Here's how you create a dictionary:

dict = {}

Here's how you associate a value with a key:

dict['bret'] = 'texas' # looks a lot like an array, except that the key doesn't have to be a number.

Here's how you retrieve a value, given a key:

dict['bret'] # value is 'texas'.

Here's how you ask how many key/value pairs are in the dictionary:

dict.length # value is 1

What values does a dictionary have?

dict.values # value is the Array ['texas'].

What keys does it have?

dict.keys # value is the Array ['bret'].

Expression Substitution

Expression substitution evaluates an expression within a string:

You can do this

name = "Aidy"
puts "My name is: #{name}" 

=> My name is: Aidy

And this:

puts "The sum of four times four is: #{4*4}"

=> The sum of four times four is: 16

Example Test Case

Google Test Search

This document walks through a very simple test case: Google Search. To begin, open it in a text editor. If you do not have that file, download it from here. To open it with SciTE, simply right-click the file in Windows Explorer, and select Edit from the popup menu.

The format of this example will be to show the Ruby test case scripting code in a box as you would see it in a text editor, with an explanation after it.

Getting Started

Open Internet Explorer, and try out the test case manually on your own:

  1. go to the Google home page
  2. enter pickaxe in the search text field
  3. click the Google Search button

Expected Result

A Google page with results should be shown. Programming Ruby should be high on the list.

Once you have tried the test case out manually, it's time to automate the test case using Watir. Return to the Google home page and view the page source: right mouse click > View Source. Now you can follow along and see how to automate this test with Watir based on the HTML tags in the Google search web application.

Section 1: Comments

Test cases should be commented, just as program code should be commented. In Ruby, any text on a single line that follows a # is a comment, and is ignored by the Ruby interpreter at run time.

What you see in the text editor:

#-------------------------------------------------------------#
# Demo test for the Watir controller.
#
# Simple Google test written by Jonathan Kohl 10/10/04.
# Purpose: to demonstrate the following Watir functionality:
#   * entering text into a text field,
#   * clicking a button,
#   * checking to see if a page contains text.
# Test will search Google for the "pickaxe" Ruby book.
#-------------------------------------------------------------#

Styles differ with comments, but they can really help with test case maintenance. In this case, the author has provided their name, a date and a purpose of the test case. This is here to improve readability, and to help others who may be using the test to understand what it does.

Section 2: Includes

To use Watir, or any other library in our test case, requires us to tell the program where to find the library.

What you see in the text editor:

# the Watir controller
require "watir"

When we run our test script, the Watir library is loaded so that our test cases can use it.

Section 3: Declare Variables

If we are going to use something in our script more than once, or something that could change, we can declare it as a variable and reuse it throughout the script. Some objects we can use for testing tend to change, such as URLs for applications we are testing. In this script, we assign the test URL as a variable. If it changes, we only have to change it in one place.

What you see in the text editor:

# set a variable
test_site = "http://www.google.com"

The test case author has chosen to assign the URL to a variable called test_site. It may not be much of an issue in this test case, but using variables for test URLs is often a good practice.

Section 4: Open an Internet Explorer Browser

To begin driving Internet Explorer, we need to tell Watir to open an instance for testing.

What you see in the text editor:

# open the IE browser
ie = Watir::IE.new

To explain what this is doing, we can start from the right of the = operator. We send a message new to the IE (Internet Explorer) class that is inside Watir module, and assign it to a variable called ie. The ie variable is a local variable (like test_site). This means it can be accessed from our script, but not from other Ruby functions or methods.

Section 5: Interacting With Google

Now we are ready to start automating the steps we ran manually using Watir.

Beginning the test case

What you see in the text editor:

# print some comments
puts "Beginning of test: Google search."

puts is a reserved word in the Ruby language that tells the Ruby Interpreter to print whatever comes after it contained in quotes to the screen. We could just as easily write this information to a file. These puts statements are in this test case to make it more self-explanatory. You can print to the screen as a "friendly message" (e.g. telling the user something is loading while they are waiting for results, or printing a result as "The answer is 5" instead of just "5") or as "flagging" and that is to print to the screen for debugging purposes. Printing what we are doing when we automate the test case is useful for debugging when developing test cases, and for quickly repeating failures for bug reports when the test case doesn't pass.

Step 1: Go to the Google site

This test case follows a pattern of printing out what we intend Watir to do on a web application, followed by the Watir scripting code to carry out that action. This is a style of test case development that is useful for tracking down test case failures quickly.

What you see in the text editor:

puts " Step 1: go to the test site: " + test_site
ie.goto test_site

The first line uses a puts statement to print out the test case step we are attempting to the screen. The second line uses the Watir method goto to direct the test case to the test site: http://www.google.com (stored in the variable test_site). When we print out the variable, we concatenate it to the string (the part in quotes) by using the + sign.

Step 2: Enter Search Term pickaxe in the search field

We need to enter the term to search in the text field on the Google home page.

What you see in the web browser:

What you see in the text editor:

puts " Step 2: enter 'pickaxe' in the search text field."
ie.text_field(:name, "q").set "pickaxe" # "q" is the name of the search field

The first line prints the step we are on to the screen. The second line enters the text pickaxe in the text field named q. The comment telling the user that q is the name of the text field is optional.

This is the tag in the HTML source with the name attribute we used:

<input maxlength=2048 name=q size=55 title="Google Search" value="">

The text field has a name attribute q, so we use that to tell Watir what object to interact with.

Step 3: Click the Google Search button

We need to click the search button to activate the Google Search functionality.

What you see in the web browser:

What you see in the text editor:

puts " Step 3: click the 'Google Search' button."
ie.button(:name, "btnG").click # "btnG" is the name of the Search button

The first line prints the step we are on to the screen. The second line clicks the Google Search button.

This is the tag in the HTML source with the name attribute we used:

<input name=btnG type=submit value="Google Search">

Section 6: Evaluating the Results

The Expected Result

This test case prints out what the Expected Result should be prior to the test case using Watir to evaluate the results.

What you see in the text editor:

puts " Expected Result:"
puts "  A Google page with results should be shown. 'Programming Ruby' should be high on the list."

These two statements simply print the expected result of the test to the screen.

Verify Results

Using Watir and a little Ruby, we can evaluate the results to verify whether the test case passed or failed.

puts " Actual Result:"
if ie.text.include? "Programming Ruby"
  puts "  Test Passed. Found the test string: 'Programming Ruby'. Actual Results match Expected Results."
else
  puts "  Test Failed! Could not find: 'Programming Ruby'."
end

There is a lot more in this section, but we can break it down.

  • The first line prints out the Actual Result heading to the screen.
  • The second line gets the text of the page and then calls the include? method to determine whether Programming Ruby appears on the first page.
  • Using an if statement, we evaluate whether the include? method was true or false.
    • If include? returns true (or actually anything but false), the text Programming Ruby appears. The test case passes and we print the Test Passed. message.
    • Else, if include? returns false, the text Programming Ruby does not appear. The test case fails and we print the Test Failed! message.
  • We close the conditional if section with an end statement.

End of Test Case

What you see in the text editor:

puts "End of test: Google search."

Prints message to the user that the test case has ended.

Developing Test Cases

The goal of this user guide is to help you get started writing test cases quickly. Each section describes the methods for driving a web application. Select the ones you need for each page of your web application based on the content of each page in the application.

Plan what you need to get Watir to do before you begin scripting. Open your web browser with the application under test in front of you, and pay close attention to the objects on that page. What text fields require entries? What buttons need to be pushed? What links need to be clicked on? It sometimes helps to write out the steps it will take to exercise a test first, and then filling in the Watir scripting code to satisfy each of those steps.

To start developing a test:

  • Open your text editor.
  • Name your test file with a .rb (Ruby) extension (like test.rb).
  • Provide your new test file with access to the Watir tool by entering this statement at the beginning of your test script:
require 'watir'
  • Open Internet Explorer and navigate to the application you wish to test.
  • Interact with it to design your test case.
  • Type the corresponding Watir methods into your test script.
  • Verify the results.

Internet Explorer Developer Toolbar

Microsoft has an extension for Internet Explorer (link does not work with Firefox) that is a great addition to any tester's toolkit and is a great help when scripting web pages using Watir. This works on the DOM in the same manner that Watir does. You can explore the DOM, find elements by clicking on them and more. It's a highly recommended tool to use while writing Watir scripts.

The Internet Explorer Developer Toolbar provides several features for exploring and understanding Web pages. These features enable you to:

  • Explore and modify the document object model (DOM) of a Web page.
  • Locate and select specific elements on a Web page through a variety of techniques.
  • View HTML object class names, ID's, and details such as link paths, tab index values, and access keys.
  • Outline tables, table cells, images, or selected tags.
  • Display image dimensions, file sizes, path information, and alternate (ALT) text.
  • Selectively clear the browser cache and saved cookies. Choose from all objects or those associated with a given domain.
  • Find the style rules used to set specific style values on an element.
  • View the formatted and syntax colored source of HTML and CSS.
  • Style Tracer: Right mouse click on a style value for an element and select Style Tracer to find the style rule that is effecting that value.
  • View Source: View the formatted and syntax colored source of the original page, currently rendered page, element or element with the styles that are effecting it.

To use this extension, in IE6 you can turn it on through the View Menu > Explorer Bar > IE DOM Explorer. In IE7, it's under the Tools icon > Toolbars > Explorer Bar > IE DOM Explorer.

Navigate to Google Search, and you should see something like the following.

In this case you can see the name attribute of the field to use in your scripts. Watir can use different attributes of a tag to manipulate that object, so it is important to know what they are. In some cases the attributes are not explicit in the tag such as the text attributes.

Interacting With a Web Page

You will notice we've chosen to name the variable name ie used in Watir test scripts for the Internet Explorer browser. You could call it whatever you wish, but we use ie for ease of use. This variable tells the Watir library to exercise test scripts against an instance of the Internet Explorer web browser.

In Ruby, think of programming in terms of objects and messages. Watir was also developed with objects and messages in mind. If you think of the ie variable as an object, you can send messages to it. Think of objects as nouns. When you start up Internet Explorer, the operating system starts the program which creates an instance of the Internet Explorer web browser. You refer to this Internet Explorer browser instance as a thing. If you send a message to that object, it will respond to that message if it recognizes it.

Think of the messages as verbs. In Ruby, you send a message to an object by separating the object you are calling from the message you are sending to it with a dot. For example:

dog.bark

would tell the object dog that it must bark.

This isn't very specific though. What dog should bark? In the Watir world, you could identify the test area to be our yard. Like ie, treat it as an object with attributes containing other objects with attributes. For example, in our yard, there are two dogs: Heidi and Megabyte. Each of these dog objects have attributes that identify them. They have names, breeds, shapes and sizes and colors. To be more specific, and interacting with them the Watir way, you could send the message bark to the dog Heidi like this:

yard.dog(:name, "Heidi").bark

This says in Watir syntax: in the yard, identify the dog Heidi by her name attribute, and send her the bark message. The expected outcome would be Heidi responding to the message by barking.

When you develop test scripts with Watir, you interact with objects on a web page by sending them messages. Like the yard example, the Internet Explorer browser itself contains objects. You can access these objects within an Internet Explorer browser instance by identifying them by different attributes. Just like in the dog example, above, you must be very specific when you send messages to objects on a web page. You must also be able to identify objects on a web page by using a variety of different attributes due to the diversity in how tags are declared by different application developers. With Watir, identify objects and send them messages by using the dot notation. For example:

ie.button

narrows down the type of object to send a message to.

ie.button(:value, "Click Me").click

identifies the object on the page as a button within the instance of Internet Explorer (ie) that has the value attribute (caption) Click Me. When you send the message (the verb) click, Watir interprets and tells Internet Explorer to click.

Watir Syntax

The Watir syntax is shown later with three views. One is the view that we see objects on a web page while viewing them in a web browser. The next view is an example of the Watir code that would be needed to automate an action using that web page object. The third view is the object on the web page shown in its HTML form. This is the way it looks when we view the source of a web page, or open the file in a text editor.

Require the Watir Tool

To use the Watir tool, first enter the following in your test script:

require 'watir'

This allows our test script to use the Watir tool.

Create a Test Instance of Internet Explorer

To create a test instance of Internet Explorer, enter the following in your test script:

ie = Watir::IE.new

Watir sends a message to Internet Explorer, telling to create a new instance of itself, and assigns that instance to ie.

To create an instance of Internet Explorer and navigate to the site with one statement:

ie = Watir::IE.start("http://mytestsite")

Watir uses the start method to both create a browser instance and navigate to a site.

Site Navigation

To direct your test script to the web application you are testing, enter the URL in this command:

ie.goto("http://mytestsite")

In the example above, enter in your application's URL in place of mytestsite.

Watir sends the goto message to Internet Explorer, telling it to enter the address you entered as a method argument in the Address bar, and to direct the browser to that site.

Buttons

In web applications, we generally submit information we have entered or selected in the web page by clicking links, buttons and images, or by hitting Enter/Return on our keyboard.

Watir clicks buttons on a web page by looking at the attributes available in the <button>, <input type="button">, <input type="image">, <input type="reset">, and <input type="submit"> HTML tags. Common attributes are id, name and value. For complete list see HTML Elements Supported by Watir.

HTML Buttons

What you see in the web browser:

This is the tag in the HTML source:

<input type="button" id="one" name="clickme" value="Click Me">

id Attribute

This is the Watir code you need to click a button using the id attribute:

ie.button(:id, "one").click

name Attribute

This is the Watir code you need to click a button using the name attribute:

ie.button(:name, "clickme").click

value Attribute

This is the Watir code you need to click a button using the value attribute:

ie.button(:value, "Click Me").click

Image Buttons

<input type="image"> tag looks like an image, but acts like a button. Like HTML buttons it can be accessed by id, name and value attributes. Image buttons can also be accessed by their src attribute.

src Attribute

What you see in the web browser:

This is the tag in the HTML source:

<input type="image" src="images/doit.gif">

This is the Watir code you need to click a button with an image using the src attribute as a regular expression:

ie.button(:src, /doit/).click

In this case we're looking for a button with doit as part of the src attribute.

Checkboxes

Watir sets or clears checkboxes by looking at the attributes available in the <input type="checkbox"> HTML tag. Common attributes are id and name. For complete list see HTML Elements Supported by Watir.

What you see in the web browser:

Check Me:

This is the tag in the HTML source:

Check Me:<input type="checkbox" id="one" name="checkme">

id Attribute

Watir code to set a checkbox using the id attribute:

ie.checkbox(:id, "one").set

Watir code to clear a checkbox using the id attribute:

ie.checkbox(:id, "one").clear

name Attribute

Watir code to set a checkbox using the name attribute:

ie.checkbox(:name, "checkme").set

Watir code to clear a checkbox using the name attribute:

ie.checkbox(:name, "checkme").clear

Links

You can use Watir to click links in a variety of ways. Watir can click links by looking at the link text you see in the browser or by looking at the attributes available in the <a> HTML tag. Common attributes are id, name and href. For complete list see HTML Elements Supported by Watir.

Here is an example using a link to the Pickaxe book by the Pragmatic Programmers:

What you see in the web browser:

Pickaxe

What you see in the HTML source:

<a href="http://pragmaticprogrammer.com/titles/ruby/" id="one" name="book">Pickaxe</a>

id Attribute

Watir code to click a link using the id attribute:

ie.link(:id, "one").click

name Attribute

Watir code to click a link using the name attribute:

ie.link(:name, "book").click

Text

Watir code to click a link using link's text:

ie.link(:text, "Pickaxe").click

href Attribute

Watir code to click a link using the href attribute:

ie.link(:href, "http://pragmaticprogrammer.com/titles/ruby/").click

Radio Buttons

Watir sets or clears radio list items by looking at the attributes available in the <input type="radio"> HTML tag. Common attributes are id and name. For complete list see HTML Elements Supported by Watir.

What you see in the web browser:

Click Me:

This is the tag in the HTML source:

<input type="radio" name="clickme" id="one">

id Attribute

Watir code to set a radio list item using the and id attribute:

ie.radio(:id, "one").set

Watir code to clear a radio list item using the id attribute:

ie.radio(:id, "one").clear

name Attribute

Watir code to set a radio list item using the name attribute:

ie.radio(:name, "clickme").set

Watir code to clear a radio list item using the name attribute:

ie.radio(:name, "clickme").clear

Selection Boxes

Watir sets or clears an item in a selection box (or dropdown box) by looking at the attributes available in the <select> HTML tag. Common attributes are id and name. For complete list see HTML Elements Supported by Watir.

What you see in the web browser:

This is the tag in the HTML source:

<select id="one" name="selectme">
  <option></option>
  <option>Web Testing</option>
  <option>in Ruby</option>
  <option>is fun</option>
</select>

id Attribute

Watir code to set a select box item using the id attribute:

ie.select_list(:id, "one").set("is fun")

name Attribute

Watir code to set a select box item using the name attribute:

ie.select_list(:name, "selectme").set("is fun")

Selection Box Methods

Watir code to clear a select box item using the id attribute:

ie.select_list(:id, "one").clearSelection

Watir code to get the contents of a select list:

contents = ie.select_list(:id, "one").getAllContents

NOTE: contents will be an array

Select Multiple

Some select lists can have multiple selections instead of just one. If multiple items can be selected in select box, Watir can set or clear an item.

What you see in the web browser:

This is the tag in the HTML source:

<select id="one" name="selectme" multiple="multiple">
  <option></option>
  <option>Web Testing</option>
  <option>in Ruby</option>
  <option>is fun</option>
</select>

You can set individual options using successive _set_s and you can clear everything that is selected with the clearSelection method. The following code would select every option in the select list and then clear everything.

ie.select_list(:id, 'one').set('Web Testing')
ie.select_list(:id, 'one').set('in Ruby')
ie.select_list(:id, 'one').set('is fun')
ie.select_list(:id, 'one').clearSelection

Text Fields

Watir sets or clears a text field by looking at the attributes available in the <input type="text"> HTML tag. Common attributes are id and name. For complete list see HTML Elements Supported by Watir.

What you see in the web browser:

This is the tag in the HTML source:

<input type="text" id="one" name="typeinme">
There is also a file upload element that looks exactly like a text_field with a "Browse" button to the right. For directions on how to interact with this control, see File Uploads page.

id Attribute

Watir code to set the text field with the string Watir World using the id attribute:

ie.text_field(:id, "one").set("Watir World")

Watir code to clear a text field using the id attribute:

ie.text_field(:id, "one").clear

name Attribute

Watir code to set the text field with the string Watir World using the name attribute:

ie.text_field(:name, "typeinme").set("Watir World")

Watir code to clear a text field using the name attribute:

ie.text_field(:name, "typeinme").clear

Forms

Forms aren't visible through the browser, but are used a lot in web applications. To find them, look at the HTML source for <form> tag. Watir can submit forms in a variety of ways.

Forms With Buttons

Watir can submit buttons on a web page contained in a form by looking at the attributes available in the <input type="submit"> HTML tag. Common attributes are id, name and value. For complete list see HTML Elements Supported by Watir.

What you see in the web browser:

This is the tag in the HTML source:

<form>
  <input type="submit" id="one" value="Submit" />
</form>

id Attribute

This is the Watir code you need to click a button that will submit a form using the id attribute:

ie.button(:id, "one").click

Forms With No Buttons

There may be input fields on a web page, but no button to submit. Instead, they will allow you to hit Enter/Return on your keyboard. When there is no button to submit the data, we can just submit the form itself.

Watir can submit a form by looking at the attributes available in the <form> HTML tag. Common attributes are id, name, action and method. For complete list see HTML Elements Supported by Watir.

What you see in the web browser:

This is the tag in the HTML source:

<form  id="one" name="loginform" action="login" method="get">
  <input />
</form>

id Attribute

Watir code to submit the form using the id attribute:

ie.form(:id, "one").submit

name Attribute

Watir code to submit the form using the name attribute:

ie.form(:name, "loginform").submit

action Attribute

Watir code to submit the form using the action attribute:

ie.form(:action, "login").submit

method Attribute

Watir code to submit the form using the method attribute:

ie.form(:method, "get").submit

Frames

Many web applications use frames. If you are having trouble accessing objects on a web page, be sure to check to see if the application is using frames. To find out, view the source of the page and look for <frame> or <iframe> HTML tags. It will look something like this:

<frameset cols="*,*">
  <frame src="menu.htm" name="menu">
  <frame src="main.htm" name="main">
</frameset>

In the HTML above, we have a menu frame on the left and a main frame on the right.

You can use Watir to find out if your page has frames:

ie.show_frames

This is a good method to use with IRB. It prints out the index and the name of the frames in the current page. Like this:

irb(main):009:0> ie.show_frames
there are 2 frames
frame  index: 1 name: menu
frame  index: 2 name: main
=> 0..1

Watir allows access to frame objects by identifying them by the attributes available in the <frame> HTML tag or by frame's index. Common attributes are id, name and src. For complete list see HTML Elements Supported by Watir.

name Attribute

Watir code to access a frame using name attribute:

ie.frame(:name, "menu")

To access individual objects within that frame, you prefix the object using the Watir code above. If we had a link in the menu frame:

<a href="index.htm">Click Menu Item</a>

we could click it like this:

ie.frame(:name, "menu").link(:text, "Click Menu Item").click

Nested Frames

Sometimes a web page that is referenced by the <frame> tag is also a page that contains a <frameset> tag. This is a nested frame. To deal with this, simply access the nested frame like this:

ie.frame(:name, "frame").frame(:name, "nested_frame")

Why do I get an access denied error when trying to access a frame?

This error message is due to Internet Explorer's attempt to prevent cross-window domain scripting (also known as cross-site scripting, or XSS).  For security reasons, IE prevents embedded code in one frame from accessing another if the frame contents come from different domains. Watir runs into the same barriers when you attempt to navigate from a page hosted from one site to a frame hosted by another.

You may try one or more of the following methods to resolve this issue:

  1. Navigate directly to the subframe (and the server that hosts it).  That is, instead of having your script click on the link, use ie.goto("http://www.thenewsite.com/framecontents.html").
  2. Add the particular host to the Internet Explorer Trusted Sites list.  From IE's menu bar, choose Tools / Internet Options; click on the Security tab; click on the Trusted Sites icon; click on the Sites... button; type the name of the site into the field labelled "Add this Web site to the zone:".  You may need to uncheck the box labelled "Require server verification ( https: ) for all sites in this zone."  Click OK to finish the process.
  3. Create an alias in the hosts file.  This text file is typically in the folder c:\windows\system32\drivers\etc.  Add a line in the form
        192.168.10.32 foosystem
        

    Replace 192.168.10.32 with the IP address of the host that is serving up the frame contents.  Then access the frame using https://foosystem/testsystem.

  4. Set Internet Explorer to its lowest possible security setting.  From IE's menu bar, choose Tools / Internet Options; click on the Security tab; click on the Default Level button, and slide the slider to the Low setting; then click on OK to finish the process.

Watir 1.4 If none of these work, and you are still getting annoying error messages about Access Denied when your scripts run, you can turn off these warnings. 

ie.logger.level = Logger::ERROR
    

Microsoft Reference: For background information about the security rules that cause this problem, see About Cross-Frame Scripting and Security

Finding Page Elements

Not all HTML tags will look the same. If you have difficulty getting Watir to interact with an object on your web page, try the Watir method with different attributes. The tag may come with one attribute, or it may come with several. If you still have trouble, see if the developers will add a id attribute to the offending tag.

Choosing Attributes

If you are having difficulty getting Watir to interact with an object, try using the method with different tag attributes. Tag declarations in HTML are varied. Some developers use tools that generate HTML, and there are many variations on tag attributes. Watir is very flexible and offers several variations on each method. There are also attributes that are part of the DOM within Internet Explorer. Anything the DOM can see, you can access using Ruby. If you have exhausted the attributes on a tag and Watir still won't interact with it, send an email to the Watir General Google Group. Please read Support before posting. The Watir development team will help out, and if needed, add support for that situation within Watir.

Accessing Tags Using Alternate Methods

In some situations, you may not know what the tag attributes of an HTML object are. They may be missing, or the tag attributes might be dynamically generated. Some web architectures dynamically generate tags, and the attributes might change each time you run a test. To work around this, try the following:

CSS

Watir supports div tags. Some web applications use one div for one state of the application, and another for a different state (such as error or success messages). Watir can check the status of the div to allow for tests on pages using CSS as part of the application.

Check out the unit test css_test.rb for usage.

Index

Elements on a web page can be accessed by where they appear on a page. If an element you want to interact with always appears in the same place, you can access it by a one-based index. Here's an example using a radio list:

What you see in the web browser:

Radio 1:
Radio 2:
Radio 3:

Watir code to set the first radio list item using its index:

ie.radio(:index, 1).set

Watir code to clear the second radio list item using its index:

ie.radio(:index, 2).clear

IRB

Use Ruby's Interactive Command Interpreter to test out script ideas. You can try out test script ideas interactively with irb.

To start IRB on Windows, select start > Run... and type irb in the Open field. Click OK, and a DOS console should open with a command prompt that looks like this:

irb(main):001:0>

Use the Watir library and enter commands to start driving a web browser interactively:

irb(main):001:0> require 'watir'
=> true
irb(main):002:0> ie = Watir::IE.start "http://www.google.com/"

Or, attach IRB to an existing browser instance using IE.attach or IE.find:

ie = Watir::IE.find(:title, "Google")                 #find by window title
ie = Watir::IE.find(:url, "http://www.google.com")    #find by url
ie = Watir::IE.find(:title,/REGEX/)                   #find by title matching REGEX
ie = Watir::IE.find(:title,//)                        #attach to any current IE instance

Use IRB to Find Page Objects

To find out what objects are on a page you are writing a test script for, use IRB to get instant feedback.

The show_all_objects method is a useful way to identify the attributes of objects you will need to use in a test script.

irb(main):003:0> ie.show_all_objects
-----------Objects in page -------------
text name=test_text id= 11 value= alt= src=
submit name=test_button id= 12 value=Click Me alt= click src=

The objects on the page are shown with their attributes such as name, id, value, alt, src. You can use these attributes to uniquely identify the objects needed for a test script. In our example above, we have two objects. A text field named test_text and a button (submit) named test_button.

The flash method can be used to test whether you have identified the object correctly. The flash method causes an object in the web browser to flash yellow ten times.

irb(main):004:0> ie.text_field(:name, "test_text").flash
=> nil

This would cause the text field with the name attribute test_text to flash yellow ten times. This is an effective way of testing whether you have identified the right object, and if you have used the right attribute. Using this in IRB is a quick way of finding out what objects can be used in a test script before commiting the script to a file.

Why does my code work in IRB but not in my .rb script?

If your code works when you enter it by hand in IRB but fails when you run your ruby script, the usual suspect is timing - perhaps the next element you want to manipulate is not manipulable yet when your snappy script moves on to the next step. Try putting a sleep in to see if that's the problem. If it is, which is often the case, then you can use wait_until{} to verify the presence of a control, text, etc.

How can I save typing in IRB?

If your scripts use classes you can load them in IRB using the "load" command. Consider the following class:

class Dog
  def bark
    puts "woof woof!"
  end
end

Then, in order to use this in IRB, type the following:

irb(main):001:0> load 'dog_class.rb'
=> true
irb(main):002:0> puppy = Dog.new
=> #<Dog:0x2bbc1bc>
irb(main):003:0> puppy.bark
woof woof!
=> nil


TIP: IRB sessions can be saved by customizing your .irbrc file


Multiple Attributes

I have more than one object of the same name. How do I commit an action on anything but the first one?

Lets imagine we have two 'Employees' links. This will click the first link that is found on the page:

$ie.link(:text, 'Employees').click

Use this syntax for the second (or more)

$ie.link(:text => 'Employees', :index  => 2).click

Regular Expressions

Watir supports regular expressions in method calls.

Here is an example using the link method to click a link using the url attribute:

ie.link(:url, /shtml/).click

This will click the link that matches shtml.

How do I use regular expressions for object recognition?

Watir allows the tester to use Regular Expressions for object recognition instead of using the full string literal. This is useful for HTML objects that are dynamically created.

For example in my WebSphere application we may have a link with this URL

    $ie.link(:url, "javascript:PC_7_0_G7_selectTerritory('0',%20'amend')").click
    

However this: 'PC_7_0_G7_' will change dependant on the environment.

With RegEx we could find that link by doing :

    $ie.link(:url, /selectTerritory\('0',%20'amend'\)/).click
    

or this

    $ie.link(:url, /javascript.*selectTerritory\('0',%20'amend'\)/).click
    

note: '.*' will match any character or digit any number of times.

RegEx contains special characters that need to be escaped. For example here ')' we use the backward slash to escape a closing bracket.

To find out what characters need to be escaped, go into irb, then enter

    Regexp.escape "javascript:PC_7_0_G7_selectTerritory('0',%20'amend')"
    

the escape sequences will be returned

    => "javascript:PC_7_0_G7_selectTerritory\\('0',%20'amend'\\)"
    

note: use only one backslash; we are shown two, because they are escaped within a string,

aidy

XPath

Created by Angrez Singh.

What is it?

XPath for Watir supplies a more powerful way to identify page elements in a Watir script. The more powerful way uses XPath expressions to identify specific elements of interest in the page.

Why is it required?

The attributes that Watir provides for identifying the HTML elements on the page are sometimes not sufficient enough to identify element(s) on the page especially if you are testing non-trivial real world web applications. XPath is well established and powerful query language for XML documents. It is trivial to clean HTML and convert it into XHTML such that we can use powerful query language XPath for identifying the element structurally on the page. XPath empowers user to generate scripts which are more generalized and less brittle.

For example, if you have the following HTML:

<table>
  <tr>
    <td><img src="1.jpg">First Image</td>
  </tr>
</table>
<table>
  <tr>
    <td><img src="2.jpg">Second Image</td>
  </tr>
</table>
<table>
  <tr>
    <td><img src="3.jpg">Third Image</td>
  </tr>
</table>

Now you want the text of <td> tag which has image with source 3.jpg. This is called structural addressing where you try to find out the element with respect to some other elements that may be above or below the element of interest, based on the tree structure of HTML that will be shown on the browser.

Now if you want to try this using Watir (without XPath), then the code might be as follows:

ie.tables.each do |t|                      # since you don't have ID's, look at every table
  for i in 1..t.row_count                  # for every row in this table
    t[i].each do |cell|                    # for every column in this row, look at its contents
      if cell.image(:src, /3.jpg/).exists? # if true, this is your cell
        puts cell.text
      end
    end
  end
end

On the other hand XPath is a very powerful mechanism for identifying the element structurally on the page.

If you try to access that element using Watir with XPath the code will be:

puts ie.cell(:xpath, "//img[@src='3.jpg']/../").text

In both cased the output will be

Third Image

What should I have before using XPath-Watir?

If you have the latest Ruby and Watir, you are fine.

If not, you should have at least:

How to use XPath in test script?

All commonly used HTML elements for testing has been provided with a new attribute in Watir called xpath for identifying them using an XPath query. This attribute is provided for most of the elements except for frame. All you have to do is to provide XPath query as second argument with this attribute and get the element.

For example:

ie.select_list(:xpath, "xpath query")

Example Code

If you want to get text from this link:

<a href="test.htm">click me</a>

you can use this code:

ie.link(:xpath,"//a[@href='test.htm']/").text # => "click me"

The Watir class that you use for identifying the element using XPath (link in above example) should match with the element that you are trying to access. Now you can use any of the methods or properties that are exposed by Watir for Link element.

What to do for elements not having class in Watir?

You can use element_by_xpath function of IE class to get the underlying ole_object. Then you can invoke any method supported by that element.

Example Code

Suppose you have a map and you want to click an area. As Watir don't have any class for map or area, directly use element_by_xpath function to get underlying ole_object.

HTML code:

<html>
  <body>
    <map name="chart">
      <area shape="poly" coords="150,16,159,17,168,20,175,25,182,32,150,56,150,56" >
      <area shape="poly" coords="182,32,188,43,190,56,150,56,150,56" href="PieChart.html?category=Critical&pieIndex=0">	
    </map>
  </body>
</html>

Watir code:

# get the underlying object and execute click method
ie.element_by_xpath("//area[contains(@href , 'PieChart.html')]/").click

Limitations

There is no support for frames, however the existing functionality that Watir provides will remain. That is you can access frames using the attributes that Watir provides but you can't use xpath attribute for accessing frames.

How it is implemented?

XPath support is added using REXML. We retrieve source HTML from the IE DOM model, which is then cleaned and converted into XHTML. Cleaned XHTML output is passed to the REXML parser. XPath supplied by the user is resolved locally using REXML to get the complete path of element(s) from the document root. We then traverse element's complete path over IE DOM using series of COM calls and return the requested element.

  1. Get the source HTML from the IE DOM model.
  2. Clean the HTML source and convert it to a valid XHTML.
  3. Pass the cleaned XHTML as input to REXML.
  4. Resolve the XPath expression locally using REXML and get the complete path of the element(s).
  5. Traverse the element's complete path over IE DOM using series of COM calls and return the requested element.

Code Design

rexml_document_object

Function returns the REXML document object.

create_rexml_document_object

This is a private function and is called only if REXML document is not created before for that HTML page. This function is called internally by rexml_document_object by checking the variable rexmlDomobject which gets set to nil when new page is rendered in the browser. If you execute multiple XPath queries on the same source page, then the object is created once on first request and reused hence forth.

elements_by_xpath(XPath)

This function resolves the XPath query, provided by the user and returns all qualified elements. The XPath query should be compatible with REXML i.e. it should contain only those attributes or functions that are supported by REXML. The function gets the complete path from the root element for all qualified elements locally using REXML. Now this path is passed to elements_by_absolute_xpath and finally qualified elements are returned back to the caller.

element_by_absolute_xpath(XPath)

This is the private function that maps the element's complete path (passed XPath) to actual element in IE DOM tree. It traverses over the IE DOM starting from the <body> tag following the passed complete path. We call IHtmlElement::getChildNodes function to get all the child nodes and select the one of our interest as indicated by the complete path. We loop till we have traversed the complete path and finally desired element is returned back.

html_source(element, htmlString, spaceString)

This function traverses the IE DOM model and creates a string that contains the HTML displayed on the browser. Same as you see with view source option when you right click on the browser. This function is initially called with element as body. During processing the function gets all the attributes of the element using IHtmlElement::outerHtml. Then the attributes of element are cleaned. If element can't have child nodes then the tag is made as self closing tag, else we just close the tag. Then this function is called recursively on the child nodes of this element. While unwinding the stack created during recursion we again check if element can have child nodes if yes then we place a closing tag that was left opened else we simple return. Script and comments tags are not taken into consideration.

tokenize_tagline(outerHtml)

This function scans the outer HTML of the element and returns an array of tokens. Token could be either tagName or "=" or attribute name or attribute value. Attribute value could be either quoted string or single word.

Input:

<input type=radio name=WATiR checked>

Output: An array with values.

{'input', 'type', '=', 'radio', 'name', '=', 'WATiR', 'checked'}

all_tag_attributes(outerHtml)

This function is called by HTML source function to get all the attributes of the tag. This function calls tokenize_tagline to separate attributes name and value. Now this function cleans the outer HTML by placing quote around the attribute values. If only attribute name is present then it attribute value is set to same as attribute name.

Input:

<input type=radio name=WATiR checked>

Output:

<input type="radio" name="WATiR" checked="checked">

xml_escape

This function is used to escape the characters that are not considered as valid data in XML. For eg: &, <, >, ", etc.

More information on REXML

The XPath that is returned by REXML is of the format:

/html/body/table/tbody/tr[2]/td[2]/div/table/tbody/tr[3]/td[1]/a[2]

The XPath string returned by REXML provides information about the location of the element from the root element for which XPath query is given.

For e.g.:
If the above provided string is returned as a result then it means that the element resides inside HTML (root element), body tag inside html (element1 inside element2: this means element2 tag inside element1 tag obtained in previous step), table tag inside body, tbody tag inside table, second tr tag inside tbody, second td tag inside row, div tag inside td, table tag inside div, tbody tag inside table, third tr tag inside tbody, first td tag inside tr, second a tag inside td.

Future Enhancements

Tweak the code of REXML to get the position of element with respect to parent. REXML code can be tweaked provided TIDY doesn't mess with the ordering of the tags. This will avoid series of COM calls required for iterating over children, we can directly jump to intended child via index.

More information

XPath and WATiR article at Angrez's blog.

Validating Test Results

How do we tell whether the test passed or failed? It is good practice to use a verification point in your test case.

To create a valid test case, we need to use some sort of validation. It isn't enough to have a sequence of events without validation in a test script. Watir can check the state of objects in the Internet Explorer DOM, and can check to see if a page contains the objects that are expected for the test to pass.

Object Exists

A simple verification point is to use the Watir method contains_text.

In our test, imagine we have gone through a sequence of steps to reach the desired point. This is a web page that contains the following text:

Reached test verification point.

Our test will pass if this is what is displayed on the page at our verification point.

Watir code to check that the text exists on the web page is contains_text method:

ie.contains_text("Reached test verification point.")

We will need to add some scripting code to validate that this occurred. Scripting code to let us know whether the test passed or not:

if ie.contains_text("Reached test verification point.")
  puts: "Test passed. Page contains the text: Reached test verification point."
else
  puts: "Test failed! Page didn't contain text: Reached test verification point."
end

This is what the scripting code above does:

  • checks if there is text Reached test verification point.
  • if true, print our passing message to the screen
  • if false, print our failure message to the screen
  • end our if block

Test Unit

This is the simplest usage of Watir and Test::Unit that I could think of. You do not have to install anything, Test::Unit is included in Ruby.

require 'test/unit'
require 'watir'

class GoogleHomePage < Test::Unit::TestCase
  def test_there_should_be_text_About_Google
    browser = Watir::IE.start "http://www.google.com" 
    assert(browser.text.include?("About Google"))
  end
end

If you run this code, you should see something like this.

C:\Documents and Settings\limited\Desktop\branches_test_unit>test_unit.rb
Loaded suite C:/Documents and Settings/limited/Desktop/branches_test_unit/test_unit
Started
.
Finished in 1.687 seconds.

1 tests, 1 assertions, 0 failures, 0 errors

Using Test::Unit Assertions

Using xUnit assertions can be a more powerful way of validating test results.

Ruby has an xUnit framework called Test::Unit that we can use with Watir. Look at the Watir Examples and unit tests for executable examples. To use Test::Unit in your test scripts, enter the following in your test script:

require 'test/unit'

Create a Test Instance

We create a new class for our test suite which is inherited from the Test::Unit TestCase class.

class TC_myTest < Test::Unit::TestCase
  # fill in Test Case methods here
end

Create a Test Case Method

Within our test case class, we need to declare test cases as methods like this:

def test_myTestCase
  # fill in method body with Watir code and assertion here
end

Test case method names must be prefixed with the word test.

When we run the test script from the command line, Test::Unit uses reflection to go through our test class and execute all the test cases declared in it. The runner by default executes the test cases alphabetically, so if you need to chain test cases, prefix letters from the alphabet or numbers after the test prefix to force them to run in order. ex. test_a_mytest.

Note: If you use numbers in your method names, note that 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12 will be executed in this order: 1, 10, 11, 12, 2, 3, 4, 5, 6, 7, 8, 9. Instead, use this format: 01, 02, 03, 04, 05, 06, 07, 08, 09, 10, 11, 12. ex. test_01_mytest, test_02_mytest, test_03_mytest will run in the order expected.

The test case class with test cases defined will look like this:

class TC_myTest < Test::Unit::TestCase
  def test_ myTestCase
    # Watir code and assertion here
  end
  def test_anotherTestCase
    # Watir code and assertion here
  end
  def test_aTestCase
    # Watir code and assertion here
  end
end

Use Assertions

Watir can support assertions by wrapping Watir methods within an assert:

assert(ie.contains_text("Reached test verification point.")

Watir can test for many different states of objects. We can use assertions to check of objects exists, are enabled or disabled, or any other state that the DOM tells the web browser about an object.

If you would like to chain test cases in a single Test::Unit class, and use one Internet Explorer instance, use either a class variable @@ie, or a global variable $ie. This allows the test script to use the same Internet Explorer instance for all the test cases.

Note: use global variables with caution.

Setup and Teardown

The method names setup and teardown are reserved for Test::Unit. If you would like to use setup and teardown functionality, simply use those as method names for the actions you want executed before and after executing each test case.

def setup
  # fill in code that will run before every test case here
end
def teardown
  # fill in code that will run after every test case here
end

Why are my test cases running in the wrong order?

Subclassing Test::Unit::TestCase will make your tests run in alphabetical order. Therefore in the case of this code:

class SampleTest < Test::Unit::TestCase
  def test_login
    # login test code, etc
  end

  def test_account
    # account test code, etc
  end
end

The second test, test_account, will run before test_login.

To run the tests in the order they are defined in the suite, subclass Watir::TestCase instead.

class SampleTest < Watir::TestCase
  def test_login
    # login test code, etc
  end

  def test_account
    # account test code, etc
  end
end

For more information see Test-Unit Patch page.

How to run a specific test case?

ruby my_test_file.rb --name test_account

RSpec

The Rspec nomenclature has progressed beyond xUnit.

Test => Example
Marick suggests we use the term 'example' instead of 'test' to emphasise the design and documentation aspect of the artifact.

Assertions => Expectations
Assertions is too strong a word for examples when we are describing what should happen.

require 'watir'
require 'spec'

Watir::Browser.default = 'firefox'

describe "a simple demonstration of watir and trad RSpec" do
  before(:each) do
    @browser ||= Watir::Browser.new
    @browser.goto("http://cukes.info/")
  end

  describe "that we have hit a valid URL" do
    it "should not return an invalid error message" do
      @browser.text.should_not include('The requested URL could not be retrieved')
    end
   end

  describe "the contents of the cukes page" do # the describe() is an example group
    it "should include aidy's name" do # the it() represents the detail that will be expressed in the code within the block
      @browser.text.should include('Aidy Lewis')
    end

    it "should not include the great Nietchzche's name" do
      @browser.text.should_not include('Frederick Nietchzche')
    end
  end

 after(:each) do
   @browser.close unless @browser.nil?
 end
end


# run with
# spec -c filename.rb

Location

Looking for more information on Watir? Watir's classes and methods are all documented in Watir's RDoc pages.

Using RDoc

On the top of the webpage for Watir's RDoc page, there are 3 lists for the files that are a part of Watir (on the left), the Classes that are a part of Watir (middle) and the methods that are a part of Watir (right).

Most of Watir's methods are in the Watir::IE class or any of the other supported Elements (like Watir::Link).

Example

Say you wanted to learn more about how Watir handles tables. Clicking on the Watir::Table class in the top middle column brings you to the RDoc page for this class. You will see the several methods available for tables including the helpful column_count, column_values, row_count, row_values and each methods. Scrolling down to the each method you will see:

Following the "Table Row" link will show you more information about the Table Row objects that Watir's Table class each itterator returns. Incidentally, if you looked up the each method for Table Row class, you would see that this yields a collection of Cell objects.

Tips and Tricks

Running Tests With the Browser Not Visible

Run the tests with a -b option if you don't want the browser to be visible. Example:

my_test.rb -b

You can also hide the browser window without using the -b flag. Example:

$HIDE_IE = true
ie = Watir::IE.new()

Running a Test Concurrently

To run a test concurrently, check out concurrent_search.rb in the examples directory for an example.

How do I get the version numbers of Ruby and Watir?

Go to command prompt.

For the Watir version type:

ruby -e 'require "watir"; puts Watir::IE::VERSION'
    

For the Ruby version type:

ruby -v
    

How to keep command prompt window open after tests are finished?

Do not run your Watir script by double clicking it. Instead, open command prompt, navigate to folder where script is located and execute the script from there.

Glossary

Instance, an object that has been created for use by a program and is stored in memory.

Message, an action descriptor that can be sent to an object. If the object recognizes the message, it will respond and display related behavior.

Object, something that contains attributes and displays behavior according to what messages have been sent to it.

Ruby, object-oriented scripting language.

Watir, Web Application Testing in Ruby.

Feedback

Questions? Comments? The Watir development team like to hear your comments and suggestions for improvement. Email questions and suggestions to the Watir General Google group. Please read Support before posting.

The End

This is the end of the tutorial. Check out other pages at Watir Wiki. Watir unit tests are good resource.

Tutorial: the end
Enter labels to add to this page:
Please wait 
Looking for a label? Just start typing.