After the upgrade from WebPack4 to WebPack5, it runs normally on Google. However, IE11 reported two compatibility problems
Webpack config
Generally, third-party dependencies are supplied to external calls using ES5 syntax, which is why the node_modules folder is often ignored when configuring Babel-Loader. In fact, most dependencies do not need to be translated, except for performance considerations
That is, when Babel is configured correctly, only the business code part of the project is polyfilled, and the syntax Babel does not apply to third-party dependencies (if you include exclude: /node_modules/).
For example, babel-loader’s 🌰:
// webpack.config.js
{
/ /...
module: {
rules: [{// The dependencies of node_modules are generally compiled and do not need to be compiled again
exclude: /node_modules/
test: /\.(js|jsx)$/,
loader: 'babel-loader'.options: {
presets: [['@babel/preset-env', {targets: 'ie 11'}]],}}]}}Copy the code
Even with this configuration, you’ll find a lot of ES6 syntax in the packaged JS files, such as the arrow function, which will simply fail when run in IE11
By default, Webpack5 does not support IE because its default runtime code uses ES6 syntax. An error will be reported when running in IE
Read the document carefully. Webpack5 configuration item Outpt. environment provides a series of configuration items about the final running environment of the code. The default configuration items do not support IE and must be specified manually
// Document configuration description
module.exports = {
output: {
environment: {
// The environment supports arrow functions ('() => { ... } ').
arrowFunction: true.// The environment supports BigInt as literal (123n).
bigIntLiteral: false.// The environment supports const and let for variable declarations.
const: true.// The environment supports destructuring ('{ a, b } = obj').
destructuring: true.// The environment supports an async import() function to import EcmaScript modules.
dynamicImport: false.// The environment supports 'for of' iteration ('for (const x of array) { ... } ').
forOf: true.// The environment supports ECMAScript Module syntax to import ECMAScript modules (import ... from '... ').
module: false,}}};Copy the code
Add a configuration to output.environment: this configuration indicates whether the environment in which our packaged code is running supports these syntax. Obviously, IE does not support some syntax, so change it to false
module.exports = {
/ /... Other attributes
output: {
environment: {
arrowFunction: false.// The environment does not support arrow functions
bigIntLiteral: false.// BigInt is not supported
const: true.destructuring: false.// Deconstruction is not supported
dynamicImport: false.// Asynchronous import is not supported
forOf: false.// Do not support for... of
module: false.// Module is not supported,}}};Copy the code
Another solution
Thanks to @Yukinotech for pointing out that WebPack provides another configuration that solves compatibility issues with runtime code compilation, specifying the runtime environment for WebPack so that you don’t need to change the enviroment properties one by one
// webpack.conf.js
module.export = {
// ...
target: ["web"."es5"]}Copy the code
Second pit: JS compression plugin -TerserWebpackPlugin
The JS compression plugin uglifyjs-webpack-plugin has been replaced by terser-webpack-plugin, and WebPack5 has built-in dependencies. The catch is that the Terser-Webpack-plugin does not use ES5 syntax by default, for example
let a = 1;
let b = {a: a}
Copy the code
This code will be compressed into:
let a=1;let b={a}
Copy the code
The ES6 syntax sugar is used in IE. This needs to be explicitly specified in the TerserWebpackPlugin
const TerserPlugin = require("terser-webpack-plugin");
module.exports = {
optimization: {
minimize: true.minimizer: [
new TerserPlugin({
ecma: 5})],}};Copy the code
The complete related configuration code is as follows:
module.exports = {
output: {
entry: 'main.js'.output: {
publicPath: ' '.path: 'dist'.target: ["web"."es5"].// It can also be specified manually
//environment: {
// arrowFunction: false, // The environment does not support arrow functions
// BigInt: false; // BigInt is not supported
// Ie 10 does not support const
// destructuring: false, // Destructuring is not supported
DynamicImport: false, asynchronous import is not supported
// forOf: false, // for... of
// Module: false, // Module is not supported
/ /},
filename: () = > (isDev ? '[name].js' : '[name].[contenthash:8].js'),
chunkFilename: () = > (isDev ? 'assets/[name].js' : 'assets/[name].[contenthash:8].js')},target: 'web'.resolve: {
extensions: ['ts'.'tsx'.'js'.'jsx'].alias: {
The '@': 'src'.vue$: 'vue/dist/vue.runtime.esm.js'}},module: {
rules: [
// Other loaders
{
test: /\.(js|jsx)$/.// The dependencies of node_modules are generally compiled and do not need to be compiled again
exclude: /node_modules/
use: {
loader: 'babel-loader'.// Options can be extracted to babel.config.js, targets can be configured using. Browserslistrc
options: {
presets: [['@babel/preset-env', {targets: 'ie 11'}]],}}}],// This is normally only enabled in the Production environment
optimization: {
minimize: true.minimizer: [
new TerserPlugin({
ecma: 5})],},}}Copy the code