SharePoint Framework unit tests React setup


Unit tests are part of the modern age development process and believe or not JavaScript has gone that far that we now create unit tests for our front end and SharePoint is no exception. With the modern SharePoint Framework, Microsoft introduced new page web parts model where we can craft apps based on TypeScript, Reactjs and create component unit tests. This post is about SPFx solution setup and prerequisites and it is part of a series about SPFx unit testing.

React SPFx unit test packages to be installed

Here are the packages we would install in order to get started with SPFx React web part unit tests


...
"devDependencies": {
    "@microsoft/sp-build-web": "~1.3.0",
    "@microsoft/sp-module-interfaces": "~1.3.0",
    "@microsoft/sp-webpart-workbench": "~1.3.0",
    "gulp": "~3.9.1",
    "@types/chai": ">=3.4.34 <3.6.0",
    "@types/mocha": ">=2.2.33 <2.6.0",
    "@types/sinon": "1.16.36",
    "sinon":"1.17.2",
    "@types/enzyme":"2.8.11",
    "chai-enzyme": "0.8.0",
    "enzyme": "2.8.0",
    "react-addons-test-utils": "15.4.2"
  }
....

SPFx default unit test frameworks and packages

The included with the SharePoint Framework testing tools by default are Mocha, Chai, Sinon (in a way) and Sinon-Chai.

"@types/chai": ">=3.4.34 <3.6.0", "@types/mocha": ">=2.2.33 <2.6.0",

The Chai Assertion Library

So Chai comes with the default scaffolded by the @microsoft/sharepoint yeoman generator react web part template. It is an assertion library for unit tests and the browser that can be delightfully paired with any JavaScript testing framework. Chai uses language chains to improve the readability of the assertions. Just have a look how fluent the expect assertions are:


expect('nav h1').dom.to.contain.text('Chai');
expect('#node .button').dom.to.have.style('float', 'left');
expect('.toggle-pane').dom.to.not.be.visible()

So we can chain any of the chainable getters to create a fluent and readable assertion in our React unit tests:


to
be
been
is
that
which
and
has
have
with
at
of
same
but
does

More about the Chai apis on the official website

Mocha for Nodejs

In short and for SharePoint and ASP.NET developers, Mocha is like NUnit and XUnit but for JavaScript. It is a feature-rich JavaScript test framework making asynchronous testing simple and fun. This is how unit test looks like:


describe('my suite', () => {
  it('my test', () => {
    // should set the timeout of this test to 1000 ms; instead will fail
    this.timeout(1000);
    assert.ok(true);
  });
});
Work with promises is fairly simple and also hooks are introduced to be used to set up preconditions and clean up after your tests.

describe('hooks', function() {

  before(function() {
    // runs before all tests in this block
  });

  after(function() {
    // runs after all tests in this block
  });

  beforeEach(function() {
    // runs before each test in this block
  });

  afterEach(function() {
    // runs after each test in this block
  });

  // test cases
});

Enzyme as mount and traversing utility for SPFx React web part components

We have the assertions and the testing framework in place, but a utility that mounts React component and can observe behavior of that component is something we should install. It is not included by default with the SharePoint Framework simply because there are multiple choices out there and maybe the Microsoft team decided to let us decide what to use. So my choice is Enzyme, maybe the most popular one. Enzyme is a JavaScript Testing utility for React that makes it easier to assert, manipulate, and traverse your React Components output. For example, we can easily mount React component then find button element to simulate click or just get text from div element.


// Mount SPFx React component for testing.
const reactComponent = mount((<Foo onButtonClick={onButtonClick} />));

// Simulate button click within SPFx React component.
reactComponent .find('button').simulate('click');
    ....
// Find React elements by using css selectors.
let element = reactComponent.find('.icon-star')

Enzyme for testing the SPFx React component state or properties change

Once the React component is mounted the component state or properties can be tested for change.

expect(reactComponent.props().bar).to.equal('foo');
expect(reactComponent.state().foo).to.equal(10);

Sinon to spy on SPFx React component EventListener and test data or state change when they are triggered

SINON.JS is JavaScript library for standalone test spies, stubs and mocks that works with any unit testing framework. It is included to the SPFx packages for the React web part template, but we have to install the @types/sinon so we get the VSCode IntelliSense support for the library.


/// <reference types="sinon" />

declare const sinon: sinon.SinonStatic;

describe('ReactTestingPart1WebPart', () => {

    let reactComponent: ReactWrapper;
    let componentDidMountSpy: sinon.SinonSpy;

    before(() => {

        componentDidMountSpy = sinon.spy(ReactTestingPart1.prototype, 'render');

        reactComponent = mount(React.createElement(
            ReactTestingPart1,
            {
                description: "test"
            }
        ));

        // Alternativly rename the current file from .ts to .tsx and mount in an HTML/XML fashion.
        // let reactComponent = mount(<ReactTestingPart1 description="test" />);
    });

    it('should render be called once', () => {

        expect(componentDidMountSpy.calledOnce).to.be.true;
    });
    ....

SharePoint Framework React mocking framework

We the .NET developers are used with libraries like Moq, Rhino mocks and NSubstitute, in the JavaScript my choice would be again SINON.JS that can also be used as mocking framework by utilizing the stub api. We can easily fake method or property to simulate business case and unit test it. It is somewhat supported with the SharePoint Framework as well.


let stubbedService = 
    sinon.stub(SPListService.prototype, "getAll")
    .returns(new Promise<Item[]>((resolve: any, reject: any) => {
         resolve([{ ID:1, Title:"title1" }, { ID:1, Title:"title2" }]);
    }));

Conclusion

SharePoint Unit Testing was tabu few years ago, but now old school developers like me attempt to do even SharePoint front end unit testing. Believe or not this is the modern SharePoint and we can build `regression less` SPFx solutions by taking the advantage of the testing capabilities and frameworks. Start challenging your coding skills through unit testing now and see if you can built stable and regression less systems.

SPFx React Unit Testing Sample in Github

Sharing is Caring!

Have a look at the next part SharePoint Framework debug unit tests and TDD

Posted on

Tags: SharePoint Framework Debugging, Karma unit testing, SPFx code coverage, SharePoint Client side testing, React unit tests

Comments