webpack

一、全局安装nodejs

 

安装后检验:cmd中:node -v,出现版本号即安装成功。

 

二、安装webpack

1.新建项目文件夹item,cmd中进入项目:cd item

2.初始化:cmd中:npm init -y,生成package.json文件

3.安装webpack和webpack-cli:cmd中:npm install --save-dev webpack webpack-cli

4.项目文件夹中添加src文件夹,src 文件夹中添加 index.js: document.write(111);(默认入口文件文件src/index.js)

5.项目文件夹中添加dist文件夹,dist文件夹中添加index.html: <script src="main.js"></script>(默认输出文件文件dist/main.js)

6.编译:cmd中:npx webpack ,自动生成main.js

 

三、使用配置文件

1.项目文件夹中创建webpack.config.js:(默认配置文件webpack.config.js)

作用:更改输入输出文件等 

const path = require('path');

module.exports = {
  mode: 'development', //模式:production(默认) 、development
  entry: './src/index.js',
  output: {
    filename: 'bundle.js',
    path: path.resolve(__dirname, 'dist')
  }
};

.编译:cmd中: npx webpack, 自动生成dist/bundle.js

2.若想修改webpack.config.js文件名,则在cmd中: npx webpack --config 新的文件名

3.若新文件名太长,则在package.json中做配置:

"scripts": {
    "build": "webpack --config 新文件名"
},

  编译:cmd中: npm run build, 自动生成dist/bundle.js

 

四、挂载到本地服务器

1.安装webpack-dev-server:

npm i webpack-dev-server --save-dev

2.package.json中:

"scripts": {
    "dev": "webpack-dev-server"
},

3.webpack/config.js中设置devServer配置服务器:

const path = require('path');
module.exports = {
  mode: 'development',
  entry: './src/index.js',
  output: {
    filename: 'bundle.js',
    path: path.resolve(__dirname, 'dist')
  },
  devServer: { // 开发服务器的配置
    host: 'localhost',
    port: 3000, // 端口
    progress: true, // 打包时进度条
    contentBase: './dist', // 浏览器打开时默认路径
    compress: true //启用gzip压缩
  }
}

4.生成:

npm run dev

浏览器打开localhost:3000

 

五、自动生成html,并载入打包好的文件

1、安装html-webpack-plugin:

npm i --save-dev html-webpack-plugin

 2.在webpack.config.js中配置:

const path = require('path');
const HtmlWebpackPlugin = require('html-webpack-plugin');
module.exports = {
  .........
  plugins: [
    new HtmlWebpackPlugin({
      template: './src/index.html', //模板文件
      filename: 'index.html', //生成的文件名
      minify: { //压缩输出,mode为production时为true ,否则为false
        removeAttributeQuotes: true, // 删除双引号
        collapseWhitespace: true // 变为一行
      },
      hash: true, // 打包时的js文件在引用时带上?hash,如src=bundle.js?8ae46c61ad7a73e29468
    })
  ]
}

3.npm run  build,自动生成dist/index.html 

 

六、生成内联样式

1.css-loader:解析@import语法。

style-loader: 把css插入head标签中。

loader特点:功能单一;一个loader用字符串,多个loader 用数组;执行顺序为从右到左。

2.安装: npm i --save-dev css-loader style-loader

3.webpack.config.js中配置:

module.exports = {
  。。。。。。

  module: {
    rules:[
      //loader执行顺序为从右到左,先解析css再插入head标签中,所以style-loader需放在css-loader左边
      { test: /\.css$/,use:[
        {
          loader: 'style-loader'
        }, 
        'css-loader'
      ]},
      {
        test: /\.scss$/,
        use: [
          {
            loader: 'style-loader'
          },
          'css-loader',
          'sass-loader' //解析scss需安装node-sass,但不需要写入
        ]
      }
    ]
  }
}

4.生成:npm run dev ,生成内联样式<style>....</style>

 

七、生成外联样式

1.安装:npm i mini-css-extract-plugin --save-dev

2.webpack.config.js中配置:

。。。。
const MiniCssExtractPlugin = require('mini-css-extract-plugin');

