๐๐ผ jest over vitest
JavaScript tooling has gotten a lot faster recently with the advent of ESModules and the creation of new Rust and Go based compilers. These speed improvements have affected everything from bundlers to test runners. Vitest is a prime example of a new test runner that leverages esbuild to execute very quickly.
I use jest to run tests on this website, but I was curious to see how vitest performed in comparison. I converted my entire test suite, and here are my thoughts on how it stacks up.
๐ initial changes
The first thing I noticed was that vitest
does not expose globals like test
and expect
by default like jest
does. This is configurable to match the jest
experience, although I preferred the explicit imports.
Another main difference is that vitest
does not automatically clean up mocks between tests like jest
does. I handled this by adding cleanup code to my setup.ts
file.
I have since found a configuration option that can clear mocks between each test.
๐ฆ types
When writing tests, I typically use jest-dom to add additional DOM matchers. These matchers come with their own types, and extend the expect
keyword as expected. While vitest
does support TypeScript, it doesn't extend these types correctly by default. In order to get this working I had to manually add the types to the vi
object.
๐ svg modules
Another thing I had to adjust was how svg
files were loaded into the test runner. With jest
, you can use the moduleNameMapper
configuration to stub out different file extensions. This was useful for all types of images and even css
.
With vitest
I found a plugin for importing svg
images. This plugin requires some interesting annotations to import statements to differentiate importing the svg
as a URL or as a React component. These annotations luckily had no effect on my application build process, and are only used during testing.
๐ performance
Based on everthing I had read, vitest
was going to be much faster than jest
thanks to esbuild
. However, in practice I found that jest
completed full test runs 14% faster.
I tried everything I could to make vitest
faster. I moved from jsdom to happy-dom. While it did increase speed, it came with its own issues. I also tried disabling threads, which cut the runtime in half! However, it came at the cost of stability, as my tests passed locally, but failed in GitHub Actions.
On the positive side, vitest
was very fast in watch mode. I don't have specific numbers here, but it felt around two to three times faster than jest
. This would be a big upside, but I don't usually do test driven development, or run my tests in watch mode very often.
๐ staying put
At the end of this little adventure, I decided that migrating to vitest wasn't the best choice for me at this time. It's not as fast as I thought it would be, and it came with a few too many quirks for my liking. This makes sense though, as vitest
is currently at v0.24.5
. I might reevaluate once it hits v1.0.0
, but for now I'm sticking with jest.