Skip to content
文章摘要

快速认识 CommonJS 与 ES Module

CommonJS

社区规范

  • 通过exportsmodule.exports完成导出
  • 可用通过exports.xxx形式导出,但不能直接使用exports={}形式导出
  • 文件最后导出的是module.exports
js
// a.js
exports.name = "张三"; // 可以导出
exports = {name:"李四"}; // 不能导出
module.exports = {name:"王二"}; // 可以导出,但是会覆盖 exports.name

// index.js
const a = require('./a.js');
console.log(a); // {name:"王二"}
  • 为何exports = {name:"李四"};不能导出?

    可能会说是因为module.exports = {name:"王二"};覆盖了,并不是。因为文件最后导出的是module.exports对象。

    通过exports.xxx形式是改变的module.exports的子对象的,但是使用exports = {name:"王二"};的方式,并不会影像module.exports值。

    module.exports 不等于 exports module.exports.xxx 等于 exports.xxx

  • require的导入参数可以是 字符 也可以是 文件地址,是如何做到的?

    因为 require.main.paths,从当前目录一直到根目录的node_modules,依次次向上查找。通过依赖包package.json.main找到文件入口

    js
    [
        'D:\\Project\\demo\\ceshi\\node_modules',
        'D:\\Project\\demo\\node_modules',
        'D:\\Project\\node_modules',
        'D:\\node_modules'
    ]
  • require 缓存

    当我们多次require同一个包或文件时,require并不会获取最新的,而是通过require.cache查找是否已经缓存了模块,假如存在,则直接从缓存中取出。

    js
    require('./a.js');
    console.log(require.cache);
    /**
     * 大概格式如下:
     * [文件地址]:{id,path,exports,filename,loaded ...}
     */

ES Module (推荐)

以后会越来越倾向于 ES Module

提示

想要在Node项目中使用使用ES Module模式

  • 第一种:直接使用mjs格式文件
  • 第二种: package.jsontype 设置为 module
  • 第三种:直接使用各种网上已经配置好的脚手架
js
// a.mjs 文件 我采用了第一种,因为就俩文件,省事点
export const a = 1;
export default {b:2}

// index.mjs
import m from "./a.mjs"
console.log(m); // {b:2}

import {a} from "./a.mjs"
console.log(a); // 1

import * as n from "./a.mjs"
console.log(n); // {a:1}

两种导出方式,三种导入方式。如上所示。

区别

CommonJS是值拷贝,ES Module是值引用。

上例子:

CommonJS

js
// a.js
let a = 1;
exports.a = a;
exports.add = function () {
a = a + 1;
    return a
};
exports.get = function () {
    return a
};

// index.js

let { a, add,get }  = require("./a.js")
console.log(a); // 1
add();
console.log(a); // 1
console.log(get()); // 2

ES Module

js
// a.mjs
export let a = 1;
export const add = function () {
    a = a + 1;
    return a
};
export const get = function () {
    return a
};

// index.mjs
import { a, add, get } from "./a.mjs"
console.log(a); // 1
add()
console.log(a); // 2
console.log(get()); // 2
  • 两种规范下,CommonJS值拷贝,打印是 1 1 2ES Module值引用,打印1 2 2