Building a custom Google Data Studio connector from A-Z. Part 3 — unit tests and eslint setup
In the previous part we managed to build a working connector. Let’s extend the project with unit tests and add lint the code with eslint.
As always I pushed the full code of this part to GitHub. You can find it at https://github.com/Bajena/spotify-gds-connector/tree/Tutorial3. You can also test the connector via this link.
1. Setting up tests
Jest — A framework for “Delightful JavaScript Testing”
There are dozens of JS testing frameworks on the market. I got inspired by other open source connectors and decided to use the Jest framework created by Facebook. They advertise it as a zero-configuration framework and I am disposed to confirm it — writing tests is really easy and fun with Jest!
First thing —install it using yarn: yarn add --dev jest
I also recommend adding "test": "jest"
to your package.json
's script
s.
Let’s see how a simple test suite looks like. I decided to create a module to encapsulate the logic of converting Date
objects to strings. Notice how I’m exporting and importing modules.
Now we can run the test suite using yarn test
command and see the following output:
→ yarn test
$ jest
PASS test/DateUtils.test.js
✓ getDatePart (9ms)Test Suites: 1 passed, 1 total
Tests: 1 passed, 1 total
Snapshots: 0 total
Time: 2.426s
Ran all test suites.
✨ Done in 3.87s.
Add ES7 support to your test suite
Current setup can be enough for writing nice unit tests, however if you’re writing modern JS on day to day basis you’ll quickly start missing advanced language features provided by the newer EcmaScript standards — especially the async/await syntax.
This gave me a bigger headache than I initially expected, so I hope to save a lot of your time here if you’re interested.
First install the required packages: yarn add --dev babel-jest babel-core babel-preset-env
.
Then add a .babelrc
file with following content:
{
"presets": ["env"]
}
Next we’ll need to change they way our modules are imported and exported. Change the export commands in the DateUtils
module to this:
if (typeof(exports) !== "undefined") {
exports['__esModule'] = true;
exports['default'] = DateUtils;
}
Then in the test you can use it using the import
command:
import DateUtils from '../src/DateUtils';
We cannot however use the import
keyword in our connector’s code. We’ll also need to import the module only for test purposes, because in Google Scripts platform everything you define in separate files is accessible without any need of requiring anything.
So let’s say we’ll need DateUtils
in DataCache.js
file. What we’ll do is add the following line to the beginning of the file:
if (typeof(require) !== "undefined") {
var DateUtils = require('./DateUtils.js')['default'];
}
We’re now able to use ES7 syntax in our tests. Go and check it yourself e.g. by adding async
keyword to any function definition.
Add code coverage
Jest supports also code coverage generation. Let’s set it up as well. We’ll do it in a few simple steps.
First add following script to package.json
: "coverage": "jest --coverage".
Next we’ll tell jest to collect code coverage only from the src files. Add this to your package.json
:
"jest": {
"collectCoverageFrom": [
"src/*.js"
]
}
Now run yarn coverage
and check out the output with the fancy code coverage table:
As you can see there’s still a lot of testing to do, but I’ll spare you the rest of this process. If you want to see the rest of the tests you can check them out in the GitHub repo — I refactored the code and achieved a following score:
2. Linting the code with eslint
Next thing I can’t live without when writing JavaScript code is a linter. My choice is eslint. Let’s add the lib itself and an eslint plugin for jest framework.
yarn add --dev eslint@latest eslint-plugin-jest@latest
Now we can add .eslintrc.js
file to the root folder of our project. You can define yours or copy the one I prepared:
Also a tip — add a file called .eslintignore
to the root of your project with coverage
in the first line. This’ll suppress warnings coming from the the output of jest’s test coverage files.
Now if you’re using code editor plugins for linting code you’re done — editor should automatically highlight any code issues.
If not you can run eslint manually using the following command:
Summary
In this tutorial we’ve made a giant step forward. Adding unit tests and linting the code will make further development and refactoring much more simple. The connector is now working, it’s fully tested and has consistent style across the whole codebase.
Theoretically we could stop at this point, but I decided I’ll show you something more… In the next part you’ll see how to test and deploy the code using CircleCI.