LWC Debugging and Testing with Toronto Salesforce Developer Group

Mohith Shrivastava
4 min readSep 25, 2020

At the Toronto, Canada, Salesforce Developer group, we spent a couple of hours today trying to learn LWC Debugging Techniques and Jest Testing.

We set ourselves below learning objectives.

  1. Explore Debugging Techniques
  2. Take a sample Lightning Web Components (LWC) and write some Jest tests.

Debugging Techniques Identified

  1. Local Development Server has limited debugging capability due to no proper source maps.
  2. Debugging on org can be done by setting breakpoints in code once we enable Lightning to run in the debug mode.
  3. Use the Sources tab in chrome and look under the lightning/page/modules/c folder to find your component.js file.
  4. Add JavaScript breakpoints to step through the code.
  5. We identified black boxing helps. We black-boxed a couple of Salesforce JavaScript files like aura_proddebug.js and scenarioTracker.js to make debugging easier.
  6. Also, make sure you turn on the custom formatter in chrome on so one can read the @api variables on the HTML template.
Find Source code for setting breakpoints in treeview.js component lib

The component code

treeView.html

<template><lightning-card title={label}><lightning-tree items={items}></lightning-tree><lightning-button label=”Change Selected” onclick={handleClick}></lightning-button></lightning-card></template>

treeView.js

import {
api,
LightningElement
} from 'lwc';
export default class TreeView extends LightningElement {
@api
label;
items = [{
label: 'Western Sales Director',
name: '1',
expanded: true,
items: [{
label: 'Western Sales Manager',
name: '2',
expanded: true,
items: [{
label: 'CA Sales Rep',
name: '3',
expanded: true,
items: []
},
{
label: 'OR Sales Rep',
name: '4',
expanded: true,
items: []
}
]
}]
},
{
label: 'Eastern Sales Director',
name: '5',
expanded: false,
items: [{
label: 'Easter Sales Manager',
name: '6',
expanded: true,
items: [{
label: 'NY Sales Rep',
name: '7',
expanded: true,
items: []
},
{
label: 'MA Sales Rep',
name: '8',
expanded: true,
items: []
}
]
}]
},
{
label: 'International Sales Director',
name: '9',
expanded: true,
items: [{
label: 'Asia Sales Manager',
name: '10',
expanded: true,
items: [{
label: 'Sales Rep1',
name: '11',
expanded: true,
items: []
},
{
label: 'Sales Rep2',
name: '12',
expanded: true,
items: []
}
]
},
{
label: 'Europe Sales Manager',
name: '13',
expanded: false,
items: [{
label: 'Sales Rep1',
name: '14',
expanded: true,
items: []
},
{
label: 'Sales Rep2',
name: '15',
expanded: true,
items: []
}
]
}
]
}
];
handleClick(e) {
const evt = new CustomEvent('treeclick', {
detail: {
node: 'xyz'
}
});
this.dispatchEvent(evt);
}
}

Writing Test Code

We use sfdx-lwc-jest npm module in our project dev-dependencies.

Writing test code was a breeze once we have scaffolded the project using the below command

sfdx force:lightning:lwc:test:create -f <folderpath>/force-app/main/default/lwc/treeView/treeView.js

We wanted to cover test for

  1. Verify Component DOM had rendered properly
  2. Verify that the component event was dispatched successfully with the right data. The trick here is you create a jest mock function using jest.Fn() and add as a listener so when the button is clicked the element can invoke a mock function instead.
  3. Also, we learned that when jest dispatches mock handler the handler has a mock property that has calls and results in an array to get information around arguments of the call and results of calls respectively.
  4. Check the JEST mock API here

jest test code

import {
createElement
} from 'lwc';
import TreeView from 'c/treeView';
describe('c-tree-view', () => {afterEach(() => {
// The jsdom instance is shared across test cases in a single file so reset the DOM
while (document.body.firstChild) {
document.body.removeChild(document.body.firstChild);
}
});
it('renders tree view component', () => {
const element = createElement('c-tree-view', {
is: TreeView
});
element.label = 'Roles';
document.body.appendChild(element);
const cardElement = element.shadowRoot.querySelector('lightning-card');
return Promise.resolve().then(() => {
expect(cardElement.title).toBe('Roles');
});
});
it('renders tree view component with label', () => {
const element = createElement('c-tree-view', {
is: TreeView
});
element.label = 'hello';
document.body.appendChild(element);
const cardElement = element.shadowRoot.querySelector('lightning-card');
return Promise.resolve().then(() => {
expect(cardElement.title).toBe('hello');
});
});
it('dispatches event on button click', () => {
const element = createElement('c-tree-view', {
is: TreeView
});
element.label = 'hello';
document.body.appendChild(element);
// Mock handler for toast event
const handler = jest.fn();
element.addEventListener('treeclick', handler);
const buttonElement = element.shadowRoot.querySelector('lightning-button');
buttonElement.click();
return Promise.resolve().then(() => {
expect(handler).toHaveBeenCalled();
expect(handler.mock.calls[0][0].detail.node).toBe('xyz');
});
});
});

Running the jest code

  1. Salesforce Extension pack in vscode has excellent support for running and debugging jest tests
  2. Use alpha version of vscode-jest extension from jest community to get code overlay.
  3. Getting coverage is also easy via command line using the below command
npm run test:unit:coverage
Code Overlay using jest extension
Code Overlay using vscode-jest extension

References

  1. Lightning stubs in sfdx-lwc-jest are found here
  2. Official Salesforce documentation on lwc jest testing
  3. Trailhead Module on jest
  4. Explore some awesome test coverage in lwc recipes app
  5. Official jest documentation for writing jest tests

--

--

Mohith Shrivastava

Principal Developer Advocate @Salesforce, Author “Learning Salesforce Lightning Application Development (Aura Component)” & “Learning Salesforce Einstein (Outda