Debugging webdriverio tests with VSCode

Debugging tests with webdriverio can get frustrating when you’re trying to figure out why your test is sometimes clicking the wrong elements or just plain not working. Am I using the correct selector? Which element is it actually clicking on? There’s 3 things that you can do to help you drill down:

  • adding many console.log statements to your test
  • using a debugger to step through the test one line at a time
  • using webdriverio’s `browser.debug()` to get an interactive js session with the browser

While the last option seems like the obvious choice, using browser.debug has its own limitations that I describe here

I searched and had found this post of getting webdriverio tests running inside of vscode to help me step through a test file line by line. That post is using an older version of node, and newer versions of node (v8.11.x+) throw an error like below:

node --debug=127.0.0.1:5859
(node:29011) [DEP0062] DeprecationWarning: `node --debug` and `node --debug-brk` are invalid. Please use `node --inspect` or `node --inspect-brk` instead.

There’s 2 parts to get this to work with newer versions of node: VSCode configuration and webdriverio configuration

VSCode configuration

See here for creating a VSCode Launch Configuration. Adding this file will allow you to run the VSCode debugger and step through your code line by line.

Heres a working .vscode/launch.json file that you can use and adapt to fit your needs

{ 
"type": "node",
"request": "launch",
"name": "Run in debug",
"port": 5859,
"timeout": 60000,
"runtimeExecutable": "${workspaceRoot}/node_modules/.bin/wdio",
"cwd": "${workspaceRoot}",
"console": "integratedTerminal",
"args": [
"--spec", "main.js"
// "--spec main.js" will be passed to your executable as // "wdio '--spec main.js'" (which isn't what you want)
],
"env": {
"DEBUG": "1"
// use an environment variable to be able
// to toggle debug mode on and off
}
}

This configuration will run your runtimeExecutable and by defining the "port" variable, it will attempt a connection to port 5859. Once that connection is successfully made, you’ll be able to set breakpoints and step through your test.

webdriverio configuration

On the webdriverio side, we need to tell it to listen for connections from a debugger on port 5859.

In your wdio.conf.js file:

exports.config = { 
debug: true,
execArgv: ['--inspect-brk=127.0.0.1:5859],

// other wdio configuration
specs: ['some/specs/here'],
suites: { .... }
....
}

This snippet will start webdriverio and start listening for connections from a debugger on 127.0.0.1:5859 (which you did in your VSCode configuration). The program will stop at this point to wait for a debugger to connect, and if nothing connects, the command will fail.

Once you run it successfully, you should see this type of output

/Users/dperez/workspace/wdio/node_modules/.bin/wdio "--spec" "main.js" 
Debugger listening on ws://127.0.0.1:5859/9698ad4c-8d7d-447f-a259-1c566cd511d6 
Debugger attached.

You’ll see the program pause at this point until a connection is made. If you never see “Debugger attached”, it means VSCode has not connected to your program, and so you can’t set breakpoints and debug.

If you run this as part of your CI process (Gitlab/Jenkins), you can make debug mode configurable. You can use env vars in your .vscode/launch.json configuration.

... 
"console": "integratedTerminal",
"env": {
"DEBUG": 1
}

This will run your program with that env var set by using:

DEBUG=1 /Users/dperez/workspace/wdio/node_modules/.bin/wdio "--spec" "main.js"

Then in your wdio.conf.js file:

exports.config = { 
debug: process.env.DEBUG === '1',
execArgv: process.env.DEBUG === '1' ? ['--inspect-brk=127.0.0.1:5859'] : []
...
// remaining wdio options
... }
}

This way, the program will only wait to attach to the debugger when you run it inside of VSCode (where the environment variable is set), and everywhere else it will run normally without it.

Wrapping up

Add these snippets to your configuration if you need to step through your program and watch how the program is executing. It sure beats writing tons of console.logs all over your code.

If you’re interested in using webdriverio’s browser.debug() mode, check out my post on using wdio’s debug mode to play with the browser. If you want to see more of these articles, give the article a 👏 and follow me here on Medium.