Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
A node.js client for webdriver/selenium 2.
JavaScript Other

Fetching latest commit…

Cannot retrieve the latest commit at this time

Failed to load latest commit information.
browser-scripts
doc
examples
lib
test
.gitignore
.travis.yml
LICENSE.APACHE2
Makefile
README.md
package.json

README.md

WD.js -- A light weight WebDriver/Se2 client for node.js

Build Status

Update node to latest

http://nodejs.org/#download

Install

npm install wd

Authors

License

Usage

): wd shell
> x = wd.remote() or wd.remote("ondemand.saucelabs.com", 80, "username", "apikey")

> x.init() or x.init({desired capabilities ovveride})
> x.get("http://www.url.com")
> x.eval("window.location.href", function(e, o) { console.log(o) })
> x.quit()

Writing a test!

var webdriver = require('wd')
  , assert = require('assert');

var browser = webdriver.remote();

browser.on('status', function(info){
  console.log('\x1b[36m%s\x1b[0m', info);
});
browser.on('command', function(meth, path){
  console.log(' > \x1b[33m%s\x1b[0m: %s', meth, path);
});

desired = {
  browserName:'chrome'
  , tags: ["examples"]
  , name: "This is an example test"
}

browser.init(desired, function() {
  browser.get("http://saucelabs.com/test/guinea-pig", function() {
    browser.title(function(err, title) {
      assert.ok(~title.indexOf('I am a page title - Sauce Labs'), 'Wrong title!');
      browser.elementById('submit', function(err, el) {
        browser.clickElement(el, function() {
          browser.eval("window.location.href", function(err, title) {
            assert.ok(~title.indexOf('#'), 'Wrong title!');
            browser.quit()
          })
        })
      })
    })
  })
})

Supported Methods

JsonWireProtocol wd
GET /status
Query the server's current status.
status(cb) -> cb(err, status)
POST /session
Create a new session.
init(desired, cb) -> cb(err, sessionID)
Initialize the browser.
GET /sessions
Returns a list of the currently active sessions.

sessions(cb) -> cb(err, sessions)

Alternate strategy to get session capabilities from server session list:
altSessionCapabilities(cb) -> cb(err, capabilities)

GET /session/:sessionId
Retrieve the capabilities of the specified session.
sessionCapabilities(cb) -> cb(err, capabilities)
DELETE /session/:sessionId
Delete the session.
quit(cb) -> cb(err)
Destroy the browser.
POST /session/:sessionId/timeouts
Configure the amount of time that a particular type of operation can execute for before they are aborted and a |Timeout| error is returned to the client.
setPageLoadTimeout(ms, cb) -> cb(err)
(use setImplicitWaitTimeout and setAsyncScriptTimeout to set the other timeouts)
POST /session/:sessionId/timeouts/async_script
Set the amount of time, in milliseconds, that asynchronous scripts executed by /session/:sessionId/execute_async are permitted to run before they are aborted and a |Timeout| error is returned to the client.
setAsyncScriptTimeout(ms, cb) -> cb(err)
POST /session/:sessionId/timeouts/implicit_wait
Set the amount of time the driver should wait when searching for elements.
setImplicitWaitTimeout(ms, cb) -> cb(err)
GET /session/:sessionId/window_handle
Retrieve the current window handle.
windowHandle(cb) -> cb(err, handle)
GET /session/:sessionId/window_handles
Retrieve the list of all window handles available to the session.
windowHandles(cb) -> cb(err, arrayOfHandles)
GET /session/:sessionId/url
Retrieve the URL of the current page.
url(cb) -> cb(err, url)
POST /session/:sessionId/url
Navigate to a new URL.
get(url,cb) -> cb(err)
Get a new url.
POST /session/:sessionId/forward
Navigate forwards in the browser history, if possible.
forward(cb) -> cb(err)
POST /session/:sessionId/back
Navigate backwards in the browser history, if possible.
back(cb) -> cb(err)
POST /session/:sessionId/refresh
Refresh the current page.
refresh(cb) -> cb(err)
POST /session/:sessionId/execute
Inject a snippet of JavaScript into the page for execution in the context of the currently selected frame.

execute(code, args, cb) -> cb(err, result)
execute(code, cb) -> cb(err, result)
args: script argument array (optional)

