Vue2.7+TS+Vuetify环境下Jest无法挂载Composition API组件
Vue 2.7 + Nuxt + Vuetify环境下Composition API组件单元测试配置方案
环境与依赖
当前技术栈:Vue 2.7 + TypeScript + Nuxt + Vuetify,核心依赖包:
"nuxt": "^2.15.8", "@nuxtjs/composition-api": "^0.33.1", "@vue/test-utils": "^1.3.0", "jest": "^28.1.3",
问题现象
挂载组件时抛出语法错误:
SyntaxError: Unexpected token (1:1141) at Parser.pp$4.raise (node_modules/vue-template-es2015-compiler/buble.js:2757:13) at Parser.pp.unexpected (node_modules/vue-template-es2015-compiler/buble.js:647:8) at Parser.pp$3.parseExprAtom (node_modules/vue-template-es2015-compiler/buble.js:2196:10) at Parser.<anonymous> (node_modules/vue-template-es2015-compiler/buble.js:6003:24) at Parser.parseExprAtom (node_modules/vue-template-es2015-compiler/buble.js:6129:31) at Parser.pp$3.parseExprSubscripts (node_modules/vue-template-es2015-compiler/buble.js:2047:19) at Parser.pp$3.parseMaybeUnary (node_modules/vue-template-es2015-compiler/buble.js:2024:17) at Parser.pp$3.parseExprOps (node_modules/vue-template-es2015-compiler/buble.js:1966:19) at Parser.pp$3.parseMaybeConditional (node_modules/vue-template-es2015-compiler/buble.js:1949:19) at Parser.pp$3.parseMaybeAssign (node_modules/vue-template-es2015-compiler/buble.js:1925:19)
测试示例代码
import { mount, createLocalVue } from '@vue/test-utils'; import CompositionApi from '@nuxtjs/composition-api'; import CustomSelect from '@/components/shared/CustomSelect'; import Vuetify from 'vuetify'; const localVue = createLocalVue(); localVue.use(CompositionApi); let vuetify; beforeEach(() => { jest.clearAllMocks(); vuetify = new Vuetify(); }); describe('test select component', () => { test('Mounts correclty', () => { const wrapper = mount(CustomSelect, { localVue, vuetify, }); expect(wrapper.vm).toBeTruthy(); }); });
当前Jest配置
// jest.config.js module.exports = { globalSetup: '<rootDir>/jest.setup.js', setupFiles: ['<rootDir>/tests/jest.init.js'], testEnvironment: 'jsdom', moduleNameMapper: { '^@/(.*)$': '<rootDir>/$1', '^~/(.*)$': '<rootDir>/$1', '^vue$': 'vue/dist/vue.common.js', '^@nuxtjs/composition-api$': '@nuxtjs/composition-api/dist/runtime/index.js', }, moduleFileExtensions: ['js', 'vue', 'json'], transform: { '^.+\\.js$': 'babel-jest', '.*\\.(vue)$': 'vue-jest', '^.+\\.ts?$': 'ts-jest', '.+\\.(css|sass|scss|png|jpg|ttf|woff|woff2)$': 'jest-transform-stub', }, transformIgnorePatterns: [ '<rootDir>/node_modules/(?!(@nuxtjs/composition-api)/)', ], snapshotSerializers: ['jest-serializer-vue'], testMatch: ['<rootDir>/tests/unit/**/*.spec.js'], };
package.json相关配置
{ "scripts": { "test": "jest", "test:watch": "jest --watch" }, "engines": { "npm": "8.11", "node": "16.16" }, "dependencies": { "@babel/eslint-parser": "^7.18.9", "@nuxt/types": "^2.15.8", "@nuxt/typescript-build": "^2.1.0", "@nuxtjs/composition-api": "^0.33.1", "@nuxtjs/vuetify": "^1.12.3", "@vueuse/core": "^9.3.1", "flush-promises": "^1.0.2", "jest-environment-jsdom": "^28.1.3", "jest-mock-axios": "^4.7.0-beta", "nuxt": "^2.15.8" }, "devDependencies": { "@babel/core": "^7.19.1", "@babel/preset-env": "^7.19.1", "@faker-js/faker": "^7.6.0", "@vue/server-test-utils": "^1.3.0", "@vue/test-utils": "^1.3.0", "babel-core": "^7.0.0-bridge.0", "babel-jest": "^28.1.3", "eslint": "^8.20.0", "jest": "^28.1.3", "jest-cli": "^28.1.3", "jest-serializer-vue": "^2.0.2", "jest-transform-stub": "^2.0.0", "mockdate": "^3.0.2", "vue-jest": "^3.0.7" } }
已尝试方案
已尝试Jest文档中的多种方案,包括配置transformIgnorePatterns、moduleNameMapper、启用ECMAScript Modules,但均无效。
需求
求Vue 2.7 + Nuxt + Vuetify环境下,测试Composition API组件的可行配置方案。
解决方案
1. 移除冗余的Composition API依赖
Vue 2.7已内置Composition API,无需再依赖@nuxtjs/composition-api,先卸载该包:
npm uninstall @nuxtjs/composition-api
同时修改测试代码,去掉相关注册逻辑:
import { mount, createLocalVue } from '@vue/test-utils'; import CustomSelect from '@/components/shared/CustomSelect'; import Vuetify from 'vuetify'; const localVue = createLocalVue(); let vuetify; beforeEach(() => { jest.clearAllMocks(); vuetify = new Vuetify(); }); describe('test select component', () => { test('Mounts correctly', () => { const wrapper = mount(CustomSelect, { localVue, vuetify, }); expect(wrapper.vm).toBeTruthy(); }); });
2. 适配Vue 2.7的Jest依赖更新
当前vue-jest@3.0.7不支持Vue 2.7,需要安装适配版本:
npm install vue-jest@5.0.0-alpha.10 --save-dev
3. 调整Jest核心配置
修改jest.config.js如下:
module.exports = { globalSetup: '<rootDir>/jest.setup.js', setupFiles: ['<rootDir>/tests/jest.init.js'], testEnvironment: 'jsdom', moduleNameMapper: { '^@/(.*)$': '<rootDir>/$1', '^~/(.*)$': '<rootDir>/$1', '^vue$': 'vue/dist/vue.esm.js', }, moduleFileExtensions: ['js', 'vue', 'json', 'ts', 'tsx'], transform: { '^.+\\.tsx?$': 'ts-jest', '^.+\\.vue$': 'vue-jest', '^.+\\.js$': 'babel-jest', '.+\\.(css|sass|scss|png|jpg|ttf|woff|woff2)$': 'jest-transform-stub', }, transformIgnorePatterns: [ '<rootDir>/node_modules/(?!(vuetify|@vueuse/core)/)', ], snapshotSerializers: ['jest-serializer-vue'], testMatch: ['<rootDir>/tests/unit/**/*.spec.js'], };
关键调整点:
- 新增
ts/tsx到文件扩展名列表 - 调整transform顺序,让TypeScript优先处理
- 更新Vue的映射文件为ES模块版本
- 扩展
transformIgnorePatterns,让Vuetify和VueUse包能被转译
4. 配置Babel适配环境
在项目根目录创建babel.config.js:
module.exports = { presets: [ ['@babel/preset-env', { targets: { node: 'current', }, }], ], };
5. 完善Vuetify测试环境
在jest.setup.js中导入Vuetify全局样式:
import 'vuetify/dist/vuetify.min.css';
在tests/jest.init.js中全局注册Vuetify:
import Vue from 'vue'; import Vuetify from 'vuetify'; Vue.use(Vuetify);
6. 验证测试运行
执行测试命令:
npm run test
内容的提问来源于stack exchange,提问作者Eugene
相关产品推荐
相关产品推荐

