Common Webpack Optimization Techniques for Reducing Build Time and Bundle Size
This article outlines practical webpack optimization methods—including bundle analysis, build‑time measurement, on‑demand loading, loader configuration, path resolution, source‑map handling, code compression, extracting common modules, CDN usage, and multi‑process builds—to improve page load speed, reduce bundle size, and enhance overall frontend performance.
As projects grow, the number of third‑party libraries and the size of the bundled output increase, leading to longer build times and larger files, which cause long white‑screen times for single‑page applications and a poor user experience.
The goal of optimization is to improve page load speed and user experience by reducing the final bundle size, loading only necessary files on the homepage, and shortening webpack build time.
1. Analyze Bundle Size with webpack-bundle-analyzer
Install the plugin and add it to the webpack configuration to visualize module sizes and dependencies.
npm install webpack-bundle-analyzer -D
const { BundleAnalyzerPlugin } = require('webpack-bundle-analyzer');
plugins: [new BundleAnalyzerPlugin()]For Vue CLI 2 you can run npm run build --report to open the report on port 8888.
2. Measure Build Time with speed-measure-webpack-plugin
Install the plugin and wrap the existing configuration to see the time spent on each stage.
npm install speed-measure-webpack-plugin --save-dev // vue.config.js
const SpeedMeasurePlugin = require('speed-measure-webpack-plugin');
const smp = new SpeedMeasurePlugin();
module.exports = { configureWebpack: smp.wrap({ plugins: [new BundleAnalyzerPlugin()] }) };3. On‑Demand Loading
Split route components and third‑party libraries so that only the code needed for the initial page is loaded.
const router = [
{ path: '/index', component: resolve => require.ensure([], () => resolve(require('@/components/index')) ) },
{ path: '/about', component: resolve => require.ensure([], () => resolve(require('@/components/about')) ) }
];Import Element UI components on demand:
import { Button } from 'element-ui';
Vue.component(Button.name, Button);4. Optimize Loader Configuration
Use cache, include/exclude, and limit regex matching to speed up loader processing.
module: {
rules: [{
test: /\.js$/,
loader: 'babel-loader?cacheDirectory',
include: [resolve('src')]
}]
}Configure resolve.extensions and resolve.alias to speed up module resolution, and use module.noParse for large non‑module libraries like jQuery.
resolve: {
extensions: ['.js', '.vue', '.json'],
alias: { 'vue$': 'vue/dist/vue.esm.js', '@': resolve('src') }
},
module: { noParse: /jquery/ }5. Disable SourceMap in Production
Turn off source maps for production builds to reduce bundle size and build time.
6. Code Compression
Use uglifyjs-webpack-plugin or parallel-uglify-plugin to compress JavaScript; the parallel version runs in multiple processes for faster compression.
plugins: [
new UglifyJsPlugin({
uglifyOptions: { compress: { warnings: false } },
sourceMap: true,
parallel: true
})
]7. Extract Common Code
For webpack 3 use CommonsChunkPlugin ; for webpack 4 use the built‑in splitChunks configuration to separate vendor and common modules.
// webpack 3
plugins: [
new webpack.optimize.CommonsChunkPlugin({ name: 'vendor', minChunks: function(module){ return module.resource && /\.js$/.test(module.resource) && module.resource.indexOf(path.join(__dirname, './node_modules')) === 0; } }),
new webpack.optimize.CommonsChunkPlugin({ name: 'common', chunks: 'initial', minChunks: 2 })
] // webpack 4
module.exports = {
optimization: {
splitChunks: {
cacheGroups: {
vendor: { priority: 1, test: /node_modules/, chunks: 'initial', minChunks: 2 },
common: { chunks: 'initial', minChunks: 2 }
}
}
}
}8. DLLPlugin
Create a separate DLL bundle for stable third‑party libraries and reference it in the main build.
// webpack.dll.config.js
const path = require('path');
const webpack = require('webpack');
module.exports = {
entry: { vendor: ['vue-router','vuex','vue','axios','echarts'] },
output: { path: path.resolve('./dist'), filename: '[name].dll.js', library: '[name]_library' },
plugins: [
new webpack.DllPlugin({ path: path.resolve('./dist', '[name]-manifest.json'), name: '[name]_library' }),
new webpack.optimize.UglifyJsPlugin({ compress: { warnings: false } })
]
};Reference the DLL in webpack.prod.conf.js with DllReferencePlugin and add the generated script tag to index.html .
9. CDN Optimization
Load Vue, Vue‑Router, Vuex, Element UI, and Axios from a CDN and mark them as externals in webpack to avoid bundling them.
externals: { vue: 'Vue', vuex: 'Vuex', 'vue-router': 'VueRouter', 'element-ui': 'ELEMENT', axios: 'axios' }10. Multi‑Process Build
Use thread-loader before other loaders or HappyPack to parallelize expensive loader work.
// thread-loader example
module.exports = { module: { rules: [{ test: /\.js$/, include: path.resolve('src'), use: ['thread-loader', 'expensive-loader'] }] } }; // HappyPack example
const HappyPack = require('happypack');
const HappyPackThreadPool = HappyPack.ThreadPool({ size: 5 });
plugins: [
new HappyPack({ id: 'babel', loaders: ['babel-loader?cacheDirectory'], threadPool: HappyPackThreadPool }),
new HappyPack({ id: 'vue', loaders: [{ loader: 'vue-loader', options: vueLoaderConfig }], threadPool: HappyPackThreadPool })
]Summary : The most practical optimizations are on‑demand loading, loader tuning, disabling source maps in production, and CDN usage. Vue‑CLI already provides code compression and common‑module extraction, which can be further customized as needed, always ensuring that optimizations do not affect business logic.
Sohu Tech Products
A knowledge-sharing platform for Sohu's technology products. As a leading Chinese internet brand with media, video, search, and gaming services and over 700 million users, Sohu continuously drives tech innovation and practice. We’ll share practical insights and tech news here.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.