Jest报错:SyntaxError: 无法在模块外使用import语句
问题排查:Jest运行时出现
SyntaxError: Cannot use import statement outside a module 问题描述
已尝试Stack Overflow上编号为58613492、59879689、61781271的解决方案,但运行Jest时仍报错:
SyntaxError: Cannot use import statement outside a module 1 | import { Lambda, SecretsManager, config as awsConfig } from 'aws-sdk'; > 2 | import axios from 'axios';
报错仅指向第二行的axios导入语句。当前使用Node.js v14.19.3,相关配置文件如下:
tsconfig.json
{ "compilerOptions": { "target": "es2017", "allowJs": true, "module": "commonjs", "outDir": "dist", "rootDir": ".", "importHelpers": true, "strict": true, "noImplicitReturns": true , "noFallthroughCasesInSwitch": true , "moduleResolution": "node", "baseUrl": "./", "lib": ["ES2020.Promise"], "types": ["node", "jest"], "allowSyntheticDefaultImports": true , "esModuleInterop": true, "sourceMap": true, "experimentalDecorators": true, "skipLibCheck": true, "forceConsistentCasingInFileNames": true }, "include": ["src"], "exclude": ["node_modules"] }
jest.config.js
module.exports = { preset: "ts-jest", transform: { "^.+\\.(ts|tsx)?$": "ts-jest", "^.+\\.(js|jsx)$": "babel-jest", }, testEnvironment: "node", testTimeout: 60000, testPathIgnorePatterns: ["dist/*"], };
babel.config.js
module.exports = { presets: [ '@babel/preset-typescript', [ '@babel/preset-env', { targets: { esmodules: false, node: 'current' }, }, ], '@babel/preset-flow', ], plugins: [ ['@babel/plugin-transform-modules-commonjs'], ['@babel/plugin-proposal-decorators', { legacy: true }], ['@babel/plugin-proposal-class-properties'], ], };
package.json
{ "name": "device-job-sender", "version": "1.0.0", "description": "", "main": "src/handlers/job-sender-handler.ts", "scripts": { "test": "jest --detectOpenHandles", "deploy:local": "sls deploy --stage local", "start:local": "docker-compose down && docker-compose up -d && npm run deploy:local", "deploy": "./.circleci/deploy.sh", "prettify": "prettier \"{src,test,scripts}/**/*.{js,ts}\" --write" }, "repository": { "type": "git", "url": "git+https://github.com/vnatures/device-job-sender.git" }, "author": "", "license": "ISC", "bugs": { "url": "https://github.com/vnatures/device-job-sender/issues" }, "homepage": "https://github.com/vnatures/device-job-sender#readme", "devDependencies": { "@babel/preset-env": "^7.14.5", "@babel/preset-typescript": "^7.14.5", "@types/aws-lambda": "^8.10.79", "@types/jest": "^26.0.24", "@types/redis": "^2.8.29", "babel-loader": "^8.2.2", "fork-ts-checker-webpack-plugin": "^6.2.12", "husky": "^7.0.1", "jest": "^26.6.3", "ts-jest": "^26.5.6", "ts-loader": "^8.1.0", "ts-node": "^9.1.1", "tsconfig-paths": "^3.9.0", "tslib": "^2.3.0", "typescript": "^4.2.3", "webpack": "^4.44.1", "webpack-node-externals": "^2.5.2" }, "dependencies": { "@types/aws-iot-device-sdk": "^2.2.3", "@vnatures/logger": "^2.0.1", "@vnatures/secrets-manager": "^2.0.2", "axios": "^1.3.3" } }
解决步骤
1. 适配axios版本与Node.js 14兼容性
axios 1.3.x默认使用ES模块发布,而Node.js 14对ES模块的处理存在限制。降级axios到兼容CommonJS的版本:
npm install axios@0.27.2
2. 修改Jest配置,强制转换axios模块
当前Jest默认跳过node_modules目录的转换,需添加规则让axios被babel-jest处理:
module.exports = { preset: "ts-jest", transform: { "^.+\\.(ts|tsx)?$": "ts-jest", "^.+\\.(js|jsx)$": "babel-jest", }, testEnvironment: "node", testTimeout: 60000, testPathIgnorePatterns: ["dist/*"], // 新增:允许转换axios模块 transformIgnorePatterns: ["node_modules/(?!axios)/"] };
3. 优化Babel配置,明确模块转换规则
调整@babel/preset-env配置,指定Node.js版本并强制转换为CommonJS,移除无用的Flow预设:
module.exports = { presets: [ '@babel/preset-typescript', [ '@babel/preset-env', { targets: { node: '14.19.3' }, modules: 'commonjs' }, ] ], plugins: [ ['@babel/plugin-transform-modules-commonjs'], ['@babel/plugin-proposal-decorators', { legacy: true }], ['@babel/plugin-proposal-class-properties'], ], };
4. 确保tsconfig包含测试文件
如果测试文件不在src目录下,修改tsconfig的include字段:
"include": ["src", "test"],
内容的提问来源于stack exchange,提问作者Eyal Solomon
相关产品推荐
相关产品推荐

