• Webpack的使用


    一、安装:在全局环境下安装

    $ npm i -g webpack webpack-dev-server

    二、运行命令,如果不能自动打开网页,在浏览器的地址栏输入:http://127.0.0.1:8080

    npm run dev

    webpack是为浏览器构建JavaScript模块脚本的quan前端工具。它可以类似于Browserify一样,但是能做的更多。

    $ browserify main.js > bundle.js
    # be equivalent to
    $ webpack main.js bundle.js

    Webpack需要一个配置文件名叫webpack.config.js,是一个commonJS的模块。有了这个文件之后,可以调用webpack,不需要别的参数。一些常用的命令行:

    webpack – building for development
    webpack -p – building for production (minification)
    webpack --watch – for continuous incremental building
    webpack -d – including source maps
    webpack --colors – making building output pretty

    可以在package.json文件中对这些命令做个性化处理。

    "scripts": {
        "dev": "webpack-dev-server --open",
        "build": "webpack -p"
      },

    执行 npm run dev 就是执行 webpack-dev-server --open,npm run build就是执行webpack -p。

    三、入口文件:是webpack用来读取以创建bundle.js的文件。Webpack根据webpack.config.js创建bundle.js。webpack.config.js代码如下:

    module.exports = {
      entry: './main.js',    // main.js是入口文件
      output: {
        filename: 'bundle.js'
      }
    };

    四、多个入口文件:webpack.config.js

    module.exports = {
      entry: {
        bundle1: './main1.js',
        bundle2: './main2.js'
      },
      output: {
        filename: '[name].js'    /**注意[name]**/
      }
    };

    五、babel 加载器

    加载器是预处理程序,在webpack构建过程之前转换应用程序的资源文件。例如,Bable-loader可以将JSX/ES6文件转换成正常的JS文件,之后Webpack开始构建这些JS文件。需要在webpack.config.js里配置module。

    module.exports = {
      entry: './main.jsx',
      output: {
        filename: 'bundle.js'
      },
      module: {
        rules: [
          {
            test: /.jsx?$/,
            exclude: /node_modules/,
            use: {
              loader: 'babel-loader',
              options: {
                presets: ['es2015', 'react']   // 需要配置插件 babel-preset-es2015 和 babel-preset-react(安装) 
              }
            }
          }
        ]
      }
    };

    题外话:提醒一下JSX的格式

    // main.jsx
    const React = require('react');
    const ReactDOM = require('react-dom');
    
    ReactDOM.render(
      <h1>Hello, world!</h1>,
      document.querySelector('#wrapper')
    );

    六、css加载器 css-loader

    webpack可以在JS文件中加载css文件,使用css-loader

    webpack.config.js中的配置

    module.exports = {
      entry: './main.js',
      output: {
        filename: 'bundle.js'
      },
      module: {
        rules:[
          {
            test: /.css$/,
            use: [ 'style-loader', 'css-loader' ]
          },
        ]
      }
    };

    需要两个加载器:css-loader 和 style-loader(为了向HTML代码中插入<style>标签)

    七、Image loader

    webpack.config.js代码:

    module.exports = {
      entry: './main.js',
      output: {
        filename: 'bundle.js'
      },
      module: {
        rules:[
          {
            test: /.(png|jpg)$/,
            use: [
              {
                loader: 'url-loader',
                options: {
                  limit: 8192
                }
              }
            ]
          }
        ]
      }
    };

    main.js

    var img1 = document.createElement("img");
    img1.src = require("./small.png");
    document.body.appendChild(img1);
    
    var img2 = document.createElement("img");
    img2.src = require("./big.png");
    document.body.appendChild(img2);

    url-loader会把图片类型的文件转换到img标签中,当图片的大小小于limit的值,会转换到data URL上??????

    八、CSS Module

    css-loader?modules 查询参数模块使CSS-modules提供了一个本地作用域的css,可以用:global(selector)关闭。

    app.css

    /* local scope */
    .h1 {
      color:red;
    }
    
    /* global scope */
    :global(.h2) {
      color: blue;
    }

    九、UglifyJS 插件。webpack有自己的插件系统来拓展它的功能,UglifyJS可以压缩输入文件bundle.js的JS代码。

    main.js

    var longVariableName = 'Hello';
    longVariableName += ' World';
    document.write('<h1>' + longVariableName + '</h1>');

    webpack.config.js

    var webpack = require('webpack');
    var UglifyJsPlugin = require('uglifyjs-webpack-plugin');
    
    module.exports = {
      entry: './main.js',
      output: {
        filename: 'bundle.js'
      },
      plugins: [
        new UglifyJsPlugin()
      ]
    };

    最后main.js会被压缩成:

    var o="Hello";o+=" World",document.write("<h1>"+o+"</h1>")

    十、HTML Webpack plugin 和 open browser webpack plugin

    HTML Webpack plugin 可以创建一个index.html文件,open browser webpack plugin可以在webpack加载时打开一个新的浏览器标签页

    十一、environment flag

    就好像是设置一个变量,只有设置了这个变量的环境才可以访问某些代码,例如:

    document.write('<h1>Hello World</h1>');
    
    if (__DEV__) {
      document.write(new Date());
    }

    webpack.config.js

    var webpack = require('webpack');
    
    var devFlagPlugin = new webpack.DefinePlugin({
      __DEV__: JSON.stringify(JSON.parse(process.env.DEBUG || 'false'))
    });
    
    module.exports = {
      entry: './main.js',
      output: {
        filename: 'bundle.js'
      },
      plugins: [devFlagPlugin]
    };

    发现package.json有这样的变化

    {
      // ...
      "scripts": {
        "dev": "cross-env DEBUG=true webpack-dev-server --open",
      },
      // ...
    }

    十二、code splitting

    对于很多大型网站应用来说,把所有的代码放在一个单独的文件里效率很低,webpack允许我们把一个大型的JS文件分割成几个块,如果在某些情况下只需要某些代码块,则可以俺需要加载这些块。webpack使用require.ensure来定义一个分割点。

    main.js

    require.ensure(['./a'], function (require) {
      var content = require('./a');
      document.open();
      document.write('<h1>' + content + '</h1>');
      document.close();
    });

    require.ensure告诉webpack ./a.js从bundle.js 分离了出来,建立了一个单独的块文件。webpack负责这些dependency,输出文件,和运行时间等,不需要在index.html和webpack.config.js添加其他的代码。webpack实际上建立了两个输出文件,bundle.js 和 0.bundle.js。Webpack实际上将main.js 和 a.js构建为不同的块(bundle.js 和 0.bundle.js),并在需要时从bundle.js加载0.bundle.js。

    另外一种代码分割的方式 使用bundle-loader。

    // main.js
    
    // Now a.js is requested, it will be bundled into another file
    var load = require('bundle-loader!./a.js');
    
    // To wait until a.js is available (and get the exports)
    //  you need to async wait for it.
    load(function(file) {
      document.open();
      document.write('<h1>' + file + '</h1>');
      document.close();
    });

    十三、common chunk

    当多个JS文件拥有公共块时,可以使用插件CommonsChunkPlugin将公共部分提取到一个单独的文件中,这有助于浏览器的缓存和节省带宽。

    这里的代码不是很理解,先粘贴过来,再研究吧??????

    // main1.jsx
    var React = require('react');
    var ReactDOM = require('react-dom');
    
    ReactDOM.render(
      <h1>Hello World</h1>,
      document.getElementById('a')
    );
    
    // main2.jsx
    var React = require('react');
    var ReactDOM = require('react-dom');
    
    ReactDOM.render(
      <h2>Hello Webpack</h2>,
      document.getElementById('b')
    );
    <html>
      <body>
        <div id="a"></div>
        <div id="b"></div>
        <script src="commons.js"></script>
        <script src="bundle1.js"></script>
        <script src="bundle2.js"></script>
      </body>
    </html>
    var webpack = require('webpack');
    
    module.exports = {
      entry: {
        bundle1: './main1.jsx',
        bundle2: './main2.jsx'
      },
      output: {
        filename: '[name].js'
      },
      module: {
        rules:[
          {
            test: /.js[x]?$/,
            exclude: /node_modules/,
            use: {
              loader: 'babel-loader',
              options: {
                presets: ['es2015', 'react']
              }
            }
          },
        ]
      },
      plugins: [
        new webpack.optimize.CommonsChunkPlugin({
          name: "commons",
          // (the commons chunk name)
    
          filename: "commons.js",
          // (the filename of the commons chunk)
        })
      ]
    }

    十四、Vendor clunk

    可以将脚本中的供应商库从CommonsChunkPlugin中提取到单独的文件中。

    main.js

    var $ = require('jquery');
    $('h1').text('Hello World');

    index.html

    <html>
      <body>
        <h1></h1>
        <script src="vendor.js"></script>
        <script src="bundle.js"></script>
      </body>
    </html>

    webpack.config.js

    var webpack = require('webpack');
    
    module.exports = {
      entry: {
        app: './main.js',
        vendor: ['jquery'],    // jQuery包含在公共块vendor.js
      },
      output: {
        filename: 'bundle.js'
      },
      plugins: [
        new webpack.optimize.CommonsChunkPlugin({
          name: 'vendor',
          filename: 'vendor.js'
        })
      ]
    };

    ProvidePlugin 插件可以使一个变量在每个模块中像一个全局变量一样使用,不需要重新import或者require。

    // main.js
    $('h1').text('Hello World');
    
    
    // webpack.config.js
    var webpack = require('webpack');
    
    module.exports = {
      entry: {
        app: './main.js'
      },
      output: {
        filename: 'bundle.js'
      },
      plugins: [
        new webpack.ProvidePlugin({
          $: 'jquery',
          jQuery: 'jquery'
        })
      ]
    };

    十五、exposing global variables 公开全局变量

    如果想使用一些全局变量,但是不想使他们包含在Webpack包里,可以在webpack.config.js中启用external字段。

    例如,新建一个data.js

    // data.js
    var data = 'Hello World';

    index.html

    <html>
      <body>
        <script src="data.js"></script>
        <script src="bundle.js"></script>
      </body>
    </html>

    但是此时,出口文件只有一个bundle.js 而不是data.js。data可以作为一个全局变量。

    webpa.config.js

    // webpack.config.js
    module.exports = {
      entry: './main.jsx',
      output: {
        filename: 'bundle.js'
      },
      module: {
        rules:[
          {
            test: /.js[x]?$/,
            exclude: /node_modules/,
            use: {
              loader: 'babel-loader',
              options: {
                presets: ['es2015', 'react']
              }
            }
          },
        ]
      },
      externals: {
        // require('data') is external and available
        //  on the global var data
        'data': 'data'
      }
    };

    可以在我们的入口JS文件中使用这个全局变量。

    // main.jsx
    var data = require('data');
    var React = require('react');
    var ReactDOM = require('react-dom');
    
    ReactDOM.render(
      <h1>{data}</h1>,
      document.body
    );

    也可以把react 和 react-dom 放入externals变量里,方便减少bundle.js的创建时间和大小。

    UglifyJs Plugin

  • 相关阅读:
    151. 翻转字符串里的单词(trim函数与split函数的使用)
    Java splt方法,按照空格分割字符串成为字符串数组(转载)
    137. 只出现一次的数字 II(没完全按要求做)
    129. 求根到叶子节点数字之和(递归
    125. 验证回文串(replaceAll()与toLowerCase())
    美团上海Java实习(已offer)面经(还没写完,转载)
    二叉树中序遍历
    优先队列/最大堆
    防御式编程
    JWT
  • 原文地址:https://www.cnblogs.com/CCCLARITY/p/8421879.html
Copyright © 2020-2023  润新知