CommonsChunkPlugin的参数详解

Q1:请问参数name和entry中的key有什么关系?

Q2:请问参数name和参数filename有什么关系?

Q3:请问参数chunks和minChunks有什么关系?

阅读 6.6k
1 个回答

官方文档
https://webpack.js.org/plugin...
下面是对官方文档英文的翻译- -
http://www.jianshu.com/p/2b81...

然后说一下:

//////////////////////////第一:[name]的含义///////////////////////////////////////

这是一个我们需要使用的公共组件foo.js

//foo.js
export let foo = 123;

---------------------------情况A:只有一个入口文件----------------------------

//入口文件
  entry: {
    page1: './src/js/entry1.js'
  }
//提取公共chuck的name
  new CommonsChunkPlugin({ name: 'vendor' })

然后我们引入foo.js

//entry1.js
import { foo } from './components/foo.js';
console.log(`${foo}-entry1`);

结果:foo.js会和entry1被打包到一起变成page1,webpack的运行文件会被抽离出来成为vendor.js

---------------------------情况B:两个入口文件----------------------------

//入口文件
  entry: {
    page1: './src/js/entry1.js',
    page2: './src/js/entry2.js'
  }
//提取公共chuck的name
  new CommonsChunkPlugin({ name: 'vendor' })

然后entry1和entry2都引入foo.js

//entry1.js
import { foo } from './components/foo.js';
console.log(`${foo}-entry1`);
//entry2.js
import同上
console.log(`${foo}-entry2`);

结果:entry1和entry2会分别被打包成page1、page2,webpack运行文件和foo.js会被抽取成为vendor

---------------------------情况C:有的入口没引用foo.js----------------------------

//入口文件
  entry: {
    page1: './src/js/entry1.js',//引用foo.js
    page2: './src/js/entry2.js',//引用foo.js
    page3: './src/js/entry3.js',//新增入口,不引用foo.js
  }
//提取公共chuck的name
  new CommonsChunkPlugin({ name: 'vendor' })

结果:会生成page123三个js文件,并且foo.js会被包含在page1和page2中,并没有被抽离出来。。vendor.js里则只有webpack运行文件,等于公共模块功能未实现.

此时就体现出在入口中指定公共模块的重要性了,就是下面的情况D

---------------------------情况D:指定公共文件入口----------------------------

//入口文件
  entry: {
    page1: './src/js/entry1.js',//不引用foo.js
    page2: './src/js/entry2.js',//引用foo.js
    page3: './src/js/entry3.js',//引用foo.js
    'vendor': ['./src/js/components/foo.js']
  }
//提取公共chuck的name
  new CommonsChunkPlugin({ name: 'vendor' })

此时我们指定了新入口vendor,并且它指向foo.js
三个入口有的引用了foo,有的则没有

结果:不管entry1/2/3是否引用foo,foo.js和webpack运行文件都被抽取出来成为vendor.

所以此方式可以用来抽取第三方类库和框架,这样每一个入口文件无论是否调用它们,都不会将它们重复打包进去,例如:

'vendor': ['react','jquery','others']

---------------------------情况E:name指定的chunk不存在----------------------------
条件:

1、入口文件里没写vendor:[...]
2、entry1和entry2都没引用任何文件
结果:那么这样会发现生成的vendor.js里是webpack运行文件加一个([])空chunk;

//////////////////////////第二:[filename]的含义///////////////////////////////////////

这个很简单,filename就是打包出来的公共模块的实际名称

1、当filename未定义,就默认使用name的名称作为打包后文件名
2、当filename已指定,就用它指定的名称了

//////////////////////////第三:[minchunks]////////////////////////////////////

minchunks表示模块抽取的最小被调用次数,也就是说minchunks:10,那么这个chunk最少需要被调用10次,webpack才会把它当做一个公共模块抽取出来。

//////////////////////////*第三:[chunks]////////////////////////////////////
前面的都是把公共模块打包成了一整块vendor.js,那么如果需要从这个vendor.js中再抽取就需要用到chunks选项

//入口文件
  entry: {
    page1: './src/js/entry1.js',
    page2: './src/js/entry2.js',
    'vendor': ['./src/js/components/foo.js']
  }
//公共模块
    new CommonsChunkPlugin({ name: 'vendor' }),
    new CommonsChunkPlugin({ name: 'manifest', chunks: ['vendor'] }),

结果:foo.js和webpack的运行文件会先被生成vendor.js,然后webpack的运行文件会被从vendor中再次抽出,生成一个manifest.js文件

上面的写法也等于:

        new webpack.optimize.CommonsChunkPlugin({
            names: ['vendor', 'manifest'],
        }),

最后,实践出真知。。多多看别人的例子和自己尝试吧。

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题
宣传栏