Testing your Solid.js code in vitest
Tags: solidjs, testing, javascript, typescript
Published: 2022-02-22 08:43:11

Some time has passed since I showed you how to test your [Solid.js](https://www.solidjs.com/) code with [jest](https://dev.to/lexlohr/testing-your-solidjs-code-2gfh) and [uvu or tape](https://dev.to/lexlohr/testing-solidjs-code-beyond-jest-39p), but now there's another solution that I don't want you to waste time to research yourself: [vitest](https://vitest.dev/).

You may have heard of [vite](https://vitejs.dev), the slim fast dev server that scored an amazing as deserved 98% satisfaction on the [state of js survey 2021](https://2021.stateofjs.com/en-US/libraries/build-tools). It's creators found unit testing too cumbersome and slow and decided to add their own perspective to the task. The result is vitest: it runs a vite server under the hood to transform the code to test as fast as possible, uses an enhanced flavor of [chai](https://www.chaijs.com/) to have jest-compatible assertions, integrates DOM mocking using [jsdom](https://github.com/jsdom/jsdom) or [happy-dom](https://github.com/capricorn86/happy-dom) and even the [tiny-spy](https://github.com/Aslemammad/tinyspy) library that was just built as a separate library to allow for easy reuse is small and compatible with jest.

## Setup

First, you need to add `vitest` and `jsdom` to your dev dependencies:

```sh
npm i --save-dev vitest jsdom
```

Then, your `vite.config.js` (or `vitest.config.js` if you want to have a different setup for testing) needs to look similar to this:

```js
/// <reference types="vitest" />
/// <reference types="vite/client" />

import { defineConfig } from 'vite'
import solid from 'solid-start' // or 'vite-plugin-solid'

export default defineConfig({
  test: {
    environment: 'jsdom',
    transformMode: {
      web: [/\.[jt]sx?$/],
    },
    // solid needs to be inline to work around
    // a resolution issue in vitest:
    deps: {
      inline: [/solid-js/],
    },
    // if you have few tests, try commenting one
    // or both out to improve performance:
    // threads: false,
    // isolate: false,
  },
  plugins: [solid()],
  resolve: {
    conditions: ['development', 'browser'],
  },
})
```

If you already have a `vite.config.js`, all you need to add is the `test` section and make sure that the correct conditions are set in `resolve`.

Lastly, you should add a script to your `package.json` to allow for testing:

```js
{
  "scripts": {
    "test": "vitest"
  }
}
```

## How to test?

Actually, vitest is 95% compatible with jest, so I'll just [send you to the corresponding part of the jest guide](https://dev.to/lexlohr/testing-your-solidjs-code-2gfh#what-now). Obviously, it won't let you run the jest transpilation pipeline, but everything else should be there.

Code coverage is provided by c8; unfortunately, even vitest cannot fix the issue in babel's handling of source maps that doesn't allow us to collect coverage from Solid.js components.

## How fast is it?

For all the promises of being blazing fast, vitest is slower than uvu and it can actually be as slow as jest for the first run of a suite containing very few test cases. Once you have more than 5-10 tests and can really use the watch mode, it easily outperforms jest, even though it will only be faster than uvu if it can omit enough test cases in a run (though to be fair, this is mostly because uvu lacks *a lot* of features that vitest provides).

Also, you should consider that vitest is still in development, so performance improvements shouldn't be unexpeced.

If you are currently using jest and don't like waiting for test results, you should definitely consider vitest; if you only have a really small test suite of less than 5 tests and don't need advanced features like a sophisticated watch mode and extendable assertions, uvu/solid-register will be faster, though it won't be nearly as comfortable as vitest.