CommonJS
在nodejs中,由於有且僅有一個入口文件(啓動文件),而開發一個應用肯定會涉及到多個文件配合,因此,nodejs對模塊化的需求比瀏覽器端要大的多
由於nodejs剛剛發佈的時候,前端沒有統一的、官方的模塊化規範,因此,它選擇使用社區提供的CommonJS作爲模塊化規範
在學習CommonJS之前,首先認識兩個重要的概念:模塊的導出和模塊的導入
模塊的導出
要理解模塊的導出,首先要理解模塊的含義
什麼是模塊?
模塊就是一個JS文件,它實現了一部分功能,並隱藏自己的內部實現,同時提供了一些接口供其他模塊使用
模塊有兩個核心要素:隱藏和暴露
隱藏的,是自己內部的實現
暴露的,是希望外部使用的接口
任何一個正常的模塊化標準,都應該默認隱藏模塊中的所有實現,而通過一些語法或api調用來暴露接口
暴露接口的過程即模塊的導出
module.exports = {
// 導出內容
}
// 或者
exports.導出名
模塊導入
當需要使用一個模塊時,使用的是該模塊暴露的部分(導出的部分),隱藏的部分是永遠無法使用的。
當通過某種語法或api去使用一個模塊時,這個過程叫做模塊的導入
const 接收這個對象參數 = require("./目錄"); // 需要絕對路徑
CommonJS規範
CommonJS使用exports導出模塊,require導入模塊
具體規範如下:
- 如果一個JS文件中存在exports或require,該JS文件是一個模塊
- 模塊內的所有代碼均爲隱藏代碼,包括全局變量、全局函數,這些全局的內容均不應該對全局變量造成任何污染
- 如果一個模塊需要暴露一些API提供給外部使用,需要通過exports導出,exports是一個空的對象,你可以爲該對象添加任何需要導出的內容
- 如果一個模塊需要導入其他模塊,通過require實現,require是一個函數,傳入模塊的路徑即可返回該模塊導出的整個內容
nodejs對CommonJS的實現
爲了實現CommonJS規範,nodejs對模塊做出了以下處理
-
爲了保證高效的執行,僅加載必要的模塊。nodejs只有執行到require函數時纔會加載並執行模塊
-
爲了隱藏模塊中的代碼,nodejs執行模塊時,會將模塊中的所有代碼放置到一個函數中執行,以保證不污染全局變量。
(function(){
//模塊中的代碼
})()
-
爲了保證順利的導出模塊內容,nodejs做了以下處理
- 在模塊開始執行前,初始化一個值module.exports = {}
- module.exports即模塊的導出值
- 爲了方便開發者便捷的導出,nodejs在初始化完module.exports後,又聲明瞭一個變量exports = module.exports
(function(module){
module.exports = {};
var exports = module.exports;
//模塊中的代碼
return module.exports;
})()
- 爲了避免反覆加載同一個模塊,nodejs默認開啓了模塊緩存,如果加載的模塊已經被加載過了,則會自動使用之前的導出結果
代碼
index.js
console.log("Hello NodeJs");
const util1 = require("./util.js");
const util2 = require("./util.js");
console.log(util1 === util2)
console.log(util1)
util.js
console.log("util模塊執行了!")
let sum = 0;
function getSum(){
return sum++;
}
exports.ff = 6;
執行順序!
Hello NodeJs
util模塊執行了!
true
{ ff: 6 }