深入浅出webpack之externals的使用


Posted in Javascript onDecember 04, 2017

我们通常在做项目时可能会把第三方库打包到bundle中,比如下面这张图

深入浅出webpack之externals的使用

如果不想把第三方库打包到bundle中,这就有了externals。官方的使用externals比较简单

externals

官网文档解释的很清楚,就是webpack可以不处理应用的某些依赖库,使用externals配置后,依旧可以在代码中通过CMD、AMD或者window/global全局的方式访问。

只需三步——

1.在HTML中引入第三方库的cdn

2.在webpack中配置externals

externals: {
 jquery: "jQuery",
}

3.在js中引用

const $ = require("jquery");
$("#content").html("<h1>hello world</h1>");

好,现在我们可以随心所欲的使用jquery插件并保证不会打包到bundle中。external是怎么办到的呢?下面我们通过bundle的源码来分析下原理。

深入浅出webpack之externals的使用

这里的/* 0 */和__webpack_require__分别指打包前js对应的模块函数,这里就不细说了。这里可以看到module.exports = jQuery,就是说我们externals中的key指的是require的东西,value指的就是它,就是说“当require的参数是jquery的时候,使用jQuery这个全局变量引用它”。这种最简洁的externals配置方式为默认的global模式,就是在window上挂一个全局变量,然后直接可以使用这个变量。具体的流程是这样,我们在源码中使用require('jquery')后,可以直接把jquery加到externals中,得到一个打包的trunk.js,但是在引入这个trunkjs之前,肯定要先引入jquery这个库文件,这个库文件会创建一个全局变量jQuery,而咱们的trunkjs中externals的jquery是global模式,所以实际上trunkjs引入jquery的时候,就会从全局变量中引用,即module.export = jQuery

深入浅出webpack之externals的使用

当然,既然是通过这种externals方式,其实我们可以不用require引入,直接使用全局变量也是可以的。

jQuery("#content").html("<h1>hello world</h1>");

大家如果注意到我刚说过的global模式的话,没错,你也许已经猜到了,我可以任意的使用不同的输出方式。如果打包文件我想运行到node环境下,我得使用commonjs规范,所以你要这么写。

externals: {
 jquery: "commonjs2 jQuery",
}

打包后会是这样子。

深入浅出webpack之externals的使用

然后我的项目中还用到了lodash,也想把它从bundle中移除,之前我的代码是这样子,引的是npm包

深入浅出webpack之externals的使用

深入浅出webpack之externals的使用

现在我们的externals配置如下

externals: {
  jquery: "jQuery",
  _: "lodash"

}

深入浅出webpack之externals的使用

我们必须要去掉这个const ,否则的话会报一个错误 lodash is not defined。为什么会这样呢?因为我们的lodash输出是global格式的,我在这里先卖一个关子,我们先统一一下输出格式,加一个libraryTarget字段

深入浅出webpack之externals的使用

这个东西是干嘛用的呢?

他是我们输出文件的模块化规范,想想我们上面配置的commonjs jquery是运行在node下,总之记住一句话——我们最长使用的模块化方案是commonjs2和umd,前者是为node环境,后者是为浏览器环境。一共有这几种规范:

"var" - Export by setting a variable: var Library = xxx (default)

"this" - Export by setting a property of this: this["Library"] = xxx
"commonjs" - Export by setting a property of exports: exports["Library"] = xxx
"commonjs2" - Export by setting module.exports: module.exports = xxx
"amd" - Export to AMD (optionally named - set the name via the library option)
"umd" - Export to AMD, CommonJS2 or as property in root

深入浅出webpack之externals的使用

然后报这个错误,也就是说我们的模块没有正确的输出,回到我们的externals,它更多的是指定当你引用一个包的时候,这个包(lodash)应该遵循哪种模块化方式(common,root,amd等等)引入,这意思就是说,打包的时候不需要关心他到底怎么输出。

externals: {
  jquery: "jQuery",
  lodash: {
   commonjs: 'lodash',
   commonjs2: 'lodash',
   amd: 'lodash',
   root: '_'
  }
 },

ok,记得要将之前的覆盖掉,替换成下面的require,因为在externals中我们规范的commmonjs规范为lodash

深入浅出webpack之externals的使用

也就是说,这就是我们最初的代码,即没有用过externals时候的代码,看,也就是说我们只需要配置externals和libraryTarget就可以,其他的业务逻辑代码不需要改变。包括我们的项目中还用了echarts,这个通通不用改变!!!!!

深入浅出webpack之externals的使用

也就是说最终的代码是externals配合libraryTarget一起使用,如果去掉umd的话,会报这个错误

深入浅出webpack之externals的使用

相应的源码是这样子

深入浅出webpack之externals的使用

就是说我不知道通过那种方式输出,所以我应该告诉webpack,我通过umd方式输出,即将你的 lodash 暴露为所有的模块定义下都可运行的方式。它将在 CommonJS, AMD 环境下运行,或将模块导出到 global 下的变量.加上umd的源码如下

