JavaScript中使用import 和require打包后实现原理分析


Posted in Javascript onMarch 07, 2018

前言:

之前使用ES6写代码,webpack打包后上线,一点问题没有,也看过打包后的代码,长的很乱,也没敢看看咋回事,加载后就是能运行!

今天通过个例子理解一下打包前,和打包后的代码!

1.创建文件夹,并在里面创建两个文件夹,app文件夹和public文件夹,app文件夹用来存放原始数据和我们将写的JavaScript模块,public文件夹用来存放之后供浏览器读取的文件(包括使用webpack打包生成的js文件以及一个 index.html 文件)。接下来我们再创建三个文件:

  • index.html --放在public文件夹中;
  • Greeter.js -- 放在app文件夹中;
  • main.js -- 放在app文件夹中;

此时项目结构如下图所示

项目结构

我们在 index.html 文件中写入最基础的html代码,它在这里目的在于引入打包后的js文件(这里我们先把之后打包后的js文件命名为 bundle.js ,之后我们还会详细讲述)。

<!-- index.html -->
<!DOCTYPE html>
<html lang="en">
 <head>
  <meta charset="utf-8">
  <title>sample Project</title>
 </head>
 <body>
  <div id='root'>
  </div>
  <script src="bundle.js"></script>
 </body>
</html>

我们在 Greeter.js 中定义一个返回包含问候信息的 html 元素的函数,并依据CommonJS规范导出这个函数为一个模块:

// Greeter.js
exports.greet= function() {
 var greet = document.createElement('div');
 greet.textContent = "Hi there and greetings!";
 return greet;
};
exports.USER_INFO = "userInfo";

main.js 文件中我们写入下述代码,用以把 Greeter模块 返回的节点插入页面。

//main.js 
 let {greeter,USER_INFO} =require('./Greeter.js');
console.log(USER_INFO);
document.querySelector("#root").appendChild(greeter());

使用webpack打包后:

(function(modules){     var installedModules = {};  function __webpack_require__(moduleId) {
    if (installedModules[moduleId]) {
      return installedModules[moduleId].exports;
    }
    var module = installedModules[moduleId] = {
      i: moduleId,
      l: false,
      exports: {}
    };
    modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
    module.l = true;
    return module.exports;
  }
  __webpack_require__.m = modules;
  __webpack_require__.c = installedModules;
  __webpack_require__.d = function(exports, name, getter) {
    if (!__webpack_require__.o(exports, name)) {
      Object.defineProperty(exports, name, {
        configurable: false,
        enumerable: true,
        get: getter
      });
    }
  };
  __webpack_require__.n = function(module) {
    var getter = module && module.__esModule ?
    function getDefault() {
      return module['default'];
    }:
    function getModuleExports() {
      return module;
    };
    __webpack_require__.d(getter, 'a', getter);
    return getter;
  };
  __webpack_require__.o = function(object, property) {
    return Object.prototype.hasOwnProperty.call(object, property);
  };
  __webpack_require__.p = "";
  return __webpack_require__(__webpack_require__.s = 0);
})
(
[
(function(module, exports, __webpack_require__) {
  //main.js
  let {
    greeter,
    USER_INFO
  } = __webpack_require__(1);
  console.log(USER_INFO);
  document.querySelector("#root").appendChild(greeter());
}),
(function(module, exports) {
  // Greeter.js
  exports.greet = function() {
    var greet = document.createElement('div');
    greet.textContent = "Hi there and greetings!";
    return greet;
  };
  exports.USER_INFO = "userInfo";
})
]);

