模块化原理

CommonJS

实现浏览器对 CommonJS 的支持

// 导出.js
const dateFormat = (date) => {
  return "2020-12-12";
};
const priceFormat = (price) => {
  return "100.00";
};

module.exports = {
  dateFormat,
  priceFormat,
};
// 导入.js
const { dateFormat, priceFormat } = require("./js/format");

console.log(dateFormat("abc"));
console.log(priceFormat("abc"));

Webpack 打包

// 定义了一个对象
// 模块的路径(key): 函数(value)
var __webpack_modules__ = {
  "./src/js/format.js": function (module) {
    const dateFormat = (date) => {
      return "2020-12-12";
    };
    const priceFormat = (price) => {
      return "100.00";
    };

    // 将我们要导出的变量, 放入到module对象中的exports对象
    module.exports = {
      dateFormat,
      priceFormat,
    };
  },
};

// 定义一个对象, 作为加载模块的缓存
var __webpack_module_cache__ = {};

// 是一个函数, 当我们加载一个模块时, 都会通过这个函数来加载
function __webpack_require__(moduleId) {
  // 1.判断缓存中是否已经加载过
  if (__webpack_module_cache__[moduleId]) {
    return __webpack_module_cache__[moduleId].exports;
  }

  // 2.给module变量和__webpack_module_cache__[moduleId]赋值了同一个对象
  var module = (__webpack_module_cache__[moduleId] = { exports: {} });

  // 3.加载执行模块,后两个参数暂时无用处
  __webpack_modules__[moduleId](module, module.exports, __webpack_require__);

  // 4.导出module.exports {dateFormat: function, priceFormat: function}
  return module.exports;
}

// 具体开始执行代码逻辑
(function () {
  // 1.加载./src/js/format.js   解构语法
  const { dateFormat, priceFormat } = __webpack_require__("./src/js/format.js");
  console.log(dateFormat("abc"));
  console.log(priceFormat("abc"));
})();

ESModule

// ./js/math.js
export const sum = (num1, num2) => {
  return num1 + num2;
};
export const mul = (num1, num2) => {
  return num1 * num2;
};
// ./src/es_index.js
import { sum, mul } from "./js/math";

console.log(mul(20, 30));
console.log(sum(20, 30));

Webpack 打包

// 1.定义了一个对象, 对象里面放的是我们的模块映射
var __webpack_modules__ = {
  "./src/es_index.js": function (
    __unused_webpack_module,
    __webpack_exports__,
    __webpack_require__
  ) {
    // 标记是 esModule
    __webpack_require__.r(__webpack_exports__);

    // 包含导入模块代码的对象
    var _js_math__WEBPACK_IMPORTED_MODULE_0__ =
      __webpack_require__("./src/js/math.js");

    console.log(_js_math__WEBPACK_IMPORTED_MODULE_0__.mul(20, 30));
    console.log(_js_math__WEBPACK_IMPORTED_MODULE_0__.sum(20, 30));
  },
  "./src/js/math.js": function (
    __unused_webpack_module,
    __webpack_exports__,
    __webpack_require__
  ) {
    __webpack_require__.r(__webpack_exports__);

    // 调用了d函数: 给 exports 设置了一个代理 definition
    // exports 对象中本身是没有对应的函数
    __webpack_require__.d(__webpack_exports__, {
      sum: function () {
        return sum;
      },
      mul: function () {
        return mul;
      },
    });

    const sum = (num1, num2) => {
      return num1 + num2;
    };
    const mul = (num1, num2) => {
      return num1 * num2;
    };
  },
};

// 2.模块的缓存
var __webpack_module_cache__ = {};

// 3.加载模块函数的实现
function __webpack_require__(moduleId) {
  if (__webpack_module_cache__[moduleId]) {
    return __webpack_module_cache__[moduleId].exports;
  }
  var module = (__webpack_module_cache__[moduleId] = {
    exports: {},
  });
  __webpack_modules__[moduleId](module, module.exports, __webpack_require__);

  return module.exports;
}

(function () {
  __webpack_require__.d = function (exports, definition) {
    for (var key in definition) {
      if (
        __webpack_require__.o(definition, key) &&
        !__webpack_require__.o(exports, key)
      ) {
        Object.defineProperty(exports, key, {
          enumerable: true,
          get: definition[key],
        });
      }
    }
  };
})();

(function () {
  __webpack_require__.o = function (obj, prop) {
    return Object.prototype.hasOwnProperty.call(obj, prop);
  };
})();

(function () {
  __webpack_require__.r = function (exports) {
    if (typeof Symbol !== "undefined" && Symbol.toStringTag) {
      Object.defineProperty(exports, Symbol.toStringTag, {
        value: "Module",
      });
    }
    Object.defineProperty(exports, "__esModule", {
      value: true,
    });
  };
})();

__webpack_require__("./src/es_index.js");

剪不断,理还乱...