Reputation: 4539
I have a very simple test:
describe('sanity', () => {
it('sanity', () => {
expect(true).toBeTruthy()
})
})
And I'm receiving the following error:
FAIL spec/javascript/sanity_test.js
● Test suite failed to run
Jest encountered an unexpected token
This usually means that you are trying to import a file which Jest cannot parse, e.g. it's not plain JavaScript.
By default, if Jest sees a Babel config, it will use that to transform your files, ignoring "node_modules".
Here's what you can do:
• To have some of your "node_modules" files transformed, you can specify a custom "transformIgnorePatterns" in your config.
• If you need a custom transformation specify a "transform" option in your config.
• If you simply want to mock your non-JS modules (e.g. binary assets) you can stub them out with the "moduleNameMapper" config option.
You'll find more details and examples of these config options in the docs:
https://jestjs.io/docs/en/configuration.html
Details:
/Users/piousbox/projects/ruby/<project>/node_modules/@atlaskit/tooltip/index.js:1
({"Object.<anonymous>":function(module,exports,require,__dirname,__filename,global,jest){export { default } from './components/Tooltip';
^^^^^^
SyntaxError: Unexpected token export
3 | import update from "immutability-helper";
4 | import {components} from "react-select-2";
> 5 | import Tooltip from "@atlaskit/tooltip";
| ^
6 | const isEqual = require("react-fast-compare");
7 | import _, {replace} from "lodash";
8 | import { get } from "$shared/request";
at ScriptTransformer._transformAndBuildScript (node_modules/@jest/transform/build/ScriptTransformer.js:537:17)
at ScriptTransformer.transform (node_modules/@jest/transform/build/ScriptTransformer.js:579:25)
at Object.<anonymous> (app/javascript/customer2/components/fob/fob_utils.js:5:1)
Test Suites: 1 failed, 1 total
Tests: 0 total
Snapshots: 0 total
Time: 1.593s
I have this .babelrc:
{
"presets": ["@babel/react", "@babel/env"]
}
How do I make the trivial test pass?
Upvotes: 33
Views: 44167
Reputation: 4066
In certain circumstances, custom modules that live in the node_modules
folder are not ready for consumption by node directly, e.g. because they are generated as a separate build step.
By default jest ignores node_modules for transformation, as they are usually vanilla JS already. However, when that's not the case, you might get your error.
You can resolve the error by making sure your transform works, and you are including the specific module(s) in your transform.
In your jest.config.ts
{...
testEnvironment: 'node',
transform: {
'^.+\\.[tj]s$': [
'ts-jest',
{
tsconfig: '<rootDir>/tsconfig.json'
}
]
},
transformIgnorePatterns: ['node_modules/(?!@prisma/client-data-model/zod)'],
moduleFileExtensions: ['ts', 'tsx', 'js', 'jsx', 'node'],
..}
We define that all node_modules, but @prisma/client-data-model/zod)
should be ignored. As defined above, @prisma/client-data- model/zod)
will now be transformed by ts-jest, too.
Upvotes: 2
Reputation: 99
STEP-1. Create a .babelrc file at root directory and include given below code into it
{
"env": {
"test": {
"plugins": ["@babel/plugin-transform-modules-commonjs"]
}
}
}
STEP-2 Run this command in the root folder of your project-
npm install --save-dev jest @babel/plugin-transform-modules-commonjs
Jest doesn't work properly with ES6 Modules. Currently they have mentioned this thing in their website also so you can resolve this issue by following above given two steps.
Upvotes: 9
Reputation: 4539
Matt's answer is accepted b/c it is insightful. The change that did it for me was adding in package.json:
"jest": {
...
"transformIgnorePatterns": [
"node_modules/(?!@atlaskit)"
],
You can add support for multiple packages at once by separating them with a |
"jest": {
...
"transformIgnorePatterns": [
"node_modules/(?!module1|module2|etc)"
],
Upvotes: 45
Reputation: 19762
Two ways you can pass this test:
Option 1.) Setup your babel configuration to handle ES6 imports by add a testing env
option (the testing
environment flag will be defined in your package.json
scripts, for example: "test": "NODE_ENV=testing jest"
or "test": "BABEL_ENV=testing jest"
)...
babel.config.js
module.exports = api => {
api.cache(true);
return {
presets: ["@babel/preset-env", "@babel/preset-react"],
plugins: [
"@babel/plugin-transform-runtime",
["@babel/plugin-proposal-class-properties", { loose: true }],
],
env: {
testing: {
presets: [
[ "@babel/preset-env", { targets: { node: "current" }}],
],
},
},
};
};
Option 2.) Transpile the ES6 module into ES5 syntax in your webpack.config.js
configuration:
webpack.config.js
const { NODE_ENV } = process.env
const inDevelopment = NODE_ENV === "development";
module.exports = {
...
module: {
rules: [
...
{
test: /\.(js|jsx)$/,
loader: "babel-loader",
exclude: !inDevelopment ? /node_modules\/(?!(@atlaskit\/tooltip))/ : /(node_modules)/,
options: {
cacheDirectory: inDevelopment,
cacheCompression: false,
},
},
...
],
}
...
}
The major difference between the two options is that the first option will only work in a testing environment. If you try to use it in a development/production environment, it may impact other 3rd party packages and cause compilation errors. Therefore, if you plan on moving this into a production environment that supports IE11 and below, then the second option is recommended. HOWEVER, keep in mind that this will transpile the package every time a production build is created and/or a test suite is run. Therefore, if you're working on a very large project (or transpiling multiple ES6 packages), it can be quite resource heavy. Therefore, I'd recommend compiling the 3rd party package(s) from ES6 to ES5 and installing it/them locally or privately (via an NPM package).
Working example (this example includes the second option): https://github.com/mattcarlotta/transpile-es6-module
To install:
cd ~/Desktop && git clone [email protected]:mattcarlotta/transpile-es6-module.git
cd transpile-es6-module
yarn install
yarn dev
to run the demoyarn test
to run test suitesUpvotes: 8