mirror of
https://github.com/apache/zeppelin
synced 2026-05-24 09:38:26 +00:00
### What is this PR for? Improved testing environment for zeppelin-web - added `test:watch` command for continuous testing - displaying coverage report in console - e2e testing in zeppelin-web (can be written easily compare to the zeppelin-server integration tests. For example: [home.spec.js](f90deb4bf3/zeppelin-web/e2e/home.spec.js)) This PR adds [a zeppelin-web specific travis profile](ad08a3bc0d/.travis.yml (L55)) and it usually takes 8-9 mins to execute unit + e2e tests (zeppelin-web) - https://travis-ci.org/1ambda/zeppelin/jobs/252453901 #### Details - the headless chrome browser works with chromedriver 2.29+ (c75dbfd25c) - in the case of ubuntu precise (our travis container), should use `/usr/bin/chromium-browser` - `xvfb` is required, please refer https://docs.travis-ci.com/user/gui-and-headless-browsers/#Using-xvfb-to-Run-Tests-That-Require-a-GUI and https://iamakulov.com/notes/install-google-chrome-on-travis/#what-does-the-code-mean - for protractor conf, please check https://github.com/travis-ci/travis-ci/issues/7650#issuecomment-302467188 - can't install stable version of chrome, precise (12.04) support was dropped by chrome - chromium-browser (37.0) is shipped by default in precise and chromedriver version 2.11 is compatible with it. (https://support.saucelabs.com/hc/en-us/articles/225095307-Chromedriver-version-for-each-Chrome-browser-version, https://github.com/travis-ci/travis-ci/issues/5899) ### What type of PR is it? [Improvement] ### Todos * [x] - `test:watch` * [x] - displaying coverage reports in console * [x] - e2e testing in zeppelin-web ### What is the Jira issue? [ZEPPELIN-2342](https://issues.apache.org/jira/browse/ZEPPELIN-2342) ### How should this be tested? CI should be green. If you want to test locally, - stop zeppelin which is running on localhost:8080 - `mvn package -DskipTests -DskipRat -Pweb-ci -B` - `mvn verify -DskipRat -pl 'zeppelin-web' -Pweb-ci -Pweb-e2e -B` #### Screenshots (coverage)  #### Screenshots (e2e)  ### Questions: * Does the licenses files need update? - NO * Is there breaking changes for older versions? - NO * Does this needs documentation? - YES, updated Author: 1ambda <[email protected]> Closes #2477 from 1ambda/ZEPPELIN-2342/differentiate-unit-and-integration-testing and squashes the following commits:ad08a3bc[1ambda] fix: Restore all other pfoeilsb6ff6d91[1ambda] fix: Use 2.30832cffb6[1ambda] fix: Use 2.27 for chrome driver4d82f03f[1ambda] fix: use 2.30 chromedriver93cc90b8[1ambda] fix: run unit test only when web-e2e enabled0911afbe[1ambda] fix: Update chromedriver version893f67ee[1ambda] fix: Set ignoreSync false for angular app9b91ae28[1ambda] fix: restore all other profilesdd300c24[1ambda] fix: split ifa5deed0d[1ambda] fix: Run xvf ni foreground8d1ab5bc[1ambda] fix: Remove sleep 3s9a81fa19[1ambda] fix: Add space between & and ;e924e760[1ambda] fix: pass test, use 2 dists58cfb238[1ambda] fix: test 2 dist0dc0304a[1ambda] fix: Use trusty for the second profile2bf62085e[1ambda] fix: Remove version61a7f9ee[1ambda] fix: DO NOT USE CHROME_BIN8926cd80[1ambda] fix: use 2.119c20a447[1ambda] fix: print chrome versionf961a90f[1ambda] use before_install9ed1e12b[1ambda] set info for testefc831c1[1ambda] fix: remove headlessdb016a31[1ambda] fix: use headless chrome in local481528f4[1ambda] fix: use precise5a096da1[1ambda] fix: use chromium-browserfcfa9c09[1ambda] fix: required282c83ec[1ambda] fix: use beta5a0d1118[1ambda] fix: use trusty93fb571c[1ambda] fix: ls usr binaff874f8[1ambda] fix: use no-sandbox for sudo false contrainer7d454a57[1ambda] fix: Run xvfb in background23e5670f[1ambda] fix: use beta chrome3e9f494f[1ambda] fix: Use /usr/bin/chrome55faa0e0[1ambda] fix: Use google-chrome-stale7da9845c[1ambda] WIP: Remove all other profilesa45f131c[1ambda] WIP: pass all tests628ff341[1ambda] fix: Set chromedriver version763f3e26[1ambda] fix: Set env94506681[1ambda] fix: redirect dbus into nullbcac8a4a[1ambda] fix: Remove sandboxfacf4c1c[1ambda] fix: Remove -X20a8cfd7[1ambda] fix: use no-sandbox0662f928[1ambda] fix: Set -X for webfc9d31f5[1ambda] fix: Use CHROME_BIN24acb8e22[1ambda] fix: Use CHROME_BIN46994918[1ambda] fix: Set info for e2e905e6ad6[1ambda] fix: Install chrome from source7f5abfdf[1ambda] fix: before_start1f345aea[1ambda] fix: use headlessdd115c39[1ambda] fix: use direct connect7d53d51f[1ambda] fix Remove chrome optioneb9f0e8d[1ambda] fix: Set direct connect false7c69f7a1[1ambda] fix: Set chromeOnly for protractord5e62e76[1ambda] fix: Set chrome driver version https://github.com/angular/angular-cli/issues/2176\#issuecomment-253496181f94a665f[1ambda] fix: Modify timeout for protractor35b6fb16[1ambda] WIP: Remove -X option to second job5189807b[1ambda] chore: Add TEST_MODULES in travis.ymle354b1b1[1ambda] chore: DO NOT rebuild web when e2e enabledb6d730fc[1ambda] fix: echo commandsin travis.yml6907c50d[1ambda] chore: Ingmore except web in test build9f13d611[1ambda] chore: Use usual test build command4ef0a2c2[1ambda] chore: Remove useless mvn setting26ef7087[1ambda] fix: use prebuilt phantomf90deb4b[1ambda] chore: Move web e2e into zeppelin-web40ac076e[1ambda] chore: New profile for e2e test only7703615b[1ambda] WIP: Add -X to the second travis profile0c2c1ecb[1ambda] chore: Add web-e2e profile to mvnca2b1703[1ambda] WIP: add -e mvn option to the second profile0c09727e[1ambda] fix: Remove -X option from selenium profile0907d728[1ambda] chore: Ingnore protractor conf in RAT2ed39733[1ambda] fix: set gecko false for webdriver manager. See https://github.com/angular/webdriver-manager/issues/216eb447ef8[1ambda] WIP: add -X log to selenium profioe742bb961[1ambda] chore: Exclude e2e specs from RATb5a17a4b[1ambda] chore: Bind browser e2e test into CI process76f4f584[1ambda] docs: Update test section in zeppelin-web/README.md15473de6[1ambda] test: Add a basic e2e test for home39dc77e4[1ambda] chore: Add test:watch commande70281ba[1ambda] feat: Use spec repoter and coverage
319 lines
10 KiB
JavaScript
319 lines
10 KiB
JavaScript
/*
|
|
* Licensed to the Apache Software Foundation (ASF) under one or more
|
|
* contributor license agreements. See the NOTICE file distributed with
|
|
* this work for additional information regarding copyright ownership.
|
|
* The ASF licenses this file to You under the Apache License, Version 2.0
|
|
* (the "License"); you may not use this file except in compliance with
|
|
* the License. You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
'use strict';
|
|
|
|
var path = require('path');
|
|
var webpack = require('webpack');
|
|
var autoprefixer = require('autoprefixer');
|
|
var HtmlWebpackPlugin = require('html-webpack-plugin');
|
|
var ExtractTextPlugin = require('extract-text-webpack-plugin');
|
|
var CopyWebpackPlugin = require('copy-webpack-plugin');
|
|
var InsertLiveReloadPlugin = function InsertLiveReloadPlugin(options) {
|
|
this.options = options || {};
|
|
this.port = this.options.port || 35729;
|
|
this.hostname = this.options.hostname || 'localhost';
|
|
}
|
|
var express = require('express');
|
|
var stringReplacePlugin = require('string-replace-webpack-plugin');
|
|
|
|
InsertLiveReloadPlugin.prototype.autoloadJs = function autoloadJs() {
|
|
return
|
|
};
|
|
|
|
InsertLiveReloadPlugin.prototype.scriptTag = function scriptTag(source) {
|
|
var reloadScriptTag = [
|
|
'// webpack-livereload-plugin',
|
|
'(function() {',
|
|
' if (typeof window === "undefined") { return };',
|
|
' var id = "webpack-livereload-plugin-script";',
|
|
' if (document.getElementById(id)) { return; }',
|
|
' var el = document.createElement("script");',
|
|
' el.id = id;',
|
|
' el.async = true;',
|
|
' el.src = "http://' + this.hostname + ':' + this.port + '/livereload.js";',
|
|
' document.getElementsByTagName("head")[0].appendChild(el);',
|
|
'}());',
|
|
''
|
|
].join('\n');
|
|
return reloadScriptTag + source;
|
|
};
|
|
|
|
InsertLiveReloadPlugin.prototype.applyCompilation = function applyCompilation(compilation) {
|
|
compilation.mainTemplate.plugin('startup', this.scriptTag.bind(this));
|
|
};
|
|
|
|
InsertLiveReloadPlugin.prototype.apply = function apply(compiler) {
|
|
this.compiler = compiler;
|
|
compiler.plugin('compilation', this.applyCompilation.bind(this));
|
|
};
|
|
|
|
/**
|
|
* Env
|
|
* Get npm lifecycle event to identify the environment
|
|
*/
|
|
var ENV = process.env.npm_lifecycle_event;
|
|
var isTest = ENV === 'test';
|
|
var isProd = ENV.startsWith('build')
|
|
var isCI = ENV === 'build:ci'
|
|
|
|
module.exports = function makeWebpackConfig () {
|
|
/**
|
|
* Config
|
|
* Reference: http://webpack.github.io/docs/configuration.html
|
|
* This is the object where all configuration gets set
|
|
*/
|
|
var config = {};
|
|
|
|
/**
|
|
* Entry
|
|
* Reference: http://webpack.github.io/docs/configuration.html#entry
|
|
* Should be an empty object if it's generating a test build
|
|
* Karma will set this when it's a test build
|
|
*/
|
|
config.entry = isTest ? {} : {
|
|
app: './src/index.js'
|
|
};
|
|
|
|
var serverPort = process.env.SERVER_PORT || 8080;
|
|
var webPort = process.env.WEB_PORT || 9000;
|
|
|
|
/**
|
|
* Output
|
|
* Reference: http://webpack.github.io/docs/configuration.html#output
|
|
* Should be an empty object if it's generating a test build
|
|
* Karma will handle setting it up for you when it's a test build
|
|
*/
|
|
config.output = isTest ? {} : {
|
|
// Absolute output directory
|
|
path: __dirname + '/dist',
|
|
|
|
// Output path from the view of the page
|
|
// Uses webpack-dev-server in development
|
|
publicPath: isProd ? '' : 'http://localhost:' + webPort + '/',
|
|
|
|
// Filename for entry points
|
|
// Only adds hash in build mode
|
|
filename: isProd ? '[name].[hash].js' : '[name].bundle.js',
|
|
|
|
// Filename for non-entry points
|
|
// Only adds hash in build mode
|
|
chunkFilename: isProd ? '[name].[hash].js' : '[name].bundle.js'
|
|
};
|
|
|
|
/**
|
|
* Devtool
|
|
* Reference: http://webpack.github.io/docs/configuration.html#devtool
|
|
* Type of sourcemap to use per build type
|
|
*/
|
|
if (isTest) {
|
|
config.devtool = 'inline-source-map';
|
|
} else if (isProd) {
|
|
config.devtool = 'source-map';
|
|
} else {
|
|
config.devtool = 'eval-source-map';
|
|
}
|
|
config.devtool = 'source-map';
|
|
|
|
/**
|
|
* Loaders
|
|
* Reference: http://webpack.github.io/docs/configuration.html#module-loaders
|
|
* List: http://webpack.github.io/docs/list-of-loaders.html
|
|
* This handles most of the magic responsible for converting modules
|
|
*/
|
|
|
|
// Initialize module
|
|
config.module = {
|
|
preLoaders: [],
|
|
loaders: [{
|
|
// headroom 0.9.3 doesn't work with webpack
|
|
// https://github.com/WickyNilliams/headroom.js/issues/213#issuecomment-281106943
|
|
test: require.resolve('headroom.js'),
|
|
loader: 'imports-loader?this=>window,define=>false,exports=>false'
|
|
}, {
|
|
// JS LOADER
|
|
// Reference: https://github.com/babel/babel-loader
|
|
// Transpile .js files using babel-loader
|
|
// Compiles ES6 and ES7 into ES5 code
|
|
test: /\.js$/,
|
|
loaders: ['ng-annotate', 'babel-loader'],
|
|
exclude: /(node_modules|bower_components)/,
|
|
}, {
|
|
// CSS LOADER
|
|
// Reference: https://github.com/webpack/css-loader
|
|
// Allow loading css through js
|
|
//
|
|
// Reference: https://github.com/postcss/postcss-loader
|
|
// Postprocess your css with PostCSS plugins
|
|
test: /\.css$/,
|
|
// Reference: https://github.com/webpack/extract-text-webpack-plugin
|
|
// Extract css files in production builds
|
|
//
|
|
// Reference: https://github.com/webpack/style-loader
|
|
// Use style-loader in development.
|
|
loader: ExtractTextPlugin.extract('style-loader', 'css-loader?sourceMap!postcss-loader')
|
|
}, {
|
|
// ASSET LOADER
|
|
// Reference: https://github.com/webpack/file-loader
|
|
// Copy png, jpg, jpeg, gif, svg, woff, woff2, ttf, eot files to output
|
|
// Rename the file using the asset hash
|
|
// Pass along the updated reference to your code
|
|
// You can add here any file extension you want to get copied to your output
|
|
test: /\.(png|jpg|jpeg|gif|svg|woff|woff2|ttf|eot)$/,
|
|
loader: 'file'
|
|
}, {
|
|
// HTML LOADER
|
|
// Reference: https://github.com/webpack/raw-loader
|
|
// Allow loading html through js
|
|
test: /\.html$/,
|
|
loader: 'raw'
|
|
}, {
|
|
// STRING REPLACE PLUGIN
|
|
// reference: https://www.npmjs.com/package/string-replace-webpack-plugin
|
|
// Allow for arbitrary strings to be replaced as part of the module build process
|
|
// Configure replacements for file patterns
|
|
test: /index.html$/,
|
|
loader: stringReplacePlugin.replace({
|
|
replacements: [{
|
|
pattern: /WEB_PORT/ig,
|
|
replacement: function (match, p1, offset, string) {
|
|
return webPort;
|
|
}
|
|
}
|
|
]})
|
|
}],
|
|
postLoaders: [
|
|
{
|
|
// COVERAGE
|
|
test: /\.js$/,
|
|
exclude: /(node_modules|bower_components|\.test\.js)/,
|
|
loader: 'istanbul-instrumenter'
|
|
}
|
|
]
|
|
};
|
|
|
|
/**
|
|
* PostCSS
|
|
* Reference: https://github.com/postcss/autoprefixer-core
|
|
* Add vendor prefixes to your css
|
|
*/
|
|
config.postcss = [
|
|
autoprefixer({
|
|
browsers: ['last 2 version']
|
|
})
|
|
];
|
|
|
|
/**
|
|
* Plugins
|
|
* Reference: http://webpack.github.io/docs/configuration.html#plugins
|
|
* List: http://webpack.github.io/docs/list-of-plugins.html
|
|
*/
|
|
config.plugins = [
|
|
// Reference: https://github.com/webpack/extract-text-webpack-plugin
|
|
// Extract css files
|
|
// Disabled when in test mode or not in build mode
|
|
new ExtractTextPlugin('[name].[hash].css', {disable: !isProd}),
|
|
];
|
|
|
|
// Skip rendering index.html in test mode
|
|
if (!isTest) {
|
|
// Reference: https://github.com/ampedandwired/html-webpack-plugin
|
|
// Render index.html
|
|
config.plugins.push(
|
|
new HtmlWebpackPlugin({
|
|
template: './src/index.html',
|
|
inject: 'body'
|
|
}),
|
|
// Reference: https://webpack.github.io/docs/list-of-plugins.html#defineplugin
|
|
new webpack.DefinePlugin({
|
|
'process.env': {
|
|
HELIUM_BUNDLE_DEV: process.env.HELIUM_BUNDLE_DEV,
|
|
SERVER_PORT: serverPort,
|
|
WEB_PORT: webPort,
|
|
PROD: isProd,
|
|
BUILD_CI: (isCI) ? JSON.stringify(true) : JSON.stringify(false)
|
|
}
|
|
})
|
|
)
|
|
}
|
|
|
|
// Add build specific plugins
|
|
if (isProd) {
|
|
config.plugins.push(
|
|
// Reference: http://webpack.github.io/docs/list-of-plugins.html#noerrorsplugin
|
|
// Only emit files when there are no errors
|
|
new webpack.NoErrorsPlugin(),
|
|
|
|
// Reference: http://webpack.github.io/docs/list-of-plugins.html#dedupeplugin
|
|
// Dedupe modules in the output
|
|
new webpack.optimize.DedupePlugin(),
|
|
|
|
// Reference: http://webpack.github.io/docs/list-of-plugins.html#uglifyjsplugin
|
|
// Minify all javascript, switch loaders to minimizing mode
|
|
new webpack.optimize.UglifyJsPlugin({
|
|
mangle: { screw_ie8: true },
|
|
preserveComments: 'some',
|
|
compress: {
|
|
screw_ie8: true,
|
|
warnings: false,
|
|
sequences: true,
|
|
dead_code: true,
|
|
conditionals: true,
|
|
booleans: true,
|
|
unused: true,
|
|
if_return: true,
|
|
join_vars: true,
|
|
drop_console: true,
|
|
}
|
|
}),
|
|
|
|
// Copy assets from the public folder
|
|
// Reference: https://github.com/kevlened/copy-webpack-plugin
|
|
new CopyWebpackPlugin([])
|
|
)
|
|
} else {
|
|
config.plugins.push(
|
|
new InsertLiveReloadPlugin(),
|
|
// reference: https://www.npmjs.com/package/string-replace-webpack-plugin
|
|
new stringReplacePlugin()
|
|
)
|
|
}
|
|
|
|
/**
|
|
* Dev server configuration
|
|
* Reference: http://webpack.github.io/docs/configuration.html#devserver
|
|
* Reference: http://webpack.github.io/docs/webpack-dev-server.html
|
|
*/
|
|
config.devServer = {
|
|
historyApiFallback: true,
|
|
port: webPort,
|
|
inline: true,
|
|
hot: true,
|
|
progress: true,
|
|
contentBase: './src',
|
|
setup: function(app) {
|
|
app.use('**/bower_components/', express.static(path.resolve(__dirname, './bower_components/')));
|
|
app.use('**/app/', express.static(path.resolve(__dirname, './src/app/')));
|
|
app.use('**/assets/', express.static(path.resolve(__dirname, './src/assets/')));
|
|
app.use('**/fonts/', express.static(path.resolve(__dirname, './src/fonts/')));
|
|
app.use('**/components/', express.static(path.resolve(__dirname, './src/components/')));
|
|
},
|
|
stats: 'minimal',
|
|
};
|
|
|
|
return config;
|
|
}();
|