Execute script using eval(code):
safeExecute(code, args, cb) -> cb(err, result)
safeExecute(code, cb) -> cb(err, result)
args: script argument array (optional)

Evaluate expression (using execute):
eval(code, cb) -> cb(err, value)

Evaluate expression (using safeExecute):
safeEval(code, cb) -> cb(err, value)

POST /session/:sessionId/execute_async
Inject a snippet of JavaScript into the page for execution in the context of the currently selected frame.

executeAsync(code, args, cb) -> cb(err, result)
executeAsync(code, cb) -> cb(err, result)
args: script argument array (optional)

Execute async script using eval(code):
safeExecuteAsync(code, args, cb) -> cb(err, result)
safeExecuteAsync(code, cb) -> cb(err, result)
args: script argument array (optional)

GET /session/:sessionId/screenshot
Take a screenshot of the current page.
takeScreenshot(cb) -> cb(err, screenshot)
POST /session/:sessionId/frame
Change focus to another frame on the page.
frame(frameRef, cb) -> cb(err)
POST /session/:sessionId/window
Change focus to another window.
window(name, cb) -> cb(err)
DELETE /session/:sessionId/window
Close the current window.
close(cb) -> cb(err)
GET /session/:sessionId/cookie
Retrieve all cookies visible to the current page.
allCookies() -> cb(err, cookies)
POST /session/:sessionId/cookie
Set a cookie.
setCookie(cookie, cb) -> cb(err)
cookie example:
{name:'fruit', value:'apple'}
Optional cookie fields:
path, domain, secure, expiry
DELETE /session/:sessionId/cookie
Delete all cookies visible to the current page.
deleteAllCookies(cb) -> cb(err)
DELETE /session/:sessionId/cookie/:name
Delete the cookie with the given name.
deleteCookie(name, cb) -> cb(err)
GET /session/:sessionId/title
Get the current page title.
title(cb) -> cb(err, title)
POST /session/:sessionId/element
Search for an element on the page, starting from the document root.

element(using, value, cb) -> cb(err, element)

elementByClassName(value, cb) -> cb(err, element)
elementByCssSelector(value, cb) -> cb(err, element)
elementById(value, cb) -> cb(err, element)
elementByName(value, cb) -> cb(err, element)
elementByLinkText(value, cb) -> cb(err, element)
elementByPartialLinkText(value, cb) -> cb(err, element)
elementByTagName(value, cb) -> cb(err, element)
elementByXPath(value, cb) -> cb(err, element)
elementByCss(value, cb) -> cb(err, element)

POST /session/:sessionId/elements
Search for multiple elements on the page, starting from the document root.

elements(using, value, cb) -> cb(err, elements)

elementsByClassName(value, cb) -> cb(err, elements)
elementsByCssSelector(value, cb) -> cb(err, elements)
elementsById(value, cb) -> cb(err, elements)
elementsByName(value, cb) -> cb(err, elements)
elementsByLinkText(value, cb) -> cb(err, elements)
elementsByPartialLinkText(value, cb) -> cb(err, elements)
elementsByTagName(value, cb) -> cb(err, elements)
elementsByXPath(value, cb) -> cb(err, elements)
elementsByCss(value, cb) -> cb(err, elements)

Retrieve an element avoiding not found exception and returning null instead:
elementOrNull(using, value, cb) -> cb(err, element)

elementByClassNameOrNull(value, cb) -> cb(err, element)
elementByCssSelectorOrNull(value, cb) -> cb(err, element)
elementByIdOrNull(value, cb) -> cb(err, element)
elementByNameOrNull(value, cb) -> cb(err, element)
elementByLinkTextOrNull(value, cb) -> cb(err, element)
elementByPartialLinkTextOrNull(value, cb) -> cb(err, element)
elementByTagNameOrNull(value, cb) -> cb(err, element)
elementByXPathOrNull(value, cb) -> cb(err, element)
elementByCssOrNull(value, cb) -> cb(err, element)

Retrieve an element avoiding not found exception and returning undefined instead:
elementIfExists(using, value, cb) -> cb(err, element)

