Diving into Watir

I’ve worked on several web-based applications in the past, and the same problem keeps cropping up:

Can we automate the full system level tests?

This answer tends to lean more towards the “Yes*” category these days, however there is an asterisk for a reason.

Some tests are harder to automate and verify than others, Downloading files for example.  Also any time specific browser controls are used to drive functionality in the site, i.e. login dialogs, many of the automated tools tend to start losing their reliability.

When I worked on .NET MVC applications, my teams tended to lean towards the C# implementation of Selenium, pairing it with the SpecFlowExtension to implement the test steps using Gherkin syntax.  Essentially this setup allowed us to define each function that the browser would execute as a step in the gherkin code, and then use that to drive the pages throughout the tests.

This tended to work well enough.  Though some of the implementation left itself to be desired.  For example, once multiple feature files started using the same test steps, the code driving those steps would still live in the original location, making it more difficult to locate them and make modifications.  We also tended to run into issues with the tests being brittle due to timing issues.  Some developers had faster machines than others, or there was potentially network latency during various test runs.  Selenium has built in wait functions, however its implementation tended to be overly generic.

A Refreshing Change

Recently, I had the opportunity to be on a team who were developing a JAVA based web-application.  Rather than just blindly using the JAVA implementation of Selenium, our test engineer suggested that we take a look at Watir as an alternative.  As his focus was on another project at the time, I ended up being the one getting my feet wet.

Watir, or Web Automated Testing In Ruby is a tool that will take control of your browser and automatically perform actions on the page, just as Selenium does.

There are currently two distinct Watir Gems, watir-classic and watir-webdriver.

Watir-classic is the original implementation of Watir that can be used to drive Internet Explorer browsers only.  This Gem is essentially depricated, and requires an older version of Ruby to run.

Watir-webdriver is a Gem that is built on top of the Selenium Webdriver implementation.  As such, by default it will open and drive a Firefox browser, and then if needed, can be configured to work with other browsers.  In fact, during the course of the project, we configured the tests to be run on Internet Explorer as well as a headless browser called PhantomJS.

Overall our developers tended to like Watir.  It is significantly less verbose then the Selenium C# implementation, and has better tools for waiting, letting us add better stability to our test steps.  It also runs relatively quickly.

Go ahead and try it

I figured I’d take some time, to outline how to configure a bare-bones test project in Watir, and then delve into more advanced techniques, such as the Page Object Pattern, in a future post.

So to start with, we’re going to configure RSpec for testing.  Why did I choose RSpec over something like Cucumber?  Either would work.  However during the initial investigation of the development environment for the project, there had been a “nice to have” of getting the testing framework to integrate with a tool called HipTest.  At the time we were developing the testing framework, HipTest did not have Cucumber support, only RSpec.  Even though this integration never ended up happening, we decided to continue with RSpec.  The following steps illustrate how one would setup the Ruby project from scratch.

  1. Download Ruby and RubyGems [Link], ensure that the install locations are added to your PATH.
  2. Install the Bundler Gem
    • From a console, type: gem install bundler
  3. In the folder where you want your testing project to be located type the following to generate a Gemfile: bundle init
  4. Open the Gemfile in a text editor and replace what is there with the following:
    • Note: the version of Ruby I’m using is 2.2.2, thus my second line reads.  You will need to replace this with whatever version of Ruby you have installed.
  5. Now that the Gemfile has been defined, we need to install the bundles specified: bundle install
  6. Now lets initialize rspec: rspec –init
    • What this does is it generates a .rspec and a \spec\spec_helper.rb file and add them to your directory structure.
  7. Now lets make a simple RakeFile
    • Make a new file named “Rakefile” (or “Rakefile.rb”) in your root testing directory.
    • Add the following lines to it:
      • What this does is to define a RakeTask called “spec”, which will look in the spec directory, and any sub directories for the suffix _spec.rb and execute those spec files.
      • By specifying the rspec_opts as above, it will update the output formatting into a more human readable notation.
      • Once this is done, typing ‘rake spec’ in your root testing directory should indicate that you have no examples found and that there were no successes or errors.