module.exports = {
  。。。。
  plugins: [
    。。。。
    new MiniCssExtractPlugin({
      filename: 'main.css'
    })
  ],
  module: {
    rules:[
      { test: /\.css$/,use:[
        // {
        //   loader: 'style-loader'
        // }, 
        // 将style-loader替换成MiniCssExtractPlugin(css插入head标签替换成外联的css)
        MiniCssExtractPlugin.loader,
        'css-loader'
      ]},
      {
        test: /\.scss$/,
        use: [
          // 'style-loader',
          MiniCssExtractPlugin.loader,
          'css-loader',
          'sass-loader'
        ]
      }
    ]
  }
}

3.生成: npm run build ,生成

 

八、压缩css、js

1.安装插件: 

cnpm i --save-dev optimize-css-assets-webpack-plugin //压缩css
cnpm i --save-dev uglifyjs-webpack-plugin //压缩js

2.webpack.config.js中配置:

。。。。
const OptimizeCss= require('optimize-css-assets-webpack-plugin'); //压缩css
const UglifyJsPlugin = require('uglifyjs-webpack-plugin');
module.exports = {
    。。。。
    plugins: [
        。。。。
        new UglifyJsPlugin({ //压缩js
            cache: true, //使用缓存
            parallel: true, // 并行打包
            sourceMap: true 
        }),
        new OptimizeCss() //压缩css
        
    ],
    。。。。
} 

3.打包: npm run build 生成压缩好的文件

 

九、将ES6转化为ES5

1.安装: babel-loader,@babel/core, @babel/preset-env,  @babel/plugin-proposal-class-properties

cnpm i babel-loader @babel/core @babel/preset-env --save-dev
cnpm i @babel/plugin-proposal-class-properties  --save-dev // 解析class
cnpm i @babel/plugin-proposal-decorators  --save-dev //解析装饰器

2.webpack.config.js中配置:

。。。。。
module.exports = {
    。。。。
    module: {
        rules: [
            。。。。。
            {
                test: /\.js$/,
                use: {
                    loader: 'babel-loader', // 将RS6转为ES5
                    options: {
                        presets: ['@babel/preset-env'],
                        plugins:[
                            // '@babel/plugin-proposal-class-properties', // 解析class
                            
                            ['@babel/plugin-proposal-decorators', { //解析装饰器
                                'legacy': true
                            }],
                            ['@babel/plugin-proposal-class-properties', { "loose" : true}] // 解析class
                            
                        ]
                    }
                }
            }
        ]
    }
} 

 

十、优化

1.安装:

cnpm i --save @babel/plugin-transform-runtime //解析高级语法(generator、promise)并优化
cnpm i --save @babel-runtime 
cnpm i --save @babel-polyfill //解析更高级语法(includes())

2.在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。。。。
    module: {
        rules: [
            。。。。。
            {
                。。。。
                use: {
                    。。。。。。
                    options: {
                        。。。。。。
                        plugins:[
                            。。。。
                            "@babel/plugin-transform-runtime"  //解析高级语法(generator、promise)并优化
                        ]
                    }
                }
            }
        ]
    },
} 

3.在src/index.js中

require('@babel/polyfill');

十一、校验

1.安装:

cnpm i --save-dev eslint eslint-loader

2.webpack.congfig.js中配置:

。。。。
module.exports = {
    。。。。
    module: {
        rules: [
            。。。。。
            {
                test: /\.js$/,
                use: {
                    loader: 'eslint-loader',
                    options: {
                        enforce: 'pre' //强制在其他loader之前执行
                    }
                },

            }
        ]
    },
} 

3.在eslint官网勾选并下载规则包.eslintrc.json

十二、设置全局变量

1.以jquery为例,安装jquery

2.设置为全局变量:

方法一:

在src/index.js中使用expose-loader:z window上挂载$

// import $ from 'jquery';
require('expose-loader?$!jquery')
console.log($);
console.log(window.$);

方法二:

webpack.congfig.js中使用expose-loader:

。。。。。
module.exports = {
    。。。。。。。
    module: {
        rules: [
            。。。。
            {
                test: require.resolve('jquery'), //请求jquery时
                use: 'expose-loader?$!jquery'
            }
        ]
    },
} 

方法三:

webpack.congfig.js中使用webpack.ProvidePlugin:在每个模块中挂载$

。。。。。
const webpack = require('webpack');
module.exports = {
    。。。。。
    plugins: [
        。。。。。。
        new webpack.ProvidePlugin({
            $: 'jquery'
        })
    ]
} 

