About the cover illustration
6. Write an end-to-end test
2.4. DEBUGGING TESTS WITH CHROME DEBUGGER
When a unit test fails, your job is to debug the test, learn why it failed, and fix the code. Debugging is part of the testing process, and you need to get good at it to become a testing master.
A common way to debug tests is to use console.log to see what the values of variables are during the execution of the code. We’ve all been there—console-logging 10 different values in an attempt to figure out what the heck is going wrong!
console.log works fine, but it’s easy to go from console-logging important values, to randomly console-logging in the hope that you find the problem. Programming is not playing with a piñata. When you
program, you should not be taking blind swings. You need to understand the code.
One way to help understand code is to use a debugging program. Chrome includes a Debugger that gives you the ability to break code execution at
specific points and step through the code line by line. When the execution is paused, you can examine variables available to the code at that point during the execution.
In this section, you’ll learn how to use Chrome’s Debugger when running tests in Jest. You’re going to add a breakpoint to the Item test so that you can inspect the wrapper object returned by Vue Test Utils mount function and see what it looks like.
Important
You need to be running Node 8.4.0 or greater; otherwise, the debugger will not work correctly. To check your node version, enter node --version. If the version is earlier than 8.4.0, install the latest version of Node by following the instructions in appendix A.
To add breakpoints for the node debugger, you add a debugger
statement. A debugger statement causes the Node Debugger to break at that point in your code. Add a debugger statement to Item.spec.js, after the wrapper declaration. Your code will look like the following.
Listing 2.13. Using Vue Test Utils to test text
import { shallowMount } from '@vue/test-utils' import Item from '../Item.vue'
describe('Item.vue', () => { test('renders 'item'', () => {
const wrapper = shallowMount(Item)
debugger 1 expect(wrapper.text()).toContain('item') })
})
1 Chrome Debugger will pause on this debugger statement.
Now you need to run the unit tests in debug mode. This is a common task, so you should add a new test:unit:debug script. The script runs Jest without a cache and in one process, in a Node Debugger process. Add the following script to the package.json script field:
"test:unit:debug': 'node --inspect-brk ./node_modules/jest/bin/jest.js --no- cache --runInBand'
And run the following command:
npm run test:unit:debug
After running this command, you should see output telling you that the Node Debugger is listening on a WebSocket.
Keep the command line open with the debugger listening. Now open Chrome and navigate to chrome://inspect in the browser. You will see node_modules/jest/bin/jest in the Remote Targets section. This is the Node Debugger process. Click Inspect to open a Chrome Debugger window (figure 2.7).
Figure 2.7. The Chrome Inspect window
The Debugger will be paused, so click the Resume Execution button in the top corner to resume execution. You can see the button in figure 2.8.
Figure 2.8. The Resume Execution button
The execution will be stopped on the debugger statement you added to the code earlier. Great—now you have access to all the variables available at this point in the code, including wrapper. Hover over wrapper to see what the object looks like. You can see that it is an instance of a VueWrapper, with element, vm, vnode, and options properties (figure 2.9).
Figure 2.9. Inspecting the wrapper
To see the methods, you need to look at the Wrapper prototype. If you click __proto__ and then __proto__ again, you can see the methods available to the wrapper object (figure 2.10).
Figure 2.10. Inspecting wrapper methods
You’ll use a lot of these methods in chapter 3. Right now, click the buttons to the right of the Resume Execution button. If you hover over the buttons, you’ll see their names. There’s a Step Into Next Function Call button:
click it to skip over the next function call and break on the next line. This can be useful if you want to skip over a function without examining what
happens inside.
Play around with these buttons to get an idea of how to walk through the execution of the code. This knowledge will come in useful if you need to debug your application later in the book.
Note
Some IDEs like WebStorm and VSCode support debugging in the IDE itself. You can see a guide for debugging Jest programs in WebStorm in the docs (http://mng.bz/UMqX), and you can learn how to debug tests running in Jest with VSCode (http://mng.bz/1j7N).
Debugging with Chrome Inspector is like a superpower. You can debug any failing test effectively when you know how to step through the code!
Before you move on to the next chapter, let’s go over what you learned.
SUMMARY
Vue projects follow a common directory structure.
You can use npm scripts to run project specific scripts, like test scripts.
Jest finds tests in a project, runs them, and reports on whether they passed or failed.
You can mount components with the Vue Test Utils shallowMount
and mount methods.
Vue Test Utils needs to run in a browser environment.
You can debug Node programs with Chrome.
EXERCISES
1
Fill in the following template to test that TestComponent renders the text “Hello, World!”:
import { shallowMount } from '@vue/test-utils' import TestComponent from '../TestComponent.vue'
test('renders Hello, World!', () => { // Add test code here
})
2
Which Vue Test Utils method would you use to mount a component if you wanted to test the rendered output of a component but not the rendered output of a child component?
mount
shallowMount
Chapter 3. Testing rendered component output
This chapter covers
Testing component output
Writing a static Hacker News feed
If a tree falls in a forest and no one is around to hear it, does it make a sound? More importantly, if a component is mounted and no one writes a test for it, did it generate output?
Testing is about input and output. In a test you supply an input, receive an output, and assert that the output is correct. The most common output of components is the rendered output—the stuff that render functions generate. That’s what this chapter is about: testing rendered component output.
To learn how to test component output, you’ll write a static Hacker News feed. The news feed is simple, but it gives you the opportunity to test different forms of output and get acquainted with the Vue Test Utils API.
This book is about testing from start to finish, and part of the testing process is converting murky requirements into specifications. The first section of this chapter is about creating specifications from requirements.
After you have the specifications for the static news feed, you’ll write tests
for the specs. By doing that, you’ll learn how to use different Vue Test Utils methods to test the rendered output of Vue components in unit tests.
After you’ve written the news feed, you’ll create a progress bar component, a task through which you’ll learn how to test styles and classes.
The first thing to do is create the specifications for the static news feed.