首先最为层是包裹着立即执行函数(加粗的内容),参数是一个数组,数组中每一项是对应的模块,每个模块包裹在 (function(module, exports, __webpack_require__) {//模块内容 });

立即执行函数运行执行  return __webpack_require__(__webpack_require__.s = 0);

也就是执行传入数组中的第一个模块main.js

将运行后的每个模块挂载到installedModules = {}上,当下个需要这个模块直接返回当前模块,不在运行代码块了!

接下来将require改为import看看打包后的如何实现

我们将 Greeter.js的信息改为如下 :

// Greeter.js
export default function() {
 var greet = document.createElement('div');
 greet.textContent = "Hi there and greetings!";
 return greet;
};
export const USER_INFO = "userInfo";
main.js 文件中的代码,修改后
//main.js 
import greet,{USER_INFO} from './Greeter.js';
console.log(USER_INFO);
document.querySelector("#root").appendChild(greet());

然后我们再次打包:

(function(modules) {
  var installedModules = {};
  function __webpack_require__(moduleId) {
    if (installedModules[moduleId]) {
      return installedModules[moduleId].exports;
    }
    var module = installedModules[moduleId] = {
      i: moduleId,
      l: false,
      exports: {}
    };
    modules[moduleId].call(module.exports, module, module.exports, __webpack_require__);
    module.l = true;
    return module.exports;
  }
  __webpack_require__.m = modules;
  __webpack_require__.c = installedModules;
  __webpack_require__.d = function(exports, name, getter) {
    if (!__webpack_require__.o(exports, name)) {
      Object.defineProperty(exports, name, {
        configurable: false,
        enumerable: true,
        get: getter
      });
    }
  };
  __webpack_require__.n = function(module) {
    var getter = module && module.__esModule ?
    function getDefault() {
      return module['default'];
    }: function getModuleExports() {
      return module;
    };
    __webpack_require__.d(getter, 'a', getter);
    return getter;
  };
  __webpack_require__.o = function(object, property) {
    return Object.prototype.hasOwnProperty.call(object, property);
  };
  __webpack_require__.p = "";
  return __webpack_require__(__webpack_require__.s = 0);
})([(function(module, __webpack_exports__, __webpack_require__) {
  "use strict";
  Object.defineProperty(__webpack_exports__, "__esModule", {
    value: true
  });
  var __WEBPACK_IMPORTED_MODULE_0__Greeter_js__ = __webpack_require__(1);
  //main.js
  console.log(__WEBPACK_IMPORTED_MODULE_0__Greeter_js__["a"]);
  document.querySelector("#root").appendChild(Object(__WEBPACK_IMPORTED_MODULE_0__Greeter_js__["b"])());
}),
(function(module, __webpack_exports__, __webpack_require__) {
  "use strict";
  __webpack_exports__["b"] = (function() {
    var greet = document.createElement('div');
    greet.textContent = "Hi there and greetings!";
    return greet;
  });;
  const USER_INFO = "userInfo";
  __webpack_exports__["a"] = USER_INFO;
})]);

总结

以上所述是小编给大家介绍的JavaScript中使用import 和require打包后实现原理分析,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对三水点靠木网站的支持!

Javascript 相关文章推荐
JS中confirm,alert,prompt函数区别分析
Jan 17 Javascript
基于jquery实现的上传图片及图片大小验证、图片预览效果代码
Apr 12 Javascript
javascript:void(0)是什么意思示例介绍
Nov 17 Javascript
使用JSON.parse将json字符串转换成json对象的时候会出错
Sep 04 Javascript
使用js实现的简单拖拽效果
Mar 18 Javascript
纯JavaScript实现的兼容各浏览器的添加和移除事件封装
Mar 28 Javascript
js实现仿百度风云榜可重复多次调用的TAB切换选项卡效果
Aug 31 Javascript
利用jquery获取select下拉框的值
Nov 23 Javascript
微信小程序 五星评分的实现实例
Aug 04 Javascript
vue.js的computed,filter,get,set的用法及区别详解
Mar 08 Javascript
JavaScript实现单图片上传并预览功能
Sep 30 Javascript
如何在JavaScript中正确处理变量
Dec 25 Javascript
Vue-cli项目获取本地json文件数据的实例
Mar 07 #Javascript
在vue项目中,使用axios跨域处理
Mar 07 #Javascript
vue中axios解决跨域问题和拦截器的使用方法
Mar 07 #Javascript
node下使用UglifyJS压缩合并JS文件的方法
Mar 07 #Javascript
angularjs使用gulp-uglify压缩后执行报错的解决方法
Mar 07 #Javascript
Vue+ElementUI实现表单动态渲染、可视化配置的方法
Mar 07 #Javascript
浅谈webpack打包之后的文件过大的解决方法
Mar 07 #Javascript
You might like
解析php多线程下载远程多个文件
2013/06/25 PHP
PHP中CURL的CURLOPT_POSTFIELDS参数使用细节
2014/03/17 PHP
php验证是否是md5编码的简单代码
2014/04/01 PHP
php实现Mysql简易操作类
2015/10/11 PHP
php实现带读写分离功能的MySQL类完整实例
2016/07/28 PHP
解决laravel上传图片之后,目录有图片,但是访问不到(404)的问题
2019/10/14 PHP
laravel中的fillable和guarded属性详解
2019/10/23 PHP
用javascript实现页面打印的三种方法
2007/03/05 Javascript
用jquery实现点击栏目背景色改变
2012/12/10 Javascript
jQuery判断复选框是否勾选的原理及示例
2014/05/21 Javascript
jQuery取id有.的值的方法
2014/05/21 Javascript
js使用for循环查询数组中是否存在某个值
2014/08/12 Javascript
jquery操作HTML5 的data-*的用法实例分享
2014/08/17 Javascript
Js 获取当前函数参数对象的实现代码
2016/06/20 Javascript
web 前端常用组件之Layer弹出层组件
2016/09/22 Javascript
jQuery视差滚动效果网页实现方法经验总结
2016/09/29 Javascript
DropDownList实现可输入可选择(两种版本可选)
2016/12/07 Javascript
vue项目打包后打开页面空白解决办法
2018/06/29 Javascript
详解如何配置vue-cli3.0的vue.config.js
2018/08/23 Javascript
vue通过style或者class改变样式的实例代码
2018/10/30 Javascript
在NPM发布自己造的轮子的方法步骤
2019/03/09 Javascript
浅析Angular 实现一个repeat指令的方法
2019/07/21 Javascript
jQuery利用cookie 实现本地收藏功能(不重复无需多次命名)
2019/11/07 jQuery
vue-cli在 history模式下的配置详解
2019/11/26 Javascript
微信小程序收藏功能的实现代码
2020/06/19 Javascript
Js利用正则表达式去除字符串的中括号
2020/11/23 Javascript
[04:29]2016国际邀请赛中国区预选赛Ehome战队教练采访
2016/06/27 DOTA
[02:46]完美世界DOTA2联赛PWL DAY4集锦
2020/11/03 DOTA
编写Python脚本抓取网络小说来制作自己的阅读器
2015/08/20 Python
python实现将excel文件转化成CSV格式
2018/03/22 Python
Python字符串处理的8招秘籍(小结)
2019/08/13 Python
Python调用scp向服务器上传文件示例
2019/12/22 Python
矫正人员思想汇报
2014/01/08 职场文书
2014年化验室工作总结
2014/11/21 职场文书
高中开学感言
2015/08/01 职场文书
股东出资协议书
2016/03/21 职场文书