elementByClassNameIfExists(value, cb) -> cb(err, element)
elementByCssSelectorIfExists(value, cb) -> cb(err, element)
elementByIdIfExists(value, cb) -> cb(err, element)
elementByNameIfExists(value, cb) -> cb(err, element)
elementByLinkTextIfExists(value, cb) -> cb(err, element)
elementByPartialLinkTextIfExists(value, cb) -> cb(err, element)
elementByTagNameIfExists(value, cb) -> cb(err, element)
elementByXPathIfExists(value, cb) -> cb(err, element)
elementByCssIfExists(value, cb) -> cb(err, element)

Check if element exists:
hasElement(using, value, cb) -> cb(err, boolean)

hasElementByClassName(value, cb) -> cb(err, boolean)
hasElementByCssSelector(value, cb) -> cb(err, boolean)
hasElementById(value, cb) -> cb(err, boolean)
hasElementByName(value, cb) -> cb(err, boolean)
hasElementByLinkText(value, cb) -> cb(err, boolean)
hasElementByPartialLinkText(value, cb) -> cb(err, boolean)
hasElementByTagName(value, cb) -> cb(err, boolean)
hasElementByXPath(value, cb) -> cb(err, boolean)
hasElementByCss(value, cb) -> cb(err, boolean)

POST /session/:sessionId/element/active
Get the element on the page that currently has focus.
active(cb) -> cb(err, element)
POST /session/:sessionId/element/:id/click
Click on an element.

clickElement(element, cb) -> cb(err)

element.click(cb) -> cb(err)

GET /session/:sessionId/element/:id/text
Returns the visible text for the element.

text(element, cb) -> cb(err, text)
element: specific element, 'body', or undefined

element.text(cb) -> cb(err, text)

Check if text is present:
textPresent(searchText, element, cb) -> cb(err, boolean)
element: specific element, 'body', or undefined

element.textPresent(searchText, cb) -> cb(err, boolean)

POST /session/:sessionId/element/:id/value
Send a sequence of key strokes to an element.

type(element, keys, cb) -> cb(err)
Type keys (all keys are up at the end of command).
special key map: wd.SPECIAL_KEYS (see lib/special-keys.js)

element.type(keys, cb) -> cb(err)

POST /session/:sessionId/keys
Send a sequence of key strokes to the active element.
keys(keys, cb) -> cb(err)
Press keys (keys may still be down at the end of command).
special key map: wd.SPECIAL_KEYS (see lib/special-keys.js)
GET /session/:sessionId/element/:id/name
Query for an element's tag name.

getTagName(element, cb) -> cb(err, name)

element.getTagName(cb) -> cb(err, name)

POST /session/:sessionId/element/:id/clear
Clear a TEXTAREA or text INPUT element's value.

clear(element, cb) -> cb(err)

element.clear(cb) -> cb(err)

GET /session/:sessionId/element/:id/attribute/:name
Get the value of an element's attribute.

getAttribute(element, attrName, cb) -> cb(err, value)

element.getAttribute(attrName, cb) -> cb(err, value)

Get element value (in value attribute):
getValue(element, cb) -> cb(err, value)

element.getValue(cb) -> cb(err, value)

GET /session/:sessionId/element/:id/displayed
Determine if an element is currently displayed.

isDisplayed(element, cb) -> cb(err, displayed)

element.isDisplayed(cb) -> cb(err, displayed)

GET /session/:sessionId/element/:id/css/:propertyName
Query the value of an element's computed CSS property.

getComputedCss(element, cssProperty , cb) -> cb(err, value)

element.getComputedCss(cssProperty , cb) -> cb(err, value)