方法四:直接用script标签引入cdn,但为了避免文件中引入的jq重复打包,在webpack.congfig.js中使用externals:

。。。。
module.exports = {
    。。。。
    externals: { //不打包
       jquery: 'jQuery' 
    },
    。。。。
} 

 

十三、图片处理

1. 通过js和css载入的图片用file-loader,安装file-loader

webpack.config.js中配置file-loader:

。。。。
module.exports = {
   。。。。。
    module: {
        rules: [
            {
                test: /\.(jpg|png|gif)$/,
                use: 'file-loader'
            },
            。。。。。。
        ]
    }
} 

通过js载入的在src/index.js中:

import logo from './index.png'
let img = new Image();
img.src = logo; // 不能直接写字符串,解析不了
console.log(img.src);
document.body.appendChild(img);

2.通过html载入的图片用html-withimg-loader

安装html-withimg-loader

webpack.config.js中配置file-loader:

。。。。
module.exports = {
   。。。。。
    module: {
        rules: [
            {
                test: /\.html$/,
                use: 'html-withimg-loader'
            },
            。。。。。。
        ]
    }
} 

在index.html中引入图片:

<img src="index.png">

3.小图片转为base64:

安装url-loader

webpack.config.js中配置url-loader:

。。。。
module.exports = {
   。。。。。
    module: {
        rules: [
            {
                test: /\.(jpg|png|gif)$/,
                // 当图片小于多少K时,用url-loader转化成base64
                // 否则用file-loader产生真实图片
                // use: ['file-loader']
                use:{
                    loader: 'url-loader',
                    options:{
                        limit: 5 * 1024, //小于5k的图片转化为base64
                        outputPath:'img/' //大于5k的图片生成在img目录下
                    }
                }
            },
            。。。。。。
        ]
    }
} 

 

十四、报错定位

1.安装source-map:

npm i --save-dev source-map

 2.在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。
    devtool: 'source-map', // 定位到源码位置,并生成源码独立文件
    // devtool: 'eval-source-map',  //安装时404
    // devtool: 'cheap-module-source-map', //安装时404
    // devtool: 'cheap-module-eval-source-map', //安装时404
}

3.npm run dev ,生成源码独立文件,报错时定位到源码列

 

十五、实时打包

在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。
    watch: true,
    watchOptions: {
        poll: 1000, //1秒检测1000次
        aggregateTimeout: 500, //防抖:输入500毫秒后再执行
        ignored: /node_modules/ //不需要监控的文件
    },
}

 

十六、清除文件夹

1.安装 clean-webpack-plugin

2.在webpack.config.js中配置:

。。。。
const {CleanWebpackPlugin} = require('clean-webpack-plugin');
module.exports = {
    。。。。
    plugin: [
        new CleanWebpackPlugin() //默认删除output.path
    ]
}

 

十七、拷贝文件

1.安装copy-webpack-plugin

2.在webpack.config.js中配置:

。。。。
const CopyWebpackPlugin = require('copy-webpack-plugin');
module.exports = {
    。。。。
    plugin: [
        new CopyWebpackPlugin([
            {from: 'doc', to:'./'} //doc目录下的文件拷贝到当前目录下(dist)
        ])
    ]
}

十八、添加版权标识 

在webpack.config.js中配置:

。。。。
const webpack = require('webpack');
module.exports = {
    。。。。
    plugin: [
        new webpack.BannerPlugin('make 2019 by jwy') //版权标识会被注释到打包文件最前
    ]
}

 十九、处理跨域

1.代理:

在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。
    devServer: {
        proxy:{ //跨域代理
            '/api': { //所有接口共有
                target: 'http://localhost:3000', //指向域名
                pathRewrite:{'^/api': ''} // 将/api改为空字符串
            }
        }
        
    }
}

在src/index.js中发起请求:

var xhr = new XMLHttpRequest();
xhr.open('GET','/api/user', true);
xhr.onload = function() {
    console.log(xhr.response);
}
xhr.send();

创建服务器server.js:

let express = require('express');
let app = express();
app.get('/api/user', (req, res)=> {
    res.json({name:'jwy'})
})
console.log(122);
app.listen(3000)

 

2.webpack中模拟接口,不用服务器

在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。
    devServer: {
        before(app) {
            app.get('/api/user', (req, res) => { //模拟接口
                res.json({name: 'jqwy'})
            })
        }
    }
}

 

