Karma + Webpack(babel-loader)+ ES6"意外的令牌导入"

时间:2016-07-19 14:30:49

标签: javascript ecmascript-6 webpack karma-runner babeljs

/ edit:我完全剥离了配置,以证明问题。我还向GitHub上传了一个可以结账的工作项目,所以你可以亲自看看。

GitHub上有问题的用例:webpack-angular15-es6-karmadownload 7z archive

npm install
npm run build
npm run test

我知道有几个相关的问题,但世界变化如此之快,因此有很多因素/依赖关系,我无法用当前提出的解决方案解决这个问题。

我有一个webpack配置,可以处理我的所有源代码,但效果很好。

为了进行测试,我重用该配置来处理一个加载源和测试文件的中央入口脚本。我找不到另一种方法将我的源代码中的模块导入到我的测试代码中进行测试。

Karma可以重新使用我的webpack配置,但浏览器会在打开后立即报告错误。

源代码使用ES6导入和webpack require语句。

的package.json:

  

npm run build>>> webpack --config webpack.config.js --display-error-details --colors --progress

     

npm run test>>> karma start --single-run --no-auto-watch karma.config.js

{
  "name": "ProblemDemo",
  "scripts": {
    "build": "rimraf dist && webpack --config webpack.config.js --display-error-details --colors --progress",
    "test": "karma start --single-run --no-auto-watch karma.config.js"
  },
  "dependencies": {
    "angular": "^1.5.7",
    "angular-filter": "^0.5.8"
  },
  "devDependencies": {
      "webpack": "1.13.1",
      "html-loader": "0.4.3",
      "babel-loader": "5.3.2",
      "html-webpack-plugin": "1.6.1",
      "rimraf": "^2.5.3",
      "run-sequence": "1.1.2",
      "jasmine-core": "^2.4.1",
      "karma": "^0.13.19",
      "karma-chrome-launcher": "^0.2.2",
      "karma-coverage": "^0.5.3",
      "karma-jasmine": "^0.3.6",
      "karma-webpack": "^1.7.0",
      "loader-utils": "^0.2.12"
  }
}

karma.config.js:

module.exports = function (config) {
    config.set({
        browsers: ['Chrome'],
        coverageReporter: {
            reporters: [
                { type: 'html', subdir: 'html' },
                { type: 'lcovonly', subdir: '.' }
            ]
        },
        files: ['./tests.webpack.js'],
        frameworks: ['jasmine'],
        preprocessors: { './tests.webpack.js': ['webpack'] },
        reporters: ['progress', 'coverage'],
        webpack: configureWebpack()
    });

    function configureWebpack(webpackConfigFunction) {
        var webpackConfig = require('./webpack.config');
        webpackConfig.entry = undefined; // karma will pass the proper argument for entry
        return webpackConfig;
    }
};

你可以看到我没有使用karma-babel插件:我不确定为什么我需要那些,看到我已经有一个带有import / require语句的代码的工作版本。

test_entry.js:

var testsContext = require.context('./test', true, /\.js$/);
testsContext.keys().forEach(testsContext);

var srcContext = require.context('./app', true, /\.js$/);
srcContext.keys().forEach(srcContext);

webpack构建成功顺利(并发出 test_entry.js 预期文件大小的块),但随后Karma打开Chrome,一旦页面加载,我就会受到欢迎以下错误:

  

Chrome 51.0.2704(Windows 7 0.0.0)错误

     

未捕获的SyntaxError:意外的令牌导入

     

at the_path / test_entry.js:41

test_entry.js 没有41行,并且不包含import语句,无论如何都应该处理它们。出了什么问题?

如果你想知道webpack配置:



// webpack.config.js, works perfectly for normal builds but not with Karma
var path = require('path');
var webpack = require('webpack');
var HtmlWebpackPlugin = require('html-webpack-plugin');