POST /session/:sessionId/accept_alert
Accepts the currently displayed alert dialog.
acceptAlert(cb) -> cb(err)
POST /session/:sessionId/dismiss_alert
Dismisses the currently displayed alert dialog.
dismissAlert(cb) -> cb(err)
POST /session/:sessionId/moveto
Move the mouse by an offset of the specificed element.
moveTo(element, xoffset, yoffset, cb) -> cb(err)
Move to element, xoffset and y offset are optional.
POST /session/:sessionId/click
Click any mouse button (at the coordinates set by the last moveto command).
click(button, cb) -> cb(err)
Click on current element.
Buttons: {left: 0, middle: 1 , right: 2}
POST /session/:sessionId/buttondown
Click and hold the left mouse button (at the coordinates set by the last moveto command).
buttonDown(cb) -> cb(err)
POST /session/:sessionId/buttonup
Releases the mouse button previously held (where the mouse is currently at).
buttonUp(cb) -> cb(err)
POST /session/:sessionId/doubleclick
Double-clicks at the current mouse coordinates (set by moveto).
doubleclick(cb) -> cb(err)
EXTRA Opens a new window (using Javascript window.open):
newWindow(url, name, cb) -> cb(err)
newWindow(url, cb) -> cb(err)
name: optional window name
Window can later be accessed by name with the window method,
or by getting the last handle returned by the windowHandles method.
EXTRA windowName(cb) -> cb(err, name)
EXTRA waitForElement(using, value, timeout, cb) -> cb(err)
EXTRA waitForVisible(using, value, timeout, cb) -> cb(err)
EXTRA waitForElementByClassName(value, timeout, cb) -> cb(err)
waitForElementByCssSelector(value, timeout, cb) -> cb(err)
waitForElementById(value, timeout, cb) -> cb(err)
waitForElementByName(value, timeout, cb) -> cb(err)
waitForElementByLinkText(value, timeout, cb) -> cb(err)
waitForElementByPartialLinkText(value, timeout, cb) -> cb(err)
waitForElementByTagName(value, timeout, cb) -> cb(err)
waitForElementByXPath(value, timeout, cb) -> cb(err)
waitForElementByCss(value, timeout, cb) -> cb(err)
EXTRA waitForVisibleByClassName(value, timeout, cb) -> cb(err)
waitForVisibleByCssSelector(value, timeout, cb) -> cb(err)
waitForVisibleById(value, timeout, cb) -> cb(err)
waitForVisibleByName(value, timeout, cb) -> cb(err)
waitForVisibleByLinkText(value, timeout, cb) -> cb(err)
waitForVisibleByPartialLinkText(value, timeout, cb) -> cb(err)
waitForVisibleByTagName(value, timeout, cb) -> cb(err)
waitForVisibleByXPath(value, timeout, cb) -> cb(err)
waitForVisibleByCss(value, timeout, cb) -> cb(err)
EXTRA isVisible(element , cb) -> cb(err, boolean)
deprecated: isVisible(queryType, querySelector, cb) -> cb(err, boolean)
EXTRA Waits for JavaScript condition to be true (polling within wd client):
waitForCondition(conditionExpr, timeout, pollFreq, cb) -> cb(err, boolean)
waitForCondition(conditionExpr, timeout, cb) -> cb(err, boolean)
waitForCondition(conditionExpr, cb) -> cb(err, boolean)
conditionExpr: condition expression, should return a boolean
timeout: timeout (optional, default: 1000)
pollFreq: pooling frequency (optional, default: 100)
return true if condition satisfied, error otherwise.
EXTRA Waits for JavaScript condition to be true (async script polling within browser):
waitForConditionInBrowser(conditionExpr, timeout, pollFreq, cb) -> cb(err, boolean)
waitForConditionInBrowser(conditionExpr, timeout, cb) -> cb(err, boolean)
waitForConditionInBrowser(conditionExpr, cb) -> cb(err, boolean)
conditionExpr: condition expression, should return a boolean
timeout: timeout (optional, default: 1000)
pollFreq: pooling frequency (optional, default: 100)
return true if condition satisfied, error otherwise.
EXTRA isVisible(cb) -> cb(err, boolean)

Full JsonWireProtocol mapping:

supported mapping

full mapping

More docs!

WD is simply implementing the Selenium JsonWireProtocol, for more details see the official docs:
 - http://code.google.com/p/selenium/wiki/JsonWireProtocol

Run the tests!

  - Run the selenium server with chromedriver: 
      java -jar selenium-server-standalone-2.21.0.jar -Dwebdriver.chrome.driver=<PATH>/chromedriver
  - cd wd
  - npm install .
  - make test
  - look at the results!

Run the tests on Sauce Labs cloud!

  - cd wd
  - npm install .
  - make test_saucelabs

Test Coverage

test coverage

Something went wrong with that request. Please try again.