Preface:

This article will introduce how to configure the development version of Webpack4 from the beginning, compile, package and merge CSS and JS to generate MD5, image processing in CSS, JS automatic injection into HTML pages, delete specified files. Extract public files, hot updates, etc.

Configuration information and detailed notes for webPack packaging optimization are attached

Updated a front-end architecture node JWT certification, welcome to take a look!!

Update a small node server architecture, welcome to take a look!!

The installation

NPM install -g webpack webpack-cliCopy the code

Create folder initialization

// Create folder mkdir webpack4demo // entercdWebpack4demo // Initializes NPM init-yCopy the code

Create folder scripts create index.js file

index.js

const s=()=>{ 
console.log('s init')
}
s()Copy the code

Create the webpack.config.js file

webpack.config.js

const path = require("path");
module.exports = {
    entry: {
        index: "./scripts/index.js"}, output: {filename:"[name].bundle.js"Path: path.join(__dirname,"dist"// Output file path}}Copy the code

Executing webpack — Mode development will generate dist/index.bundle.js



Create index.html and import JS

<! DOCTYPE html> <html lang="en">
<head>
    <meta charset="UTF-8">
    <title>$Title$</title>
</head>
<body>
$END$
</body>
<script src="./dist/index.bundle.js"></script>
</html>Copy the code

Open the browser and you will see that the js file set previously takes effect

Compile and merge CSS and JS to generate MD5

Create a.js, c.js, a.cs and change index.js

a.js

import acss from './a.css'
import c from './c.js'
const a={
    init(){
        console.log("a init bbbaaa")},cinit(){
       c.init()
    }
}
export default a;Copy the code

c.js

const c={
    init(){
        console.log("ccccc")}}export default c;Copy the code

a.css

body{ 
    background-color: #6b0392;
}Copy the code

index.js

import a from './a.js'
import c from './c.js'
const s=()=>{
    a.init()
    a.cinit()
    c.init()
    console.log('s init')
}
s()Copy the code

Configure the webpack.config.js file

const path = require("path");
module.exports = {
    entry: {
        index: "./scripts/index.js"
    },
    output: {
        filename: "[name].bundle.[hash].js", / / /hash] will generate randomness laterhashValue path: the path. The join (__dirname,"dist"}, module: {test: /\.css$/,
                use: [ 'style-loader'.'css-loader']// Handle CSS}]},}Copy the code

Install style-loader and CSS-loader

npm install style-loader css-loader --save-dev
Copy the code

Execute Webpack — Mode Development and you will see an MD5-worthy JS file that will import it into HTML

Image manipulation in CSS

Install the url – loader, file – loader

npm install url-loader file-loader --save-dev
Copy the code

Modify a. CSS to place an image in the scripts directory

body{
    background-image: url("./timg.jpg");
    background-color: #a748ca;
}Copy the code

Configure the webpack.config.js file

module: {
    rules: [
        {
            test: /\.css$/,
            use: [ 'style-loader'.'css-loader'] {},test:/\.(png|jpg|gif)$/,
            use:[{
                loader:'url-loader',
                options:{
                    outputPath:'images/'// Output to the images folderlimit:500 // Is a Base64 file, write JS}}]}]},Copy the code

Execute Webpack — Mode Development and you’ll see that there is an image in the Images folder in Dist. Open index.html



Js automatically injects HTML files

With the htML-webpack-plugin, generated JS can be automatically imported into HTML pages without manual addition

// install html-webpack-plugin NPM install html-webpack-plugin --save-dev // Install webpack webpack-cli NPM install webpack webpack-cli --save-devCopy the code

Configure the webpack.config.js file

const path = require("path");
const HtmlWebpackPlugin = require('html-webpack-plugin'); HTML -webpack-plugin module. Exports = {entry: {index:"./scripts/index.js"
    },
    output: {
        filename: "[name].bundle.[hash].js",
        path: path.join(__dirname, "dist")
    },
    module: {
        rules: [
            {
                test: /\.css$/,
                use: [ 'style-loader'.'css-loader'[// new HtmlWebpackPlugin({// configure filename:'index.html'// Output file name template:'./index.html'Dist /index.html}),]}Copy the code

Execute WebPack — Mode Development to remove the script that you manually introduced earlier, and you’ll see that an index.html is automatically generated in Dist. Open it up and you’ll see it.

Delete a specified file

Use the clean-webpack-plugin to remove the specified files. For more configuration, see the clean-webpack-plugin

npm install clean-webpack-plugin --save-devCopy the code

Configure the webpack.config.js file

const CleanWebpackPlugin = require('clean-webpack-plugin'); New HtmlWebpackPlugin({// configure filename:'index.html'// Output file name template:'./index.html'Dist /index.html}), new CleanWebpackPlugin(['dist'], // Pass an array to specify the directory to delete.Copy the code

Execute webpack — Mode Development and you can see that the dist directory has been deleted and a new DIST has been generated with the previous JS files removed.

Extract public files

We can see that both A.js and index.js have introduced c.js files. Why should we extract common code? In short, it is to reduce code redundancy and improve loading speed. Different from the previous WebPack configuration:

Configuration before / / / / new webpack. Optimize the SplitChunksPlugin ({/ / name:'common'// chunks: [// chunks: [// chunks: [// chunks: [// chunks: [// chunks: ['index'.'a'}), // Now configure optimization: {splitChunks: {cacheGroups: {Commons: {//"initial",
                name: "common"// Name minChunks: 2, reference minSize: 0 at least twice // Generate a new package as long as it exceeds 0 bytes}, vendor: {// remove the third-party plug-intest: /node_modules/, // specifies third-party package chunks under node_modules:'initial',
                name: 'vendor'Priority: 10},}}}, priority: 10},Copy the code

Jq NPM install jquery –save in a.js, index.js with import $from ‘jquery’ output $

Generate 3 JS files and execute Webpack — Mode Development



Hot update, automatic refresh

We’ll use webpack-dev-server, which is a small server based on Node.js and WebPack with powerful auto-refresh and hot replace features.

Webpack – dev – server installation

npm install webpack-dev-server --save-devCopy the code

Configure the webpack.config.js file

const webpack = require("webpack");
plugins: [
    new HtmlWebpackPlugin({
        filename: 'index.html',
        template: './index.html',
    }),
    new CleanWebpackPlugin(['dist']), / / incoming array, want to delete the directory / / hot update, hot update is not refresh new webpack. HotModuleReplacementPlugin ()], devServer: {// Configure this static file server, which can be used to preview a packaged project inline:true// Add a websocket client hot:true// contentBase: path.resolve(__dirname,'dist'),// develop service runtime file root directory host:'localhost',// host address port: 9090,// port number compress:true// Whether the development server starts gzip isocompression},Copy the code

Configuration package. Json

"scripts": {
  "dev": "webpack-dev-server --mode development"
},Copy the code

Run NPM run dev to access http://localhost:9090/

Any modification of any file will automatically refresh the site to show the modification of the corresponding content.

Conclusion:

Webpack4 also has a lot of a lot of configuration, such as CSS split ah, less Sass configuration ah, JS compilation ES6 ah, multi-entry configuration ah, production environment configuration, JS did not use the module automatically detect the separation and so on, can only wait for the next time free in the summary, thank you for watching, the new user into the pit, welcome to point out the error.

Webpack packaging optimizes configuration

Attached are 3 files, webpack.base.conf.js(base configuration file), webpack.dev.conf.js(development environment configuration file), and webpack.prod.conf.js(production environment configuration file) with detailed comments

webpack.base.conf.js

const path = require("path")
const chalk = require('chalk');

const ProgressBarPlugin = require('progress-bar-webpack-plugin'// progress bar const MiniCssExtractPlugin = require('mini-css-extract-plugin'Const VueLoaderPlugin = require(const VueLoaderPlugin = require('vue-loader/lib/plugin');
const HappyPack = require('happypack'// multithread compression const OS = require('os'Const happyThreadPool = happypack.threadpool ({size: 1)// Node provides system operation module // Specifies the number of thread pools according to the number of system cores const happyThreadPool = happypack.threadpool ({size: 1) os.cpus().length }) const ExtractTextPlugin = require('extract-text-webpack-plugin') // Convert to absolute pathfunction resolve(dir) { 
return path.join(__dirname,'.. ', dir);
}
function assetsPath(_path_) {
let assetsSubDirectory = 'static';
return path.posix.join(assetsSubDirectory, _path_)
}
module.exports = {
entry: {
app: './src/main.js'}, output: {path: resolve("dist"),// Output file path filename:'[name].js'Resolve: {// Resolve: [path.resolve()'src'),
path.resolve('node_modules') // specify the node_modules location to search for when you import third-party modules], // enable autocomplete, specify the extensions to search for: ['.js'.'.vue'.'.json'], // Configure aliases to speed up WebPack's module lookupalias: {
'vue$': 'vue/dist/vue.esm.js'// Add $at the end to indicate an exact matchThe '@': resolve('src'}}, // module module: {// Multiple loaders are written from right to left, because the conversion is from right to left.test: /\.vue$/,
loader: 'vue-loader',
include: resolve('src'// exclude: /node_modules/ / exclude}, {test: /\.js|jsx$/,
exclude: /node_modules/,
loader: 'happypack/loader? id=happys',// cacheDirectory Cache loader execution result include: resolve('src'),
exclude: /node_modules/ 
},
{
test: /\.css$/,
loader: ExtractTextPlugin.extract({
fallback: 'style-loader',
use: ['css-loader'.'postcss-loader'.'less-loader']
}),
include: [resolve('src'Exclude: /node_modules/}, {exclude: /node_modules/test: /\.less$/,
loader: ExtractTextPlugin.extract({
fallback: 'style-loader',
use:['css-loader'.'postcss-loader'.'less-loader']}),
include: resolve('src'),
exclude: /node_modules/ 
},
{
test: /\.(png|jpe? g|gif|svg)(\? . *)? $/, loader:'url-loader',
options: {
limitBase64 name: assetsPath('img/[name].[hash:7].[ext]')}Copy the code

webpack.dev.conf.js

const webpack = require('webpack')
const path = require('path')
const baseWebpackConfig = require('./webpack.base.conf')
const merge = require('webpack-merge')
const HtmlWebpackPlugin = require('html-webpack-plugin'Const devWebpackConfig = merge(baseWebpackConfig, {devtool:'eval-source-map'// specify addsource-map the way // configure this static file server, which can be used to preview the packaged project devServer: {inline:true// Add a websocket client hot:true,// contentBase: path.join(__dirname,".."."dist"Port: 3824, // host:'localhost',
overlay: true,
compress: falseWatchOptions: {ignored: /node_modules/, // Ignore the aggregateTimeout directory that does not need to listen for changes: Plugins: [new HtmlWebpackPlugin({template: path.resolve(__dirname,'.. '.'src'.'index.html'),
filename: 'index.html',
// vendor: './vendor.dll.js', // align with output.filename in the DLL configuration filehash:true,// prevent caching // minify:{// removeAttributeQuotes:true/ / compression remove quotes / /}}), new webpack. HotModuleReplacementPlugin (), //HMR new webpack.NamedModulesPlugin() // HMR ] }) module.exports = devWebpackConfigCopy the code

webpack.prod.conf.js

const path = require('path');
const glob = require('glob');
const webpack = require('webpack')
const CopyWebpackPlugin = require('copy-webpack-plugin'Const CleanWebpackPlugin = require('clean-webpack-plugin'Const HtmlWebpackPlugin = require() const HtmlWebpackPlugin = require('html-webpack-plugin'Const baseWebpackConfig = require(const baseWebpackConfig = require('./webpack.base.conf')
const merge = require('webpack-merge')
const WebpackParallelUglifyPlugin = require('webpack-parallel-uglify-plugin')
const OptimizeCSSPlugin = require('optimize-css-assets-webpack-plugin')
const PurifyCSSPlugin = require("purifycss-webpack");
const ExtractTextPlugin = require('extract-text-webpack-plugin')

function assetsPath(_path_) {
    let assetsSubDirectory = 'static';
    return path.posix.join(assetsSubDirectory, _path_)
  }
const prodWebpackConfig = merge(baseWebpackConfig, {
    output:{
        path: path.resolve(__dirname, '.. /dist'),
        filename: assetsPath('js/[name].js'),
        publicPath: '/'Plugins: [new HtmlWebpackPlugin({template: path.resolve(__dirname,})}'.. /src'.'index.html'),
            filename:'index.html',
            // chunks:['index'.'common'],
            // vendor: './vendor.dll.js'.hash:true// Prevent caching minify:{removeAttributeQuotes:true// collapseWhitespace:true}}), new CopyWebpackPlugin([{from: path.join(__dirname,'.. /src'.'assets'),
                to: path.join(__dirname,  '.. '.'dist'.'assets'),
                ignore: ['*']
            }
        ]),
        new CleanWebpackPlugin(['dist'], {
            root: path.join(__dirname, '.. '),
            exclude: ['manifest.json'.'vendor.dll.js'],
            verbose: true,
            dry:  false}), new WebpackParallelUglifyPlugin ({workerCount: 4, / / open a few child processes to the execution of concurrent compression, the default is the current computer CPU number minus 1 uglifyJS: {output: {beautify:false// No need to format comments:false// Keep comments}, compress: {warnings:false// Uglifyjs delete no code when no warning drop_console is output:trueCollapse_vars: // Delete all console statements collapse_vars:true,
                    reduce_vars: trueNew OptimizeCSSPlugin({cssProcessorOptions: {safe:}), // Compress the extracted CSS and solve the ExtractTextPlugin's js problem.true}}), // Eliminate unused CSS new PurifyCSSPlugin({paths: glob.sync(path.join(__dirname,'.. /src/*.html'),}), // Package CSS to generate another folder new ExtractTextPlugin({filename:'static/css/[name].css'.disable: false,
            allChunks: false
          })
    ]
})
module.exports = prodWebpackConfigCopy the code