webpack之代码分离-libraries

浏览器缓存机制

浏览器的缓存机制,简单的说就是将一次请求的资源保存在本地。客户端和服务端通过http请求约定怎么去使用、更新这个资源。利用这个机制,我们可以减少资源传输,提高页面加载速度。

  • Expires 规定了缓存过期时间
  • Cache-Control 规定了缓存存活时间
  • Last-Modified 该资源最后修改时间
  • If-Modified-Since 如果资源在该日期之后发生修改,则进行更新。
  • ETag ETag 是代表该文件的唯一字符串,是第二种检查缓存是否需要更新的机制。
  • If-None-Match 如果ETag与之不相同则进行更新。

代码分离

单入口只会生成一个打包的bundle.js,它既包括了页面独立的JS文件,也包含了许多从CDN获取的,公用的模块。
哪怕我们对页面的独立JS进行微小改动,bundle.js也需要重新打包。用户再次访问时,就需要下载完整的bundle.js。为了充分使用浏览器的缓存机制,我们需要将公共库单独打包。

CommonsChunkPlugin

单纯的使用多入口,因为所有依赖都要被打包,并不能解决问题。于是需要使用插件CommonsChunkPlugin

修改配置文件webpack.config.js

var webpack = require('webpack');
var path = require('path');

module.exports = function(env) {
    return {
        entry: {
            main: './index.js',
            vendor: 'moment'//引入的库
        },
        output: {
            filename: '[name].[chunkhash].js',
            path: path.resolve(__dirname, 'dist')
        },
        plugins: [
            new webpack.optimize.CommonsChunkPlugin({
                name: 'vendor' // 指定公共 bundle 的名字。
            })
        ]
    }
}

隐式生成vendor

var webpack = require('webpack');
var path = require('path');

module.exports = function() {
    return {
        entry: {
            main: './index.js'
        },
        output: {
            filename: '[name].[chunkhash].js',
            path: path.resolve(__dirname, 'dist')
        },
        plugins: [
            new webpack.optimize.CommonsChunkPlugin({
                name: 'vendor',
                minChunks: function (module) {
                   // 该配置假定你引入的 vendor 存在于 node_modules 目录中
                   return module.context && module.context.indexOf('node_modules') !== -1;
                }
            })
        ]
    };
}

Manifest

Manifest就是webapck runtime code,它支撑页面运行时,webpack可以处理打包后的文件。
当webpack只生成一个bundle时,Manifest这部分代码也被打包进入bundle。而当生成多个bundle时,这部分代码会被放入公共库vendor中。
这就导致vendor文件的hash发生改变。使得浏览器缓存无法生效。

故而,我们需要将Manifest单独独立出来。代码如下
webpack.config.js

var webpack = require('webpack');
var path = require('path');

module.exports = function(env) {
    return {
        entry: {
            main: './index.js',
            vendor: 'moment'
        },
        output: {
            filename: '[name].[chunkhash].js',
            path: path.resolve(__dirname, 'dist')
        },
        plugins: [
            new webpack.optimize.CommonsChunkPlugin({
                names: ['vendor', 'manifest'] // 指定公共 bundle 的名字。
            })
        ]
    }
};

隐式

var webpack = require('webpack');
var path = require('path');

module.exports = function() {
    return {
        entry: {
            main: './index.js' //注意这里只有一个入口
        },
        output: {
            filename: '[name].[chunkhash].js',
            path: path.resolve(__dirname, 'dist')
        },
        plugins: [
            new webpack.optimize.CommonsChunkPlugin({
                name: 'vendor',
                minChunks: function (module) {
                   // 该配置假定你引入的 vendor 存在于 node_modules 目录中
                   return module.context && module.context.indexOf('node_modules') !== -1;
                }
            }),
            //CommonChunksPlugin 将从 vendor和bundles中提取所有的公用库
            //但由于已经没有其他公用模块了,故而只会将runtime code存入manifest中
            new webpack.optimize.CommonsChunkPlugin({
                name: 'manifest' 
            })
        ]
    };
}
最后编辑于 :
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容