Vue-test-utils не может найти `Set()`: ReferenceError: Невозможно найти переменную: Set
В настоящее время я пытаюсь написать несколько тестов для компонента Vue. Однако, когда я пытаюсь запустить тесты, он выдает следующее сообщение:
[BABEL] Note: The code generator has deoptimised the styling of /home/bono/dev/git_repos/hypernode-control-panel/hncp/vue/common/tests/unit/UpdateElementRadio.spec.es5.js as it exceeds the max of 500KB.
13 12 2018 15:52:18.339:INFO [karma-server]: Karma v3.1.3 server started at http://0.0.0.0:9876/
13 12 2018 15:52:18.341:INFO [launcher]: Launching browsers PhantomJS with concurrency unlimited
13 12 2018 15:52:18.344:INFO [launcher]: Starting browser PhantomJS
13 12 2018 15:52:18.594:INFO [PhantomJS 2.1.1 (Linux 0.0.0)]: Connected on socket fBfbs8v8mD1WMsLOAAAA with id 26571362
ERROR LOG: '[Vue warn]: Error in config.errorHandler: "ReferenceError: Can't find variable: Set"'
ERROR LOG: ReferenceError: Can't find variable: Set
patchRenderMixin
callHook
_init
VueComponent
createComponentInstanceForVnode
init
createComponent
createElm
patch
_update
updateComponent
get
Watcher
mountComponent
$mount
mount
shallowMount
callFn@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4550:25
run@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4542:13
runTest@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:5078:13
http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:5196:19
next@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4992:16
http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:5002:11
next@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4926:16
http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4970:9
timeslice@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:82:27
ERROR LOG: '[Vue warn]: Error in beforeCreate hook: "ReferenceError: Can't find variable: Set"
found in
---> <UpdateElementRadio> at hncp/vue/common/src/components/UpdateElementRadio.vue
<Root>'
ERROR LOG: ReferenceError: Can't find variable: Set
patchRenderMixin
callHook
_init
VueComponent
createComponentInstanceForVnode
init
createComponent
createElm
patch
_update
updateComponent
get
Watcher
mountComponent
$mount
mount
shallowMount
callFn@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4550:25
run@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4542:13
runTest@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:5078:13
http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:5196:19
next@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4992:16
http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:5002:11
next@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4926:16
http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:4970:9
timeslice@http://localhost:9876/base/node_modules/mocha/mocha.js?840d4fbbcc65a16cec39f9e25af2ea6d2cff68ea:82:27
UpdateElementRadio
✗ accepts label_text prop
Can't find variable: Set
patchRenderMixin
callHook
_init
VueComponent
createComponentInstanceForVnode
init
createComponent
createElm
patch
_update
updateComponent
get
Watcher
mountComponent
$mount
mount
shallowMount
PhantomJS 2.1.1 (Linux 0.0.0): Executed 1 of 1 (1 FAILED) ERROR (0.041 secs / 0.01 secs)
npm ERR! Test failed. See above for more details.
Это тест, который я пытаюсь запустить (обратите внимание, что это может быть немного бессмысленным тестом, я просто пытаюсь заставить вещи работать в первую очередь):
import Vue from 'vue'
import { expect } from 'chai';
import { shallowMount } from '@vue/test-utils';
import UpdateElementRadio from '../../src/components/UpdateElementRadio.vue';
describe('UpdateElementRadio', () => {
it('accepts label_text prop', () => {
shallowMount(UpdateElementRadio);
const vm = new Vue(UpdateElementRadio).$mount();
console.log(vm.props);
expect(vm.props.label_text).to.equal(String);
});
});
Я не слишком опытен в настройке этой вещи, но все работает нормально, когда я не пытаюсь использовать какую-либо mount
функция от vue-test-utils
, У меня такое чувство, что что-то не так с моей настройкой Babel или что-то в этом роде, так как это ссылка на es2015 (по крайней мере, я обнаружил, что пытался получить ее от lib.es2015
файл). Я пытался использовать разные предустановки Babel, но ни одна из них не работала (или выдавала больше ошибок). Я также проверил документы для @babel/preset-env
и я думаю, что это правильный пресет для использования.
Я поделюсь своим конфигом кармы, конфигом вебпака и package.json
также:
karma.conf.js:
// Karma configuration
// Generated on Thu Dec 13 2018 11:28:18 GMT+0100 (Central European Standard Time)
let webpackConfig = require('./webpack.config.js');
module.exports = function (config) {
config.set({
// base path that will be used to resolve all patterns (eg. files, exclude)
basePath: '',
// frameworks to use
// available frameworks: https://npmjs.org/browse/keyword/karma-adapter
frameworks: ['mocha'],
// list of files / patterns to load in the browser
files: [
'hncp/vue/**/tests/unit/*.spec.js'
],
// preprocess matching files before serving them to the browser
// available preprocessors: https://npmjs.org/browse/keyword/karma-preprocessor
preprocessors: {
'hncp/vue/**/tests/unit/*.spec.js': ['webpack', 'sourcemap', 'babel']
},
babelPreprocessor: {
options: {
presets: ['@babel/preset-env'],
sourceMap: 'inline',
},
filename: function (file) {
return file.originalPath.replace(/\.js$/, '.es5.js')
},
sourceFileName: function (file) {
return file.originalPath;
},
},
webpack: webpackConfig,
// test results reporter to use
// possible values: 'dots', 'progress'
// available reporters: https://npmjs.org/browse/keyword/karma-reporter
reporters: ['spec'],
plugins: [
'karma-phantomjs-launcher',
'karma-webpack',
'karma-sourcemap-loader',
'karma-mocha',
'karma-spec-reporter',
'karma-babel-preprocessor',
'karma-chai',
],
// web server port
port: 9876,
// enable / disable colors in the output (reporters and logs)
colors: true,
// level of logging
// possible values: config.LOG_DISABLE || config.LOG_ERROR || config.LOG_WARN || config.LOG_INFO || config.LOG_DEBUG
logLevel: config.LOG_INFO,
// enable / disable watching file and executing tests whenever any file changes
autoWatch: true,
// start these browsers
// available browser launchers: https://npmjs.org/browse/keyword/karma-launcher
browsers: ['PhantomJS'],
// Continuous Integration mode
// if true, Karma captures browsers, runs the tests and exits
singleRun: true,
// Concurrency level
// how many browser should be started simultaneous
concurrency: Infinity,
})
};
webpack.config.js:
var path = require ('path'); var webpack = require ('webpack'); var BundleTracker = require ('webpack-bundle-tracker'); const VueLoaderPlugin = require ('vue-loader / lib / plugin');
module.exports = {
context: __dirname,
mode: 'development',
entry: {
'hncp/order': ['./hncp/vue/order/src/main'],
},
output: {
path: path.resolve('./hncp/static/webpack_bundles/'),
filename: "[name].js"
},
module: {
rules: [
{ // Needed for loading Vue stuff
test: /\.vue$/,
loader: 'vue-loader'
},
{ // Needed for loading things like <style> tags (used inside Vue stuff)
test: /\.css$/,
loader: 'style-loader!css-loader'
},
{ // Needed for loading things like png files (used inside Vue templates)
test: /\.(eot|svg|png|ttf|woff|woff2)(\?\S*)?$/,
loader: 'file-loader'
},
{
test: /\.js$/,
exclude: /(node_modules|bower_components)/,
use: {
loader: 'babel-loader',
options: {
presets: ['@babel/preset-env']
}
}
}
]
},
plugins: [
new BundleTracker({filename: './webpack-stats.json'}),
new VueLoaderPlugin()
],
};
package.json:
{
"scripts": {
"test": "karma start --single-run"
},
"dependencies": {
"babel-preset-es2015": "^6.24.1",
"karma-cli": "^2.0.0",
"karma-phantomjs-launcher": "^1.0.4",
"vue-template-compiler": "^2.5.21"
},
"devDependencies": {
"@babel/core": "^7.2.0",
"@babel/preset-env": "^7.2.0",
"@vue/test-utils": "^1.0.0-beta.27",
"babel-loader": "^8.0.4",
"chai": "^4.2.0",
"css-loader": "^2.0.0",
"file-loader": "^2.0.0",
"karma": "^3.1.3",
"karma-babel-preprocessor": "^8.0.0-beta.0",
"karma-chai": "^0.1.0",
"karma-chrome-launcher": "^2.2.0",
"karma-mocha": "^1.3.0",
"karma-sourcemap-loader": "^0.3.7",
"karma-spec-reporter": "0.0.32",
"karma-webpack": "^3.0.5",
"mocha": "^5.2.0",
"style-loader": "^0.23.1",
"vue": "^2.5.21",
"vue-loader": "^15.4.2",
"vue-test-utils": "^1.0.0-beta.11",
"webpack": "^4.27.1",
"webpack-bundle-tracker": "^0.4.2-beta",
"webpack-cli": "^3.1.2"
}
}
Если попробуйте использовать $mount
от Vue
это отлично работает То есть:
import Vue from 'vue'
import { expect } from 'chai';
import { mount } from '@vue/test-utils';
import UpdateElementRadio from '../../src/components/UpdateElementRadio.vue';
describe('UpdateElementRadio', () => {
it('accepts label_text prop', () => {
const vm = new Vue(UpdateElementRadio).$mount();
console.log(vm);
expect(vm.props.label_text).to.equal(String);
});
});
Я знаю, что это немного на что смотреть, но не хватает идей о том, как это исправить.
редактировать
Это UpdateElementRadio
:
<template>
<div class="float-label">
<label>{{ label_text }}</label>
<input type="radio" :name="name" v-on:change="$emit('update-value', value)"/>
<slot></slot>
<div class="update-element-radio-content" style="float:right">
{{ value }}
</div>
</div>
</template>
<script>
export default {
name: 'UpdateElementRadio',
props: {
label_text: String,
name: String,
value: Number
},
};
</script>
2 ответа
Поэтому я выяснил, почему это происходит, когда оказывается, что виновником был PhantomJS. Поскольку он больше не разрабатывается активно, это также означает, что он не поддерживает ES6. Смотрите эту проблему на Github для той же проблемы, с которой я столкнулся.
Поэтому вместо этого я решил использовать Chrome для своих тестов и внес следующие изменения:
В karma.conf.js:
//Other config...
plugins: [
'karma-chrome-launcher',
...
]
//Other config...
browsers: ['ChromeHeadless'],
//Other config
В файле package.json убедитесь, что karma-chrome-launcher
установлено:
{
//other
"devDependencies": {
// Other...
"karma-chrome-launcher": "^2.2.0",
// Other...
}
}
Я думаю, что это связано с compact
флаг в babel, его значение по умолчанию составляет 500 КБ.
Вы можете изменить конфигурацию в .babelrc
{
"compact": false
// other config
}
Если у вас нет файла Babel, вы можете попробовать отредактировать веб-пакет
rules: [
{ // Needed for loading Vue stuff
test: /\.vue$/,
loader: 'vue-loader',
compact: false
},
{ // Needed for loading things like <style> tags (used inside Vue stuff)
test: /\.css$/,
loader: 'style-loader!css-loader',
compact: false
},
{ // Needed for loading things like png files (used inside Vue templates)
test: /\.(eot|svg|png|ttf|woff|woff2)(\?\S*)?$/,
loader: 'file-loader'
},
{
test: /\.js$/,
exclude: /(node_modules|bower_components)/,
use: {
loader: 'babel-loader',
options: {
presets: ['@babel/preset-env']
}
},
compact: false
}
]