3.在服务端中启用webpack,端口使用服务端端口:

在服务器server.js中配置处理webpack和中间件webpack-dev-middleware:

let express = require('express');
let app = express();

let webpack = require('webpack');
let middle = require('webpack-dev-middleware'); //中间件
let config = require('./webpack.config.js'); //引入webpack配置文件
let compiler = webpack(config); //用webpack处理config文件,并返回编译后结果

app.use(middle(compiler)); //app中使用中间件

app.get('/api/user', (req, res)=> {
    res.json({name:'j222wy'})
})
console.log(122);
app.listen(3000)

在localhost:3000/api/user 中可以访问到/api/user接口

在localhost:3000/index.html 中可以访问到src/index.html

 

二十、解析第三方包

1. 在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。
    resolve: { //解析第三方包
        modules: [path.resolve('node_module')], // 只在node_module文件夹中找包
        extensions: ['.js', '.css', '.json', '.vue'], //解析引入的没有后缀名的文件
        mainFields: ['style', 'main'], // 先查找package.json中的style对应的路径,若无再查找main(默认是查找main)
        mainFiles: [], //入口文件名(默认index.js)
        alias: { //设置别名
            bootstrap: 'bootstrap/dist/css/bootstrap.css'
        }
    }
}

 

二十一、定义编译时全局常量

1. 在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。
    plugins: [
        new webpack.DefinePlugin({ //创建一个在编译时可以配置的全局常量(引号里是表达式,字符串需用JSON.stringify())
            DEV: JSON.stringify('dev'), //相当于 var DEV='dev' 
            BOOL: 'true', //相当于var BOOL = true 
            EXPRESS: '1+2' // 相当于var EXPRESS = 1+2 
        })
    ]
}

在src/index.js中:

let url = '';
if(DEV === 'dev') {
    url = 'localhost: 8080';
} else {
    url = 'http://juntao.com';    
}

console.log(url);

二十二、区分不同环境

 1.安装webpack.merge

2.将webpack.config.js改为webpack.base.js

3.新建webp.dev.js和webpack.prod.js:

const {smart} = require('webpack-merge');
let base = require('./webpack.base.js');

module.exports = smart(base, {
    mode: 'development',
    devServer: {

    }
})

 

const {smart} = require('webpack-merge');
let base = require('./webpack.base.js');

module.exports = smart(base, {
    mode: 'production',
    
})

 

二十三、不解析文件依赖库(优化)

1. 在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。
    module: {
        noParse: /jquery | loader/ // 不去解析这些文件的依赖库(当这些文件无依赖库时可这样设置)
    }
}

 

二十四、忽视插件中引入配置的代码

1. 在webpack.config.js中配置:

。。。。
module.exports = {
    。。。。
    plugins:[
        new webpack.IgnorePlugin(/\.\/locale/, /moment/) //moment插件中如果使用./locale引入配置,则忽略
    ]
}

 

二十五、动态链接库(第三方库过大,打包起来耗时间时可用)

以react、react-DOM为例:

1.安装react、react-dom、babel-loader、@babel/core、@babel/preset-env、@babel/preset-react

2.创建webpack.react.js:

const path = require('path');
const webpack = require('webpack');
module.exports = {
    mode: 'development',
    entry: {
        react: ['react', 'react-dom']
    },
    output: {
        filename: '__dll__[name].js',
        path: path.resolve(__dirname, 'dist'),
        library: '__dll__[name]', //为打包输出的东西设置变量名
        libraryTarget: 'var' //声明变量的关键字(默认var)
    },
    plugins: [
        new webpack.DllPlugin({ //生成任务清单
            name: '__dll__[name]', //引入打包的东西,因此name需与output.library相同
            path: path.resolve(__dirname, 'dist', 'manifest.json') 
        })
    ]
}

3.打包:npx webpack --config webpack.react.js,生成__dll__react.js和manifest.json。

manifest.json清单中的内容可以在__dll__react.js中找到。

4.webpack.config.js:将manifest.json清单引入

const path= require('path');
const webpack = require('webpack');
const htmlWebpackPlugin = require('html-webpack-plugin');