module.exports = {
	debug: true,
	entry: {
		app: ['./app/index.js'],
		vendor: ['./app/vendor.js']
	},
	output: {
		path: path.join(__dirname, 'dist'),
		filename: 'js/[name].js'
	},
	plugins: [
		new HtmlWebpackPlugin({
			template: './app/index.html',
			inject: 'body',
			minify: false
		}),
		new webpack.optimize.CommonsChunkPlugin('vendor', 'js/vendor.js'),
		new webpack.SourceMapDevToolPlugin({
			filename: '[file].map',
			exclude: /vendor/
		})
	],
	resolve: {
		extensions: ['', '.js'],
		alias: {
			app: path.join(__dirname, 'app')
		}
	},
	module: {
		loaders: [
			{
				test: /\.js$/,
				loader: 'babel-loader',
				include: path.join(__dirname, 'app'),
				exclude: path.join(__dirname, 'node_modules')
			},
			{
				test: /\.html$/,
				loader: 'html-loader'
			}
		]
	},
	resolveLoader: {
		root: path.join(__dirname, 'node_modules')
	},
};




如果您想查看 test_entry.js 所需的测试,我无法运行该测试:



import jasmine from 'jasmine-core';
import readableNumberFilter from './file_path/readableNumber.filter';

// for some reason needed, or else unexpected token errors during build:
var describe = jasmine.describe;
var it = jasmine.it;
var expect = jasmine.expect;

describe('readableNumber Filter', function () {
	describe('readableNumber Filter formatting', () => {
		it('it should support optional arguments', function () {
			expect(readableNumberFilter("50.3")).toEqual("50,30");
		});
	});
});




编辑20-7-2016

问题仍然存在,更新的babel-loader依赖项(包括设置es2015预设选项)。 " babel-core":" ^ 6.11.4"," babel-loader":" ^ 6.2.4"," babel-preset-es2015":" ^ 6.9.0",

1 个答案:

答案 0 :(得分:32)

问题在于您没有转发测试源 - 文件src/global/filters/dateFormat.filter.spec.js未被编译。

您需要更改此加载程序配置:

{
    test: /\.js$/,
    loader: 'babel-loader',
    include: path.join(__dirname, 'app'),
    exclude: path.join(__dirname, 'node_modules')
},

如下所示,为了使其有效:

{
    test: /\.js$/,
    loader: 'babel-loader',
    include: [
        path.join(__dirname, 'app'),
        path.join(__dirname, 'test')
    ],
    exclude: path.join(__dirname, 'node_modules')
},

webpack.optimize.CommonsChunkPlugin插件也存在问题 - 它应该被禁用为业力: https://github.com/webpack/karma-webpack/issues/22

比禁用此插件后,您的测试文件中存在错误:

import jasmine from 'jasmine-core';

import readableNumberFilter from 'readableNumber.filter';

var describe = jasmine.describe;
var it = jasmine.it;
var expect = jasmine.expect;

describe('readableNumber Filter', function () {
    describe('readableNumber Filter formatting', () => {
        it('it should support optional arguments', function () {
            expect(readableNumberFilter("50.3")).toEqual("50,30");
        });
    });
});

此测试中的错误很少:

  1. import jasmine from 'jasmine-core'; - 您不应该这样做(业力会做,也会添加describeitexpect
  2. import readableNumberFilter from 'readableNumber.filter'; - 这不是你如何实例化角度服务来测试它们的方式。
  3. 你应该这样做(这个测试实际上适用于上面提到的所有修复):

    import angular from 'angular';
    import 'angular-mocks';
    
    import testModule from '../../../../app/src/global/index';
    
    const { module, inject } = angular.mock;
    
    describe('readableNumber Filter', () => {
        beforeEach(module(testModule));
    
        let $filter;
    
        beforeEach(inject((_$filter_) => {
            $filter = _$filter_;
        }));
    
        describe('readableNumber Filter formatting', () => {
            it('it should support optional arguments', () => {
                const result = $filter('readableNumber')("50.3");
                expect(result).toEqual("50,30");
            });
        });
    });
    

    注意:您需要安装模块angular-mocks;

    要支持代码覆盖率报告,您需要配置测试webpack配置以使用babel-istanbul-loader之类的内容。顺便说一下,你还需要升级到Babel6。

    此外,您还需要使webpack配置更具可配置性(测试和生产的配置需要略有不同)。

    我已向您发送了包含所有这些修复程序的提示请求:https://github.com/bbottema/webpack-angular15-es6-karma/pull/1

    关于使用webpack构建angular 1.x项目,包括通过karma进行代码覆盖测试 - 也许您会对我的项目感兴趣:https://github.com/zxbodya/angular-webpack-seed - 它是具有所有必需配置的入门模板。