I have this simple test:
import React from 'react'
import { render } from '@testing-library/react'
import Button from '.'
describe('Button', () => {
it('renders button without crashing', () => {
const label = 'test'
render(<Button label={label} />)
})
})
And I have a jest.config.json
with this content
{
"setupFilesAfterEnv": [
"<rootDir>/lib/settings/setupTests.ts"
]
}
And on my setupTests.ts
I have
import '@testing-library/jest-dom'
When I run npm run test
(which just run jest
), I got the following error:
The error below may be caused by using the wrong test environment, see https://jestjs.io/docs/configuration#testenvironment-string.
Consider using the "jsdom" test environment.
What I am doing wrong? This used to work before an upgrade.
jsdom is an implementation of a browser environment, which supports these types of UI tests. For Jest version 28 and greater, jest-environment-jsdom was removed from the default jest installation to reduce package size.
To set up a JSDOM environment within Jest, start by creating a new Jest configuration file called jest. config. js . In this file, export an object whose testEnvironment property's value is "jsdom" .
Jest uses jsdom to provide an environment that behaves much like a browser's DOM or document. Each test file gets a single instance of jsdom, and changes aren't reset between tests inside the file. It's a best practice to clean up between tests so that a test's output doesn't affect any other test.
jsdom is a pure JavaScript implementation of the DOM and browser APIs that runs in node. If you're not using Jest and you would like to run your tests in Node, then you must install jsdom yourself. There's also a package called global-jsdom which can be used to setup the global environment to simulate the browser APIs.
Thanks to JSDOM, you can run your tests in Jest, which, as I have mentioned, can only run in Node. By using passing the value "jsdom" to Jest’s testEnvironment option, you can make it set up a global instance of JSDOM which you can use when running your tests.
By using passing the value "jsdom" to Jest’s testEnvironment option, you can make it set up a global instance of JSDOM which you can use when running your tests. Figure 2. The JavaScript environment within Node.
With JSDOM you can emulate, manipulating the DOM and attaching event listeners to elements, for example. JSDOM JSDOM is an implementation of web standards written in purely in JavaScript which you can use in Node. To understand how JSDOM works, let’s use it to create an object that represents index.html and which we can use in Node.
Given that Jest depends on Node-specific APIs and therefore only runs in Node, you can’t use Jest also. To be able to run your tests in Jest, instead of running your tests within the browser, you can bring browser APIs to Node by using JSDOM. You can think of JSDOM as an implementation of the browser environment which can run within Node.
In your package.json
, or jest.config.js
/jest.config.ts
file, change the value of the testEnvironment
property to jsdom
.
package.json
"jest":{
"testEnvironment": "jsdom"
}
jest.config.[js|ts]
{
"testEnvironment": "jsdom"
}
If you are using jest 28, you will need to install jest-environment-jsdom
separately by either:
npm: npm i jest-environment-jsdom --save-dev
yarn: yarn add -D jest-environment-jsdom
By default, jest uses the node
testEnvironment. This essentially makes any tests meant for a browser environment invalid.
jsdom
is an implementation of a browser environment, which supports these types of UI tests.
For Jest version 28 and greater, jest-environment-jsdom
was removed from the default jest
installation to reduce package size.
jest testEnvironment documentation
Jest 28 breaking changes
This can be solved on a per-test-file basis by adding a @jest-environment
docblock to the beginning of your file. For example:
/** @jest-environment jsdom */
import React from 'react'
import { render } from '@testing-library/react'
import Button from '.'
describe('Button', () => {
it('renders button without crashing', () => {
const label = 'test'
render(<Button label={label} />)
})
})
If your project has a mix of UI and non-UI files, this is often preferable to changing the entire project by setting "testEnvironment": "jsdom"
within your package.json or Jest config. By skipping initializing the JSDom environment for non-UI tests, Jest can run your tests faster. In fact, that's why Jest changed the default test environment in Jest 27.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With