Tabris.js – How to write unit tests
In this blog post, you’ll learn how to write unit tests for your Tabris.js application. To do that, you need a special setup to run your code without a native client because Tabris.js requires an Android or iOS device to run your application, and the native client is not available on your development machine. Fortunately, the native client can be mocked out so that your tests can run in Node.js without a mobile device. The client mock is pre-configured in the test setup of apps generated by tabris-init
; you can achieve that either by running tabris init
to start a new application (make sure the option Set up unit tests with Mocha is selected currently, available only for TypeScript projects): –
or you can have your setup similar to the sandbox.ts file in the test folder to create a test environment. You need to install the following necessary modules manually:
mocha – unit testing framework for Node.js.
sinon – spies, stubs and mocks for JavaScript.
chai – assertion library.
sinon-chai – Sinon.JS Assertions for Chai.
Now with your test environment set up, Tabris.js provides a submodule called ClientMock. This module creates an environment that lets you interact with all components programmatically without a native client. See the docs for more details.
Let’s say that we have the following MyComponent.tsx file:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
import {Button, TextView, Constraint, Composite, Properties} from 'tabris'; export class MyComponent extends Composite { constructor(properties?: Properties<MyComponent>) { super(); this.set(properties); this.append( <$> <Button center onSelect={this.showText}>Tap here</Button> <TextView centerX bottom={[Constraint.prev, 20]} font={{size: 24}}/> </$> ); } showText = () => { $(TextView).only().text = 'My component!'; }; } |
That creates a Button and TextView component and changes the text value of the TextView component when the button is tapped. Now we want to test that the correct text will be used when the button is tapped. For that we have the following MyComponent.test.ts file to test the component:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
import {tabris, ClientMock, sandbox, expect} from './sandbox'; // the same sandbox.ts file mentioned above import {MyComponent} from '../src/MyComponent'; // path to the MyComponent.ts file import {contentView, Button, TextView} from 'tabris'; describe('MyComponent', () => { beforeEach(() => { tabris._init(new ClientMock()); contentView.append(new MyComponent()); }); afterEach(() => { sandbox.restore(); }); it('shows message on button tap', () => { $(Button).only().onSelect.trigger(); expect($(TextView).only().text).to.equal('My component!'); }); }); |
then we can execute the tests with the following command:
1 |
mocha --require ts-node/register ./test/*.test.* |
If you have already initialized your application with the tabris init
command you can instead use the npm run test command. Once the texts are executed, you should get the following result:
So, this means a unit test is successfully executed without a native client! This example application with the unit test is available here. It is a slightly modified one of the Tabris.js template applications.
Let us know your thoughts!
Feedback is welcome!
Want to join the discussion?Feel free to contribute!