For this blog post, I can not share the code I already built as it belongs to my employer.
Instead, I will start from scratch using the Jasmine 1.2.0 standalone release. It includes a sample test suite which will be a perfect
fit for this example. It includes the main test runner (an HTML page called
and the Jasmine distribution (under the
lib/ directory). It also includes example code
src. If you unzip the file and load
SpecRunner.html in your browser,
you should see the test suite pass without errors.
To run the test suite using Phantom.js, I’ve used Joshua Carver’s Jasmine runner for Phantom.js. I copied
lib directory from the project under
lib/phantom-jasmine in my source tree.
Next I changed the
SpecRunner.html to add an additional reporter called
ConsoleReporter - which is part of Joshua’s project.
Third step: patch Jasmine to get a stack trace on test failure. The current version of Jasmine (1.2.0) does not show stack traces when executed throught Phantom.js. Thanks to a tip found on Stackoverflow I was able to fix that with a very simple patch and submitted a pull request.
1 2 3 4 5 6 7 8 9 10
Assuming that Phantom.js is installed and available in the
the test suite can be executed using the following command:
Finally, I wrapped the above command in a Rake task so that I can
rake phantomjs to run the test suite:
1 2 3 4 5
This is what the output looks like:
In order to execute the Jasmine test suite in real browsers, I am using Selenium
Webdriver. I am using the
selenium-webdriver gem to interact with it.
In just a minute, I will show how I have added an additional task to my
to run the tests.
Also note that a webserver is required to serve the
SpecRunner.html file and
its dependencies. One could setup a webserver such as Apache but I think it is
too much work and creates an external unnecessary dependency for the test runner
(every environment where the tests are executed would need to configure an
instance of Apache). Instead, I prefer to use the
service_manager gem to spin
up a simple web server on demand using the
python -m SimpleHTTPServer command.
With Service Manager, you define services that will be automatically started when
the tests begin and stopped at the end. Because Python is widely available, no extra
dependencies should be required. For more information, see service_manager documentation on GitHub.
Rakefile in the end is fairly straightforward:
bundlerand some gems
ServiceManagerwhich will spawn the webserver process
- Detect the browser passed as a command line argument
- Instantiate Webdriver and load the
- Capture the output of the
ConsoleReporterand display it
- Finally, check the status for success or failure
Rakefile looks like this:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43
To run the
webdriver task, just execute
rake webdriver browser=firefox. You should
see Firefox start and go through the tests. This is what the output looks like:
A remaining step is that I will need to add support for browsers other than Firefox or Chromium, as well as support for remote Webdriver instances (such as Internet Explorer running in a virtual machine).
Before wrapping up, I’d like to show a failure example. Let’s break some code
by commenting out line 17 of
rake phantomjs fails
as expected. Notice how I can see the full stack trace which points me to line
Phantom.js, Webdriver and Jasmine are a really powerful combo to test drive code. Not only that, they are also really easy to set up. Kudos to the various Open Source contributors behind these projects for providing a great developer experience!
The next step of this adventure is continuous integration. I need to integrate the tests with our Jenkins instance. Hopefully, that should be trivial since I have my tests runner command ready to go.
If you want to see the code, it’s available on GitHub.