深入浅出webpack之externals的使用

看到了吧,我通过require('lodash')引入模块,输出走的是commonjs规范,贴下最终的配置

entry: {
  main: './src/index.js'
 },
 externals: {
  jquery: "jQuery",
  lodash: {
   commonjs: 'lodash',
   commonjs2: 'lodash',
   amd: 'lodash',
   root: '_'
  }
 },
 output: {
  filename: '[name].[chunkhash].js',
  path: path.resolve(__dirname,'dist'),
  libraryTarget: 'umd'
 },

 以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
Wordpress ThickBox 点击图片显示下一张图的修改方法
Dec 11 Javascript
JavaScript黑洞数字之运算路线查找算法(递归算法)实例
Jan 28 Javascript
jQuery的each循环用法简单示例
Jun 12 Javascript
一步一步封装自己的HtmlHelper组件BootstrapHelper(二)
Sep 14 Javascript
用v-html解决Vue.js渲染中html标签不被解析的问题
Dec 14 Javascript
微信小程序 picker-view 组件详解及简单实例
Jan 10 Javascript
解决jQuery ajax动态新增节点无法触发点击事件的问题
May 24 jQuery
解决AjaxFileupload 上传时会出现连接重置的问题
Jul 07 Javascript
原生js实现拖拽功能基本思路详解
Apr 18 Javascript
解决百度Echarts图表坐标轴越界的方法
Oct 17 Javascript
jQuery实现的记住帐号密码功能完整示例
Aug 03 jQuery
解决vue动态路由异步加载import组件,加载不到module的问题
Jul 26 Javascript
基于js 字符串indexof与search方法的区别(详解)
Dec 04 #Javascript
基于JavaScript中字符串的match与replace方法(详解)
Dec 04 #Javascript
基于JSONP原理解析(推荐)
Dec 04 #Javascript
利用Javascript获取选择文本所在的句子详解
Dec 03 #Javascript
微信小程序图片选择区域裁剪实现方法
Dec 02 #Javascript
vue中eventbus被多次触发以及踩过的坑
Dec 02 #Javascript
Angular之toDoList的实现代码示例
Dec 02 #Javascript
You might like
索尼SONY ICF-SW7600GR电路分析与改良
2021/03/02 无线电
php中通过正则表达式下载内容中的远程图片的函数代码
2012/01/10 PHP
深入探讨:PHP使用数据库永久连接方式操作MySQL的是与非
2013/06/05 PHP
CodeIgniter使用smtp服务发送html邮件的方法
2015/06/10 PHP
php如何实现只替换一次或N次
2015/10/29 PHP
利用PHP获取网站访客的所在地位置
2017/01/18 PHP
php中的单引号、双引号和转义字符详解
2017/02/16 PHP
php 广告点击统计代码(php+mysql)
2018/02/21 PHP
用jquery实现点击栏目背景色改变
2012/12/10 Javascript
js播放wav文件(源码)
2013/04/22 Javascript
window.showModalDialog()返回值的学习心得总结
2014/01/07 Javascript
jquery教程ajax请求json数据示例
2014/01/13 Javascript
javascript的push使用指南
2014/12/05 Javascript
在JavaScript应用中使用RequireJS来实现延迟加载
2015/07/01 Javascript
基于Vue.js实现简单搜索框
2020/03/26 Javascript
Bootstrap学习笔记 轮播(Carousel)插件
2017/03/21 Javascript
JavaScript模拟文件拖选框样式v1.0的实例
2017/08/04 Javascript
vue-router 导航钩子的具体使用方法
2017/08/31 Javascript
利用yarn代替npm管理前端项目模块依赖的方法详解
2017/09/04 Javascript
VUE兄弟组件传值操作实例分析
2019/10/26 Javascript
Vue请求java服务端并返回数据代码实例
2019/11/28 Javascript
解决vue的touchStart事件及click事件冲突问题
2020/07/21 Javascript
vue el-upload上传文件的示例代码
2020/12/21 Vue.js
Python实现投影法分割图像示例(一)
2020/01/17 Python
详解python os.path.exists判断文件或文件夹是否存在
2020/11/16 Python
pandas apply使用多列计算生成新的列实现示例
2021/02/24 Python
使用canvas实现黑客帝国数字雨效果
2020/01/02 HTML / CSS
Kivari官网:在线购买波西米亚服装
2018/10/29 全球购物
提高EJB性能都有哪些技巧
2012/03/25 面试题
董事长秘书工作职责
2014/06/10 职场文书
服务标语口号
2014/07/01 职场文书
2015年小学数学教师工作总结
2015/05/20 职场文书
2015党建工作简报
2015/07/21 职场文书
机关干部纪律作风整顿心得体会
2016/01/23 职场文书
python opencv通过4坐标剪裁图片
2021/06/05 Python
GitHub上77.9K的Axios项目有哪些值得借鉴的地方详析
2021/06/15 Javascript