module.exports = {
    mode: 'development',
    entry: './src/index.js',
    output: {
        filename: 'bundle.js',
        path: path.resolve(__dirname, 'dist')
    },
    module: {
        noParse: /jquery | loader/,// 不去解析这些文件的依赖库(当这些文件无依赖库时可这样设置)
        rules: [
            {
                test: /\.js$/,
                exclude: /node_module/,
                include: path.resolve('src'),
                use: {
                    loader: 'babel-loader',
                    options:{
                        presets: [
                            '@babel/preset-env',
                            '@babel/preset-react'
                        ]
                    }
                }
            }
        ]
    },
    plugins:[
        new htmlWebpackPlugin({
            template: './public/index.html',
        }),
        new webpack.IgnorePlugin(/\.\/locale/, /moment/), //moment插件中如果使用./locale引入配置,则忽略
        new webpack.DllReferencePlugin({
            manifest: path.resolve(__dirname, 'dist', 'manifest.json')
        })
    ]
}

 5.在src/inedx.html中引入__dll__react.js:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <title>Page Title</title>
    <meta name="viewport" content="width=device-width, initial-scale=1">
    
</head>
<body>
    <div id="root"></div>
    <script src="__dll__react.js"></script>
</body>
</html>

 

二十六、多线程打包

1.安装happyhack

2.在webpack.config.js中配置:

 

。。。。
const Happypack = require('happypack');
module.exports = {
   。。。。
    module: {
        。。。。
        rules: [
            {
                test: /\.js$/,
                exclude: /node_module/,
                include: path.resolve('src'),
                use: 'Happypack/loader?id=js' // 用Happypack中id=js的loader配置打包
            },
            {
                test: /\.css$/,
                use: 'Happypack?loader?id=css'
            }
        ]
    },
    plugins:[
        new Happypack({
            id: 'js',
            use:[
                {
                    loader: 'babel-loader',
                    options: {
                        presets: [
                            '@babel/preset-env',
                            '@babel/preset-react'
                        ]
                    }
                }
            ]
        }),
        new Happypack({
            id: 'css',
            use: ['style-loader','css-loader']
        }),
        。。。。
    ]
}

 

二十七、webpack中自动优化

1.import 在生产环境下会自动去除没用的代码(内置tree-shaking自动删除)

2.require会把结果放在default上,不会自动删除没有用到的代码

3.webpack中会自动忽略一下可以简化的代码

let a =1; let b =1; let c =1; let d = a+b+c;打包时会直接忽略abc,把d设为3

 

二十八、抽离公共代码

1.在webpack.config.js中配置:

。。。。
module.exports = {
    mode: 'production', //development
    。。。。
    optimization: { //
        splitChunks: { //分割代码块
            cacheGroups: { //缓存组
                common: { //公共模块抽离    
                    chunks: 'initial', //一开始就进行抽离
                    minSize: 0, //文件大于0k时进行抽离
                    minChunks: 2 //使用两次就进行抽离
                },
                vendor: { //第三方模块抽离
                    priority: 1, //优先抽离
                    test: /node_modules/, //node_modules中的文件的话就处理
                    chunks:'initial',
                    minSize: 0,
                    minChunks: 2
                }
            }
        }
    }
}

2.创建one.js和two.js

console.log('one')
console.log('two')

3.在index.js和other.js中分别引入one.js和two.js:

import './one.js'
import './two.js'

4.打包: npm run build,生成抽离出来的代码文件common~index~other.js

 

二十九、懒加载

使用import()实现懒加载, 返回promise,打包生成1.js文件

1.创建src/source.js

console.log('source22222');

2.在src/index.js中:

var button = document.createElement('button');
button.innerHTML = '按钮';
button.addEventListener('click', function() {
    console.log(111111);
    import('./source.js').then((data) => {
        console.log(data);
    })
})
document.body.appendChild(button);

3.打包:npm run build,生成1.js:

(window.webpackJsonp=window.webpackJsonp||[]).push([[1],[,function(o,n){console.log("source22222")}]]);

 

三十、模块热替换

模块热替换:在运行时更新各种模块,而无需进行完全刷新。(搭配 webpack-dev-server在开发环境中使用)

1.在webpack.config.js中配置:

。。。。
module.exports = {
   。。。。
    plugins:[
        。。。。
        new webpack.NamedModulesPlugin(), // 显示模块的相对路径
        new webpack.HotModuleReplacementPlugin()
    ]
}

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值