我的项目环境是,使用redux和redux-saga进行响应,webpack Jenkins用于CI / CD 一个月以来,我们遇到了一个奇怪的问题,Jenkins(webpack)的构建和部署成功,但是当我访问门户网站时,由于低于Javascript错误,该页面显示空白页面
Uncaught ReferenceError: saga is not defined
at Module.1148 (main.44c97d10353333934fe5.bundle.js:1)
at __webpack_require__ (manifest.6a34ff8be70a737e5aa6.bundle.js:1)
at Object.646 (main.44c97d10353333934fe5.bundle.js:1)
at __webpack_require__ (manifest.6a34ff8be70a737e5aa6.bundle.js:1)
at checkDeferredModules (manifest.6a34ff8be70a737e5aa6.bundle.js:1)
at Array.webpackJsonpCallback [as push] (manifest.6a34ff8be70a737e5aa6.bundle.js:1)
at vendor.fef8d73f71dc764a97a1.bundle.js:1
当在代码库中查看失败的文件时,sagas.js文件具有“ export default sagas”,因此在构建过程中sagas中的s被截断了,因此出现了javascript错误
在Jenkins中重新运行相同的构建后,它将生成一个干净的构建,并且应用程序可以正常运行而不会出现上述错误
奇怪的是,这种行为并非在它是间歇性的每个构建中都会发生
另一个与此类似的错误
built version of utag.js with errors
actual version of utag.js from code base
主要问题是我无法在本地复制该问题,我在分支上运行了webpack构建,这导致javascript错误-但没有运气,每次webpack在本地生成一个干净的构建
这是我的配置文件
Package.json
{
"name": "portal",
"version": "0.1.0",
"private": true,
"scripts": {
"start": "webpack-dev-server --open --inline --progress --env development --config webpack/dev.config.js",
"build:prod": "webpack --env production --config webpack/prod.config.js",
"build:test": "webpack --env test --config webpack/prod.config.js",
"stylelint": "stylelint '**/*.scss', '**/*.css'",
"stylelint:silentexit": "stylelint '**/*.scss', '**/*.css'; exit 0",
"jslint": "eslint . --fix",
"jslint:silentexit": "eslint .; exit 0",
"test": "npm run jslint && npm run test:unit",
"test:unit": "jest --colors",
"test:watch": "jest --watch --passWithNoTests",
"test:coverage": "jest --coverage -u --colors",
"storybook": "start-storybook -p 9001 -c .storybook",
"generateSvgIconComponents": "styled-svg src/icons/*.svg --size=small:18x18 --size=medium:24x24 --size=large:36x36"
},
"eslintConfig": {
"extends": "react-app"
},
"browserslist": [
">0.2%",
"not dead",
"not ie <= 10",
"not op_mini all"
],
"dependencies": {
"@babel/polyfill": "^7.4.4",
"@rebass/components": "^4.0.0-1",
"acorn": "^6.2.0",
"babel-plugin-react-css-modules": "^5.2.6",
"babel-polyfill": "^6.26.0",
"bootstrap": "^4.1.3",
"connected-react-router": "^6.5.2",
"fixed-data-table-2": "^0.8.26",
"glamor": "^2.20.40",
"history": "^4.9.0",
"html-webpack-plugin": "^3.2.0",
"javascript-excel": "^1.0.3",
"jspdf": "^1.5.3",
"jspdf-react": "^1.0.10",
"lodash": "^4.17.14",
"moment": "^2.24.0",
"prop-types": "^15.7.2",
"qs": "^6.6.0",
"react": "^16.8.2",
"react-bootstrap": "^0.32.4",
"react-compound-slider": "^2.3.0",
"react-csv": "^1.1.1",
"react-data-export": "^0.5.0",
"react-draggable": "^4.0.3",
"react-list-drag-and-drop": "^0.9.1",
"react-markdown": "^4.2.2",
"react-pdf": "^4.1.0",
"react-redux": "^6.0.1",
"react-router-dom": "^5.0.1",
"react-tooltip": "^3.10.0",
"react-virtualized": "^9.21.1",
"redux": "^4.0.1",
"redux-actions": "^2.6.4",
"redux-saga": "^1.1.3",
"reselect": "^4.0.0",
"styled-components": "^4.3.1",
"styled-system": "^4.2.4",
"validate.js": "^0.13.1",
"webpack-merge": "^4.2.2",
"whatwg-fetch": "^3.0.0",
"xlsx": "^0.14.3"
},
"devDependencies": {
"@babel/core": "^7.4.5",
"@babel/plugin-proposal-class-properties": "^7.4.4",
"@babel/plugin-transform-react-jsx-source": "^7.5.0",
"@babel/preset-env": "^7.4.5",
"@babel/preset-react": "^7.0.0",
"@storybook/react": "^4.1.18",
"babel-eslint": "^10.0.2",
"babel-jest": "^24.8.0",
"babel-loader": "^8.0.6",
"babel-plugin-lodash": "^3.3.4",
"babel-plugin-root-import": "^6.2.0",
"babel-plugin-syntax-dynamic-import": "^6.18.0",
"babel-plugin-transform-es2015-modules-commonjs": "^6.26.2",
"babel-plugin-transform-runtime": "^6.23.0",
"clean-webpack-plugin": "^2.0.2",
"copy-webpack-plugin": "^5.0.4",
"css-loader": "^2.1.1",
"deep-freeze": "0.0.1",
"enzyme": "^3.10.0",
"enzyme-adapter-react-16": "^1.14.0",
"eslint": "^5.14.1",
"eslint-loader": "^2.1.2",
"eslint-plugin-react": "^7.13.0",
"faker": "^4.1.0",
"html-loader": "^0.5.5",
"jest": "^24.8.0",
"jest-enzyme": "^7.0.1",
"jest-react-hooks-mock": "^1.1.0",
"node-fetch": "^2.6.0",
"pdf2json": "^1.1.8",
"react-dom": "^16.7.0",
"redux-mock-store": "^1.5.3",
"redux-saga-testing": "^1.0.5",
"sinon": "^7.3.2",
"style-loader": "^0.23.1",
"styled-svg": "^2.4.7",
"stylelint": "^9.10.1",
"stylelint-config-standard": "^18.3.0",
"svg-url-loader": "^3.0.0",
"uglifyjs-webpack-plugin": "^2.1.3",
"webpack": "4.41.2",
"webpack-bundle-analyzer": "^3.3.2",
"webpack-cli": "^3.3.4",
"webpack-dev-server": "^3.7.1"
}
}
webpack / base.config.js
'use strict'
const path = require('path')
const CleanWebpackPlugin = require('clean-webpack-plugin')
const CopyPlugin = require('copy-webpack-plugin')
const BundleAnalyzerPlugin = require('webpack-bundle-analyzer').BundleAnalyzerPlugin
const HtmlWebpackPlugin = require('html-webpack-plugin')
const dirName = __dirname.replace('webpack','');
const util = require('./util');
// cleans 'dist' folder everytime before a new build
const cleanPLugin = env => (new CleanWebpackPlugin({
root: path.join(dirName, util.getRootContext(env) ),
verbose: true,
dry: false
}));
const AnalyzerPlugin = new BundleAnalyzerPlugin(
{
analyzerMode: 'none'
}
);
const copyWebpackPlugin = env => ( new CopyPlugin([ {
from : path.join(dirName, 'src/assets/static'),
to : path.join(dirName, `dist/${util.getRootContext(env)}/assets`)
}, {
from : path.join(dirName, 'src/assets/pages'),
to : path.join(dirName, `dist/${util.getRootContext(env)}`)
}
]));
const HTMLPlugin = new HtmlWebpackPlugin({
template: path.join(dirName, 'src/scripts/index.html'),
chunksSortMode: 'none'
});
module.exports = (env) => {
// BUILDING WEBPACK
const config = {};
config.plugins = [cleanPLugin(env), AnalyzerPlugin, HTMLPlugin, copyWebpackPlugin(env)]
config.entry = ["whatwg-fetch", "babel-polyfill", path.join(dirName, '/src/scripts/index.js')]
config.output = {
path: path.join(dirName, '/dist'),
filename: '[name].build.js',
chunkFilename: '[name].bundle.js',
}
config.module = {
rules: [
{
test: /\.(js|jsx)$/,
exclude: /node_modules/,
loader: 'babel-loader'
},
{
test: /\.(png|jpg|gif|woff|ttf|woff2)$/,
use: [
{
loader: 'file-loader',
options: {}
}
]
},
{
test: /\.svg/,
use: {
loader: 'svg-url-loader',
options: {}
}
},
{
test: /\.(css|less)$/,
use: [ 'style-loader', 'css-loader' ]
}
]
}
config.resolve = {
extensions: [ '.js', '.jsx', '.json', '.css' ],
alias: {
DesignSystem: path.resolve(dirName, 'src/design-system/'),
Icons: path.resolve(dirName, 'src/icons/'),
Scripts: path.resolve(dirName, 'src/scripts/'),
CMS: path.resolve(dirName, 'cms/'),
}
}
config.node = { fs: 'empty' }
return config
}
webpack / prod.config.js
const merge = require('webpack-merge');
const baseConfig = require('./base.config.js');
const UglifyJsPlugin = require('uglifyjs-webpack-plugin');
const path = require('path');
const util = require('./util');
const dirName = __dirname.replace('webpack','');
module.exports = env => (merge(baseConfig(env),
{
optimization: {
splitChunks: {
cacheGroups: {
commons: {
test: /[\\/]node_modules[\\/]/,
name: 'vendor',
chunks: 'initial'
}
}
},
runtimeChunk: {
name: 'manifest'
},
minimizer: [
new UglifyJsPlugin({
sourceMap: true,
uglifyOptions: {
ecma: 8,
mangle: false,
keep_classnames: true,
keep_fnames: true
}
})
]
},
output: {
path: path.join(dirName, `./dist/${util.getRootContext(env)}`),
publicPath: `/${util.getRootContext(env)}/`,
chunkFilename: '[name].[chunkhash].bundle.js',
filename: '[name].[chunkhash].bundle.js'
},
mode: 'production'
}
));
npm run build:prod is the command which runs this build
任何提示或帮助将不胜感激。
谢谢!