Environment Prerequisites
- Webpack version: 5.1.4
- Node.js version: 20.15.1
- Note: Configuration details may vary across different version ranges.
Local Webpack Installation
npm install webpack webpack-cli --save-dev
Default Webpack Behavior
- No explicit configuration required: create a
src/index.jsfile (the default entry point), then runnpx webpackto trigger a build. - Supports both CommonJS and ES Module (ESM) JavaScript modularization stendards.
// src/utils/constants.js
export default "Webpack Core Setup";
// src/index.js
import message from './utils/constants.js';
console.log(message);
To verify, create an index.html file in your project root, link the bundled JS output, and open the HTML in a browser.
Custom Webpack Configuration
- Default config file name:
webpack.config.js - For custom config, use a file like
webpack.custom.config.js
const path = require('path');
module.exports = {
mode: 'production',
performance: {
maxEntrypointSize: 50 * 1024 * 1024, // 50MB limit for entry bundles
maxAssetSize: 30 * 1024 * 1024, // 30MB limit for individual assets
hints: false // Disable size-related warnings/errors
},
entry: {
main: './src/index.js',
secondary: './src/auxiliary.js'
},
output: {
filename: 'bundle/[name].[contenthash:8].js',
path: path.resolve(__dirname, 'build'),
publicPath: '',
clean: true // Automatically clear build directory before new build
}
};
To run with a custom config:
// package.json
"scripts": {
"build": "webpack --config webpack.custom.config.js"
}
Execute via npm run build.
Webpack Dev Server
- Serves files from memory for faster rebuilds
- Installation and usage:
npm install webpack-dev-server --save-dev
// package.json
"scripts": {
"dev": "webpack-dev-server"
}
Run with npm run dev.
Add dev server settings to your config:
module.exports = {
devServer: {
port: 3002,
host: '0.0.0.0',
client: {
progress: true
},
static: './build',
compress: true,
hot: true,
proxy: [{
context: ['/api/v1'],
target: 'http://localhost:8080'
}]
},
devtool: 'source-map'
};
Devtool Recommendations:
- Development:
eval-source-map(fast rebuilds, precise error mapping) - Production:
source-map(separate map file for debugging without exposing source)
html-webpack-plugin
Automatically generates HTML files linked to bundled assets:
npm install html-webpack-plugin --save-dev
Add to config:
const path = require('path');
const HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
plugins: [
new HtmlWebpackPlugin({
template: './src/template.html',
filename: 'main.html',
minify: {
removeAttributeQuotes: true,
collapseWhitespace: true
},
hash: true,
chunks: ['main']
})
]
};
Essential Webpack Loaders
Style Processing
Handle CSS and preprocessor files:
# Core style loaders
npm install css-loader style-loader --save-dev
# Less support
npm install less less-loader --save-dev
# Sass support
npm install sass sass-loader --save-dev
# Stylus support
npm install stylus stylus-loader --save-dev
Inline Style Injecsion:
module.exports = {
module: {
rules: [
{
test: /\.css$/,
use: [
{
loader: 'style-loader',
options: {
insert: 'head',
injectType: 'styleTag'
}
},
'css-loader'
]
}
]
}
};
Extract CSS to Separate Files:
npm install mini-css-extract-plugin --save-dev
const MiniCssExtractPlugin = require('mini-css-extract-plugin');
module.exports = {
plugins: [new MiniCssExtractPlugin({
filename: 'styles/[name].[hash].css'
})],
module: {
rules: [
{
test: /\.less$/,
use: [
MiniCssExtractPlugin.loader,
'css-loader',
'less-loader'
]
}
]
}
};
CSS Compatibility with PostCSS:
npm install postcss postcss-loader postcss-preset-env --save-dev
Create postcss.config.js:
module.exports = {
plugins: [
require('postcss-preset-env')({
browsers: ['> 2%', 'last 5 versions', 'Firefox ESR'],
autoprefixer: { grid: true }
})
]
};
Update loader rules to include postcss-loader after css-loader.
Optimize CSS/JS:
npm install css-minimizer-webpack-plugin terser-webpack-plugin --save-dev
const CssMinimizerPlugin = require('css-minimizer-webpack-plugin');
const TerserJSPlugin = require('terser-webpack-plugin');
module.exports = {
optimization: {
minimizer: [
new CssMinimizerPlugin({ parallel: true }),
new TerserJSPlugin({
parallel: true,
terserOptions: {
compress: {
drop_console: true,
drop_debugger: true
}
}
})
]
}
};
Static Asset Handling
Process images, fonts, and media:
npm install url-loader file-loader --save-dev
Add rules to config:
module.exports = {
module: {
rules: [
{
test: /\.(png|jpe?g|gif|svg)$/i,
type: 'javascript/auto',
use: [
{
loader: 'url-loader',
options: {
limit: 8192,
outputPath: 'assets/images'
}
}
]
},
{
test: /\.(woff2?|eot|ttf|otf)$/i,
type: 'javascript/auto',
use: [
{
loader: 'url-loader',
options: {
limit: 8192,
outputPath: 'assets/fonts'
}
}
]
}
]
}
};
Babel for ES6+ Transpilation
Enable compatibility with older browsers:
npm install babel-loader @babel/core @babel/preset-env --save-dev
npm install @babel/runtime core-js --save
npm install @babel/plugin-transform-runtime --save-dev
Add Babel rule:
module.exports = {
module: {
rules: [
{
test: /\.m?js$/,
include: path.resolve(__dirname, 'src'),
exclude: /node_modules/,
use: {
loader: 'babel-loader',
options: {
presets: [
['@babel/preset-env', {
useBuiltIns: 'usage',
corejs: 3
}]
],
plugins: ['@babel/plugin-transform-runtime']
}
}
}
]
}
};
Additional Plugins & Configuration
copy-webpack-plugin
Copy static files to build directory:
npm install copy-webpack-plugin --save-dev
const CopyWebpackPlugin = require('copy-webpack-plugin');
module.exports = {
plugins: [
new CopyWebpackPlugin({
patterns: [
{ from: 'static', to: './' }
]
})
]
};
Built-in BannerPlugin
Add custom headers to bundled files:
const webpack = require('webpack');
module.exports = {
plugins: [
new webpack.BannerPlugin('Copyright 2024 Frontend Tooling Team')
]
};
Resolve Configuration
Simplify module imports:
module.exports = {
resolve: {
modules: [path.resolve('node_modules')],
extensions: ['.js', '.css', '.json'],
alias: {
'@src': path.resolve(__dirname, 'src'),
'@assets': path.resolve(__dirname, 'src/assets')
}
}
};
Environment Variables
Use cross-env for cross-platform environment setup:
npm install cross-env --save-dev
// package.json
"scripts": {
"dev": "cross-env APP_ENV=development webpack-dev-server",
"build": "cross-env APP_ENV=production webpack"
}
Define runtime variables with DefinePlugin:
const webpack = require('webpack');
const envConfig = require(`./config/${process.env.APP_ENV}.config.js`);
module.exports = {
plugins: [
new webpack.DefinePlugin({
APP_CONFIG: JSON.stringify(envConfig)
})
]
};