Skip to content

A debuggable JS BDD framework that uses the official selenium-webdriver for Node and cucumber-js

Notifications You must be signed in to change notification settings

cambridgeweblab/selenium-cucumber-js

 
 

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

17 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

selenium-cucumber-js

A debuggable JS BDD framework that uses the official selenium-webdriver for Node and cucumber-js.

Installation

npm install selenium-cucumber-js --save-dev

Usage

node ./node_modules/selenium-cucumber-js/index.js -s ./step-definitions

Options

-h, --help                output usage information
-V, --version             output the version number
-s, --steps <path>        path to step definitions. defaults to ./step-definitions
-p, --pageObjects <path>  path to page objects. defaults to ./page-objects
-b, --browser <path>      name of browser to use. defaults to chrome
-t, --tags <tagName>      name of tag to run

Feature files

A feature file is a Business Readable, Domain Specific Language file that lets you describe software’s behaviour without detailing how that behaviour is implemented. Feature files are written using the Gherkin syntax and must live in a folder named features within the root of your project.

# ./features/google-search.feature

Feature: Searching for vote cards app
  As an internet user
  In order to find out more about the itunes vote cards app
  I want to be able to search for information about the itunes vote cards app

  Scenario: Google search for vote cards app
    When I search Google for "itunes vote cards app"
    Then I should see some results

Step definitions

Step definitions are the glue between features files and the actual system under test. Step definitions are written in JavaScript and should be stored in either ./features/step-definitions or ./step-definitions folder. If you use a different location you must provide the path via the -s command line switch.

// ./step-definitions/google-search.js

module.exports = function () {

    this.When(/^I search Google for "([^"]*)"$/, function (searchQuery) {

        driver.get('http://www.google.com');

        var input = driver.findElement(by.name('q'));

        input.sendKeys(searchQuery);
        input.sendKeys(selenium.Key.ENTER);
    });

    this.Then(/^I should see some results$/, function () {

        driver.wait(until.elementsLocated(by.css('div.g')), 10000);

        return driver.findElements(by.css('div.g')).then(function (elements) {
            expect(elements.length).to.not.equal(0);
        });
    });
};

The following variables are available within the Given(), When() and Then() functions:

Variable Description
driver an instance of selenium web driver (the browser)
selenium the raw selenium-webdriver module, providing access to static properties/methods
page page objects
by the selenium By class used to locate elements on the page
until the selenium until class used to wait for elements/events
expect instance of chai expect to expect('something').to.equal('something')
assert instance of chai assert to assert.isOk('everything', 'everything is ok')
trace handy trace method to log console output with increased visibility

Page objects

Page objects are accessible via the global page variable and are automatically loaded from ./page-objects or the path specified using the -p switch. Page objects are exposed using the camel case version of their filename, for example ./page-objects/google-search.js becomes page.googleSearch. Page objects also have access to the same runtime variables described in step definitions section above.

An example page object:

// ./page-objects/gogole-search.js

module.exports = {

    elements: {
        searchInput: by.name('q')
    },

    preformSearch: function (keywords) {

        // notice the element path below use the full page qualifier
        var input = driver.findElement(page.googleSearch.elements.searchInput);

        input.sendKeys(keywords);
        input.sendKeys(selenium.Key.ENTER);
    }
};

And its usage within a step definition:

module.exports = function () {

    this.When(/^I search Google for "([^"]*)"$/, function (searchQuery) {

        page.googleSearch.preformSearch(searchQuery);
    });
};

Event handlers

You can register event handlers for the following events within the cucumber lifecycle.

Event Example
BeforeFeature this.BeforeFeatures(function(feature, callback) {})
BeforeScenario this.BeforeScenario(function(scenario, callback) {});
AfterScenario this.AfterScenario(function(scenario, callback) {});
AfterFeature this.AfterFeature(function(feature, callback) {});

How to debug

Selenium methods return a JavaScript Promise that will be resolved when the method completes. This means you can assign a .then function and use it to trigger your debugger by inserting a debugger statement, for example:

module.exports = function () {

    this.When(/^I search Google for "([^"]*)"$/, function (searchQuery) {

        driver.findElement(by.name('q')).then(function(input) {
            expect(input).to.exist;
            debugger; // <<- your IDE should step in at this point, with the browser open
            return input;
        })
        .then(function(input){
            input.sendKeys(searchQuery);
            input.sendKeys(selenium.Key.ENTER);
        });
    });
};

Demo

This project includes an example feature file and step definition to help you get started. You can run the example using the following command:

node ./node_modules/selenium-cucumber-js/index.js

About

A debuggable JS BDD framework that uses the official selenium-webdriver for Node and cucumber-js

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages

  • JavaScript 94.6%
  • Gherkin 5.4%