Tag Archives: Selenium

Nemo.js: PayPal’s open source node.js automation framework

By

Nemo.js came about as a response to the adoption of krakenjs within PayPal. Writing automation in JavaScript made sense for a variety of reasons: involving web application engineers in the automation process, executing tests in a common context, utilizing the task and test frameworks already in place. Nothing in the node.js ecosystem met the extensive requirements of automation tests at PayPal, so Nemo.js was born.

Nemo.js wraps around the ubiquitous Selenium WebDriver, and as such, allows control of virtually any browser on any operating system. Nemo.js is built with a plugin architecture. This allows the core module to be very small. It allows users to customize their testing environment, without including features they do not need. It allows an easy interface for authoring new plugins that can then be shared with others. It also allows the user their choice of test runner and task runner.

Nemo setup

Nemo was designed to reduce cruft in spec files, as well as offer maximum flexibility. The basic setup pattern is:

var Nemo = require('nemo');
var nemo = {};
var plugins = require('../config/nemo-plugins.json');
var setup = require('../config/setups').fooSpec;

(new Nemo(plugins)).setup(setup).then(function (_nemo) {
  nemo = _nemo;
  /***
   * nemo.wd is a reference to selenium-webdriver commonjs module
   * nemo.driver is a reference to the active WebDriver instance
   * nemo.view will contain views and addView method (if using nemo-view)
   * nemo.props contains any properties defined in the nemoData ENV variable
  **/
});

Combine this pattern with a test runner like Mocha.js and a task runner like Grunt.js and you’ve got an incredibly powerful and configurable automation environment. You can easily run and organize tests in both development and continuous integration environments, against multiple browser/OS/device combinations.

Nemo-view plugin

Using the nemo-view plugin, verbose Selenium syntax becomes much more readable

driver.wait(function () {
  return driver.isElementPresent(By.id('email'));
}, 10000, 'cannot find email input');
driver.findElement(By.css('form#signup button[type=submit]')).click();
driver.findElement(By.id('email')).sendKeys(email);
driver.findElement(By.id('password')).sendKeys(password);
driver.findElement(By.id('password_confirm')).sendKeys(password);
driver.isElementPresent(By.css('input[name=captcha]')).
  then(function(present) {
    if (present) {
      driver.findElement(By.css('input[name=captcha]')).sendKeys('abcde'); 
    }
  });

To this:

var signup = nemo.view.addView('signup');

signup.emailTextInputWait(10000, 'cannot find email input');
signup.showSignupButton().click();
signup.emailTextInput().sendKeys(email);
signup.passwordTextInput().sendKeys(password);
signup.confirmPasswordTextInput().sendKeys(confirmPassword);
signup.captchaInputPresent().
then(function(present) {
  if (present) {
    signup.captchaInput().sendKeys('abcde');
  }
});

The nemo-view plugin builds its methods from a JSON locator file like signup.json, used in the above example:

{
  emailTextInput: {
    locator: 'email',
    type: 'id'
  },
  showSignupButton: {
    locator: 'form#signup button[type=submit]',
    type: 'css'
  },
  passwordTextInput: {
    locator: 'password',
    type: 'id'
  }
}
… and so on

Also, if you have locators which may differ by country, nemo and nemo-view handle that easily. Simply set a locale property, and modify your locator file:

  termsLinkText: {
    FR: {
      locator: 'termes et conditions',
      type: 'partialLinkText'
    },
    DE: {
      locator: 'Geschäftsbedingungen',
      type: 'partialLinkText'
    },
    default: {
      locator: 'Terms and Conditions',
      type: 'partialLinkText'
    }
  }

Other Plugins

Folks within PayPal have been authoring plugins to access our development databases and services. They aren’t publicly available due to their lack of applicability outside of PayPal. There is a small but growing list of publicly available plugins though, and we hope to see more from the open source community.

The generator-nemo yeoman generator

Layering Nemo onto a krakenjs application couldn’t be easier. Just run the following from within your project’s home directory:

$ npm install -g generator-nemo
$ yo nemo

As long as you have a webdriver binary to match your desired testing browser (see driver setup in the nemo-docs) you are ready to get started with Nemo.

You can also get some popcorn and just watch a screencast of me using generator-nemo:

using generator-nemo from Matt Edelman on Vimeo.

The future of Nemo.js

The future is bright. Strong adoption within PayPal, and a team ramping up to take over support and roadmap from the original author, means we are poised to support our internal as well as external customers well into the future. Of course, being an open source software, the community at-large is welcome to guide the direction of Nemo.js and contribute plugins, etc.

Get started!

Nemo.js home page: Includes several screencasts on how to get started with Nemo.js and its core features

Nemo.js documents repository: How to setup your driver binaries, author plugins, and much more.

Nemo.js example application: An exemplar implementation of Nemo.js + Mocha.js + Grunt.js

Nemo.js yeoman generator: Add Nemo.js to an existing kraken 1.0 application, create views, install plugins

PayPal hosts BayJax meetup dedicated to JavaScript testing

By

On November 20, 2013, the BayJax meetup group convened at PayPal HQ to talk about JavaScript testing. Four presenters, including myself, covered various facets of JavaScript testing. While the driving rain of that evening dampened attendance somewhat (there were a couple left over pizzas and some empty chairs), the high quality videos linked below can serve to widen the audience for this informative event.

Vojta Jina on Karma: Part 1 and Part 2

Vojta Jina discussed the Karma testing framework. In addition to running the exhaustive suite of tests for AngularJS, Karma is a standout JS unit testing framework in its own right. Enjoy:

Reid Burke on Testing Web Apps: Part 1Part 2 and Part 3

Setting up a continuous integration environment to run 100K+ tests on 12 different browsers is hard, but necessary. Managing the feedback from such a system is also hard, but necessary. Reid shares his valuable perspective based on meeting this challenge for the YUI team; using YetiSauceLabs, Jenkins and parallelization.

Santiago Suarez Ordoñez: Part 1 and Part 2

Santiago, a SauceLabs Senior Infrastructure Developer and Selenium committer, looks at the history of JavaScript testing and also towards its future. He discusses the origin of Selenium, Selenium2, how the Selenium2 API is becoming a W3C spec, and how the web driver codebase will then shrink to basically nothing. He also discusses what he sees as the ideal approach to automated testing for small teams. Finally he outlined a very cool cross-browser JavaScript testing API which SauceLabs is currently developing.

Matt Edelman on Nemo: Part 1Part 2 and Part 3

PayPal has adopted NodeJS for its web applications (please see krakenjs). We wanted to write our browser automation tests in JavaScript and execute them from within the application they are testing. While there were a couple different webdriver APIs available (selenium-webdriver and wd) in npm, there wasn’t an available framework which provided the flexible configuration needed to run the same tests across multiple environments and devices. I wrote the Nemo module to satisfy these requirements, as well as to suggest (not enforce) a factorization which promotes maintainable, readable, and reusable code.

As you can see in the diagram below, the system uses JSON wire protocol, which can communicate with numerous drivers (selenium grid, ghostdriverios-driverAppium, SauceLabs, etc.) in order to automate just about any browser or even native mobile applications:

system-diagram

We are using Nemo along with Grunt (see grunt task grunt-loop-mocha) and Mocha to write and run automated tests throughout the entire development lifecycle: development, QA, and continuous integration. Look for Nemo to be open source very soon!

One notable change since this talk occurred is that you can now parallelize Nemo tests in order to complete test suites more quickly.

Happy Testing!