That’s to be expected, as we haven’t written a test yet.

Configuring Watir Tests

  1. Open up the automatically generated file : ‘~\spec\spec_helper.rb’.
    1. There should be a lot of pregenerated code and comments in this file.
    2. Note that the first block of comments indicates that this spec helper is run before each spec file is executed.
      • That means that this is the correct place to instantiate a Watir browser so that it occurs when we execute our tests.
  2. At the top of the file (outside of the RSpec.configure), lets go ahead and add the following lines :
    • require ‘watir-webdriver’
      @browser = Watir::Browser.new
    • What his does is instantiate a new instance of a browser to be controlled by Watir and assign it to a local variable called browser.  By default Watir-webdriver will open an instance of Firefox and will throw an error if Firefox is not installed.
  3. Within the bounds of the RSpec.configure add the following lines:
    • config.around(:example) do |example|
      @browser = browser
      example.run
      end
      config.after(:suite) {
      browser.close unless @browser.nil?
      }
    • By pecifying an around function, which focuses on each :example, we can control what occurs as each test is executed.  In this case we are assigning the browser variable to a globally accessible variable for each test run.
    • The after(:suite) definition defines the behavior of what should happen as each test suite ends.  In our case we want to close the browser down.

Now let’s go write a spec to see if it works:

In the ~\spec folder create a new ruby file ending in the string _spec.rb.  You may recognize this format from the Rakefile screen shot above.  For the purposes of this blog post, I shall create a file called blog_example_spec.rb.

At this point, call ‘rake spec’ on the command line, hopefully you should see a browser open and close.

Now we’re actually writing tests using the RSpec syntax, namely the “describe” and “it” syntax.  What this does is let us write our tests in easy to parse human text.

So let’s write a basic test to go to Google’s homepage and verify that a search button exists.  This will illustrate some of the Watir basics, and show that the browser can actually do something.

Using Watir-webdriver’s documentation, we can figure out how to use the @browser object we defined previously to navigate to a url, by using the @browser.goto statement.

So we can start to define our step like :

describe ‘Going to Google’ do
it ‘should have a search button’ do
@browser.goto ‘http://www.google.com’
end
end

By running rake spec on the command line, the browser should open, and then navigate to Google’s homepage and then close.  A good first step.

We can now leverage watir’s  object selectors to find buttons.  Watir has several selectors that can be used, ranging as generic as “element” to being as specific as “input” or “button”.  So let’s start by finding a button, and failing the test if it isn’t present:

describe ‘Going to Google’ do
it ‘should have a search button’ do
@browser.goto ‘http://www.google.com’
fail if !@browser.button.visible?
end
end

This should also pass.

However, given the above code, we have no idea what button we found.  What calling the object selectors will do is grab the first element that matches the description.  So if we just cared about any old button, this test would be fine.  However, we want to verify that this is the search button.  Thus we will need to add an additional qualifier to the selector.  In this case, adding the “:text” selector will allow us to verify that a button with the “Google Search” text is visible.

describe ‘Going to Google’ do
it ‘should have a search button’ do
@browser.goto ‘http://www.google.com’
fail if !@browser.button(:text => “Google Search”).visible?
end
end

Now this will fail if the page does not contain a visible button with that exact text.

So you might be thinking, “Why would I ever care about the presence of a search button on Google so much that I’d write an automated test for it?”  Well you probably won’t.  This test was meant to be an obvious oversimplification of what you can do with Watir, while still actually executing.  In the future, I may add additional posts for more complicated Watir tests, as well as demonstrate the Page Object Pattern, which can be used to simplify the tests even further.

Comments
  • Charles

    Note that there is a minor typo that is a pain to track down:

    @browser = Watir::Browser.new

    should be

    browser = Watir::Browser.new

Add your comment

Your email address will not be published.